opencv-ffi 0.0.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/.gitignore +7 -0
- data/Gemfile +15 -0
- data/README.md +126 -0
- data/Rakefile +52 -0
- data/docs/DocsIndex.md +1 -0
- data/docs/examples/load_image.rb +25 -0
- data/ext/Rakefile +13 -0
- data/ext/aishack-sift/.gitignore +4 -0
- data/ext/aishack-sift/Descriptor.h +34 -0
- data/ext/aishack-sift/KeyPoint.h +38 -0
- data/ext/aishack-sift/README +20 -0
- data/ext/aishack-sift/SIFT.cpp +1036 -0
- data/ext/aishack-sift/SIFT.h +84 -0
- data/ext/aishack-sift/example/.gitignore +2 -0
- data/ext/aishack-sift/example/Makefile +24 -0
- data/ext/aishack-sift/example/MySIFT.cpp +29 -0
- data/ext/aishack-sift/mkrf_conf.rb +13 -0
- data/ext/aishack-sift/siftlib.cpp +85 -0
- data/ext/eigen/.gitignore +4 -0
- data/ext/eigen/eigen_polynomial.cpp +41 -0
- data/ext/eigen/eigen_svd.cpp +100 -0
- data/ext/eigen/mkrf_conf.rb +14 -0
- data/ext/mkrf-monkey.rb +85 -0
- data/ext/mkrf-rakehelper-monkey.rb +52 -0
- data/ext/mkrf_conf.rb +3 -0
- data/ext/opencv-ffi/.gitignore +4 -0
- data/ext/opencv-ffi/matcher_helper.cpp +56 -0
- data/ext/opencv-ffi/mkrf_conf.rb +12 -0
- data/ext/opencv-ffi/vector_math.cpp +39 -0
- data/ext/opensurf/.gitignore +4 -0
- data/ext/opensurf/README +38 -0
- data/ext/opensurf/fasthessian.cpp +376 -0
- data/ext/opensurf/fasthessian.h +108 -0
- data/ext/opensurf/integral.cpp +58 -0
- data/ext/opensurf/integral.h +55 -0
- data/ext/opensurf/ipoint.cpp +108 -0
- data/ext/opensurf/ipoint.h +76 -0
- data/ext/opensurf/kmeans.h +172 -0
- data/ext/opensurf/mkrf_conf.rb +10 -0
- data/ext/opensurf/responselayer.h +92 -0
- data/ext/opensurf/surf.cpp +317 -0
- data/ext/opensurf/surf.h +66 -0
- data/ext/opensurf/surflib.cpp +98 -0
- data/ext/opensurf/surflib.h +96 -0
- data/ext/opensurf/utils.cpp +357 -0
- data/ext/opensurf/utils.h +63 -0
- data/lib/.gitignore +1 -0
- data/lib/opencv-ffi-ext/eigen.rb +84 -0
- data/lib/opencv-ffi-ext/features2d.rb +4 -0
- data/lib/opencv-ffi-ext/matcher_helper.rb +24 -0
- data/lib/opencv-ffi-ext/opensurf.rb +217 -0
- data/lib/opencv-ffi-ext/sift.rb +118 -0
- data/lib/opencv-ffi-ext/vector_math.rb +115 -0
- data/lib/opencv-ffi-wrappers.rb +7 -0
- data/lib/opencv-ffi-wrappers/core.rb +24 -0
- data/lib/opencv-ffi-wrappers/core/iplimage.rb +50 -0
- data/lib/opencv-ffi-wrappers/core/mat.rb +268 -0
- data/lib/opencv-ffi-wrappers/core/misc_draw.rb +44 -0
- data/lib/opencv-ffi-wrappers/core/point.rb +286 -0
- data/lib/opencv-ffi-wrappers/core/rect.rb +40 -0
- data/lib/opencv-ffi-wrappers/core/scalar.rb +104 -0
- data/lib/opencv-ffi-wrappers/core/size.rb +88 -0
- data/lib/opencv-ffi-wrappers/enumerable.rb +10 -0
- data/lib/opencv-ffi-wrappers/features2d.rb +17 -0
- data/lib/opencv-ffi-wrappers/features2d/image_patch.rb +322 -0
- data/lib/opencv-ffi-wrappers/features2d/star.rb +111 -0
- data/lib/opencv-ffi-wrappers/features2d/surf.rb +115 -0
- data/lib/opencv-ffi-wrappers/highgui.rb +10 -0
- data/lib/opencv-ffi-wrappers/imgproc.rb +4 -0
- data/lib/opencv-ffi-wrappers/imgproc/features.rb +35 -0
- data/lib/opencv-ffi-wrappers/imgproc/geometric.rb +39 -0
- data/lib/opencv-ffi-wrappers/matcher.rb +297 -0
- data/lib/opencv-ffi-wrappers/matrix.rb +37 -0
- data/lib/opencv-ffi-wrappers/misc.rb +41 -0
- data/lib/opencv-ffi-wrappers/misc/params.rb +34 -0
- data/lib/opencv-ffi-wrappers/sequence.rb +37 -0
- data/lib/opencv-ffi-wrappers/vectors.rb +38 -0
- data/lib/opencv-ffi.rb +12 -0
- data/lib/opencv-ffi/calib3d.rb +26 -0
- data/lib/opencv-ffi/core.rb +15 -0
- data/lib/opencv-ffi/core/draw.rb +68 -0
- data/lib/opencv-ffi/core/dynamic.rb +13 -0
- data/lib/opencv-ffi/core/library.rb +5 -0
- data/lib/opencv-ffi/core/operations.rb +122 -0
- data/lib/opencv-ffi/core/point.rb +22 -0
- data/lib/opencv-ffi/core/types.rb +172 -0
- data/lib/opencv-ffi/cvffi.rb +8 -0
- data/lib/opencv-ffi/features2d.rb +7 -0
- data/lib/opencv-ffi/features2d/library.rb +6 -0
- data/lib/opencv-ffi/features2d/star.rb +30 -0
- data/lib/opencv-ffi/features2d/surf.rb +38 -0
- data/lib/opencv-ffi/highgui.rb +31 -0
- data/lib/opencv-ffi/imgproc.rb +9 -0
- data/lib/opencv-ffi/imgproc/features.rb +37 -0
- data/lib/opencv-ffi/imgproc/geometric.rb +42 -0
- data/lib/opencv-ffi/imgproc/library.rb +6 -0
- data/lib/opencv-ffi/imgproc/misc.rb +39 -0
- data/lib/opencv-ffi/version.rb +3 -0
- data/opencv-ffi.gemspec +26 -0
- data/test/core/test_draw.rb +46 -0
- data/test/core/test_operations.rb +135 -0
- data/test/core/test_size.rb +14 -0
- data/test/core/test_text.rb +52 -0
- data/test/ext/test_eigen.rb +105 -0
- data/test/ext/test_opensurf.rb +35 -0
- data/test/ext/test_sift.rb +26 -0
- data/test/ext/test_vector_math.rb +85 -0
- data/test/features2d/test_surf.rb +63 -0
- data/test/imgproc/test_goodfeatures.rb +18 -0
- data/test/setup.rb +65 -0
- data/test/test_calib3d.rb +38 -0
- data/test/test_core.rb +26 -0
- data/test/test_ext.rb +8 -0
- data/test/test_features2d.rb +9 -0
- data/test/test_files/images/IMG_7088.JPG +0 -0
- data/test/test_files/images/IMG_7088_small.JPG +0 -0
- data/test/test_files/images/IMG_7089.JPG +0 -0
- data/test/test_highgui.rb +26 -0
- data/test/test_imgproc.rb +35 -0
- data/test/test_wrappers.rb +8 -0
- data/test/wrappers/core/test_draw.rb +41 -0
- data/test/wrappers/core/test_mat.rb +40 -0
- data/test/wrappers/core/test_operations.rb +35 -0
- data/test/wrappers/core/test_types.rb +235 -0
- data/test/wrappers/features2d/test_image_patch.rb +108 -0
- data/test/wrappers/test_imgproc.rb +87 -0
- data/test/wrappers/test_matcher.rb +96 -0
- data/test/wrappers/test_star.rb +28 -0
- data/test/wrappers/test_surf.rb +36 -0
- metadata +234 -0
|
@@ -0,0 +1,98 @@
|
|
|
1
|
+
|
|
2
|
+
#include <opencv2/core/types_c.h>
|
|
3
|
+
#include <opencv2/features2d/features2d.hpp>
|
|
4
|
+
#include "surflib.h"
|
|
5
|
+
|
|
6
|
+
#include <stdio.h>
|
|
7
|
+
|
|
8
|
+
typedef struct {
|
|
9
|
+
char upright;
|
|
10
|
+
int octaves, intervals, init_sample;
|
|
11
|
+
float thres;
|
|
12
|
+
} OpenSURFParams_t;
|
|
13
|
+
|
|
14
|
+
typedef struct {
|
|
15
|
+
CvPoint pt;
|
|
16
|
+
float scale;
|
|
17
|
+
float orientation;
|
|
18
|
+
int laplacian;
|
|
19
|
+
float descriptor[64];
|
|
20
|
+
} OpenSURFPoint_t;
|
|
21
|
+
|
|
22
|
+
/* "constructor" for OpenSURFPoint_t */
|
|
23
|
+
|
|
24
|
+
/* Ape the existing OpenCV interface a bit... */
|
|
25
|
+
extern "C"
|
|
26
|
+
CvSeq *openSurfDetect( IplImage *img,
|
|
27
|
+
CvMemStorage *storage,
|
|
28
|
+
OpenSURFParams_t params )
|
|
29
|
+
{
|
|
30
|
+
std::vector<Ipoint> ipts;
|
|
31
|
+
|
|
32
|
+
surfDet( img, ipts, params.octaves, params.intervals, params.init_sample, params.thres );
|
|
33
|
+
|
|
34
|
+
/* Now unpack the ipts to keypoints */
|
|
35
|
+
CvSeq *points = cvCreateSeq( 0, sizeof(CvSeq), sizeof(OpenSURFPoint_t), storage );
|
|
36
|
+
|
|
37
|
+
for( std::vector<Ipoint>::iterator i = ipts.begin(); i != ipts.end(); i++ ) {
|
|
38
|
+
// TODO. Impedence mismatch trying to match CVSurf's "size" and "hessian"
|
|
39
|
+
OpenSURFPoint_t point;
|
|
40
|
+
point.pt.x = (*i).x;
|
|
41
|
+
point.pt.y = (*i).y;
|
|
42
|
+
point.scale = (*i).scale;
|
|
43
|
+
point.orientation = (*i).orientation;
|
|
44
|
+
point.laplacian = (*i).laplacian;
|
|
45
|
+
|
|
46
|
+
cvSeqPush( points, &point );
|
|
47
|
+
}
|
|
48
|
+
|
|
49
|
+
return points;
|
|
50
|
+
}
|
|
51
|
+
|
|
52
|
+
|
|
53
|
+
extern "C"
|
|
54
|
+
CvSeq *openSurfDescribe( IplImage *img, CvSeq *points,
|
|
55
|
+
OpenSURFParams_t params )
|
|
56
|
+
{
|
|
57
|
+
/* Repack the CvSeq to ipts */
|
|
58
|
+
std::vector<Ipoint> ipts;
|
|
59
|
+
|
|
60
|
+
CvSeqReader reader;
|
|
61
|
+
cvStartReadSeq( points, &reader, 0 );
|
|
62
|
+
for( int i = 0; i < points->total; i++ ) {
|
|
63
|
+
OpenSURFPoint_t *point = (OpenSURFPoint_t *)reader.ptr;
|
|
64
|
+
Ipoint ip;
|
|
65
|
+
|
|
66
|
+
ip.x = point->pt.x;
|
|
67
|
+
ip.y = point->pt.y;
|
|
68
|
+
ip.scale = point->scale;
|
|
69
|
+
ip.orientation = point->orientation;
|
|
70
|
+
ip.laplacian = point->laplacian;
|
|
71
|
+
|
|
72
|
+
ipts.push_back(ip);
|
|
73
|
+
|
|
74
|
+
CV_NEXT_SEQ_ELEM( points->elem_size, reader );
|
|
75
|
+
}
|
|
76
|
+
|
|
77
|
+
surfDes( img, ipts, params.upright );
|
|
78
|
+
|
|
79
|
+
for(unsigned int i = 0; i < ipts.size(); i++ ) {
|
|
80
|
+
Ipoint pt( ipts[i] );
|
|
81
|
+
OpenSURFPoint_t *point = (OpenSURFPoint_t *)cvGetSeqElem( points, i );
|
|
82
|
+
point->pt.x = pt.x;
|
|
83
|
+
point->pt.y = pt.y;
|
|
84
|
+
point->scale = pt.scale;
|
|
85
|
+
point->orientation = pt.orientation;
|
|
86
|
+
point->laplacian = pt.laplacian;
|
|
87
|
+
memcpy( point->descriptor, pt.descriptor, sizeof(float)*64 );
|
|
88
|
+
}
|
|
89
|
+
|
|
90
|
+
return points;
|
|
91
|
+
}
|
|
92
|
+
|
|
93
|
+
extern "C"
|
|
94
|
+
CvSeq *createOpenSURFPointSequence( CvMemStorage *storage )
|
|
95
|
+
{
|
|
96
|
+
return cvCreateSeq( 0, sizeof(CvSeq), sizeof(OpenSURFPoint_t), storage );
|
|
97
|
+
}
|
|
98
|
+
|
|
@@ -0,0 +1,96 @@
|
|
|
1
|
+
/***********************************************************
|
|
2
|
+
* --- OpenSURF --- *
|
|
3
|
+
* This library is distributed under the GNU GPL. Please *
|
|
4
|
+
* use the contact form at http://www.chrisevansdev.com *
|
|
5
|
+
* for more information. *
|
|
6
|
+
* *
|
|
7
|
+
* C. Evans, Research Into Robust Visual Features, *
|
|
8
|
+
* MSc University of Bristol, 2008. *
|
|
9
|
+
* *
|
|
10
|
+
************************************************************/
|
|
11
|
+
|
|
12
|
+
#ifndef SURFLIB_H
|
|
13
|
+
#define SURFLIB_H
|
|
14
|
+
|
|
15
|
+
#include <opencv2/core/core.hpp>
|
|
16
|
+
|
|
17
|
+
#include "integral.h"
|
|
18
|
+
#include "fasthessian.h"
|
|
19
|
+
#include "surf.h"
|
|
20
|
+
#include "ipoint.h"
|
|
21
|
+
#include "utils.h"
|
|
22
|
+
|
|
23
|
+
|
|
24
|
+
//! Library function builds vector of described interest points
|
|
25
|
+
inline void surfDetDes(IplImage *img, /* image to find Ipoints in */
|
|
26
|
+
std::vector<Ipoint> &ipts, /* reference to vector of Ipoints */
|
|
27
|
+
bool upright = false, /* run in rotation invariant mode? */
|
|
28
|
+
int octaves = OCTAVES, /* number of octaves to calculate */
|
|
29
|
+
int intervals = INTERVALS, /* number of intervals per octave */
|
|
30
|
+
int init_sample = INIT_SAMPLE, /* initial sampling step */
|
|
31
|
+
float thres = THRES /* blob response threshold */)
|
|
32
|
+
{
|
|
33
|
+
// Create integral-image representation of the image
|
|
34
|
+
IplImage *int_img = Integral(img);
|
|
35
|
+
|
|
36
|
+
// Create Fast Hessian Object
|
|
37
|
+
FastHessian fh(int_img, ipts, octaves, intervals, init_sample, thres);
|
|
38
|
+
|
|
39
|
+
// Extract interest points and store in vector ipts
|
|
40
|
+
fh.getIpoints();
|
|
41
|
+
|
|
42
|
+
// Create Surf Descriptor Object
|
|
43
|
+
Surf des(int_img, ipts);
|
|
44
|
+
|
|
45
|
+
// Extract the descriptors for the ipts
|
|
46
|
+
des.getDescriptors(upright);
|
|
47
|
+
|
|
48
|
+
// Deallocate the integral image
|
|
49
|
+
cvReleaseImage(&int_img);
|
|
50
|
+
}
|
|
51
|
+
|
|
52
|
+
|
|
53
|
+
//! Library function builds vector of interest points
|
|
54
|
+
inline void surfDet(IplImage *img, /* image to find Ipoints in */
|
|
55
|
+
std::vector<Ipoint> &ipts, /* reference to vector of Ipoints */
|
|
56
|
+
int octaves = OCTAVES, /* number of octaves to calculate */
|
|
57
|
+
int intervals = INTERVALS, /* number of intervals per octave */
|
|
58
|
+
int init_sample = INIT_SAMPLE, /* initial sampling step */
|
|
59
|
+
float thres = THRES /* blob response threshold */)
|
|
60
|
+
{
|
|
61
|
+
// Create integral image representation of the image
|
|
62
|
+
IplImage *int_img = Integral(img);
|
|
63
|
+
|
|
64
|
+
// Create Fast Hessian Object
|
|
65
|
+
FastHessian fh(int_img, ipts, octaves, intervals, init_sample, thres);
|
|
66
|
+
|
|
67
|
+
// Extract interest points and store in vector ipts
|
|
68
|
+
fh.getIpoints();
|
|
69
|
+
|
|
70
|
+
// Deallocate the integral image
|
|
71
|
+
cvReleaseImage(&int_img);
|
|
72
|
+
}
|
|
73
|
+
|
|
74
|
+
|
|
75
|
+
|
|
76
|
+
|
|
77
|
+
//! Library function describes interest points in vector
|
|
78
|
+
inline void surfDes(IplImage *img, /* image to find Ipoints in */
|
|
79
|
+
std::vector<Ipoint> &ipts, /* reference to vector of Ipoints */
|
|
80
|
+
bool upright = false) /* run in rotation invariant mode? */
|
|
81
|
+
{
|
|
82
|
+
// Create integral image representation of the image
|
|
83
|
+
IplImage *int_img = Integral(img);
|
|
84
|
+
|
|
85
|
+
// Create Surf Descriptor Object
|
|
86
|
+
Surf des(int_img, ipts);
|
|
87
|
+
|
|
88
|
+
// Extract the descriptors for the ipts
|
|
89
|
+
des.getDescriptors(upright);
|
|
90
|
+
|
|
91
|
+
// Deallocate the integral image
|
|
92
|
+
cvReleaseImage(&int_img);
|
|
93
|
+
}
|
|
94
|
+
|
|
95
|
+
|
|
96
|
+
#endif
|
|
@@ -0,0 +1,357 @@
|
|
|
1
|
+
/***********************************************************
|
|
2
|
+
* --- OpenSURF --- *
|
|
3
|
+
* This library is distributed under the GNU GPL. Please *
|
|
4
|
+
* use the contact form at http://www.chrisevansdev.com *
|
|
5
|
+
* for more information. *
|
|
6
|
+
* *
|
|
7
|
+
* C. Evans, Research Into Robust Visual Features, *
|
|
8
|
+
* MSc University of Bristol, 2008. *
|
|
9
|
+
* *
|
|
10
|
+
************************************************************/
|
|
11
|
+
|
|
12
|
+
#include <opencv2/highgui/highgui_c.h>
|
|
13
|
+
#include <opencv2/core/core_c.h>
|
|
14
|
+
#include <opencv2/imgproc/imgproc_c.h>
|
|
15
|
+
#include <iostream>
|
|
16
|
+
#include <fstream>
|
|
17
|
+
#include <time.h>
|
|
18
|
+
|
|
19
|
+
#include "utils.h"
|
|
20
|
+
|
|
21
|
+
using namespace std;
|
|
22
|
+
|
|
23
|
+
//-------------------------------------------------------
|
|
24
|
+
|
|
25
|
+
static const int NCOLOURS = 8;
|
|
26
|
+
static const CvScalar COLOURS [] = {cvScalar(255,0,0), cvScalar(0,255,0),
|
|
27
|
+
cvScalar(0,0,255), cvScalar(255,255,0),
|
|
28
|
+
cvScalar(0,255,255), cvScalar(255,0,255),
|
|
29
|
+
cvScalar(255,255,255), cvScalar(0,0,0)};
|
|
30
|
+
|
|
31
|
+
//-------------------------------------------------------
|
|
32
|
+
|
|
33
|
+
//! Display error message and terminate program
|
|
34
|
+
void error(const char *msg)
|
|
35
|
+
{
|
|
36
|
+
cout << "\nError: " << msg;
|
|
37
|
+
getchar();
|
|
38
|
+
exit(0);
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
//-------------------------------------------------------
|
|
42
|
+
|
|
43
|
+
//! Show the provided image and wait for keypress
|
|
44
|
+
void showImage(const IplImage *img)
|
|
45
|
+
{
|
|
46
|
+
cvNamedWindow("Surf", CV_WINDOW_AUTOSIZE);
|
|
47
|
+
cvShowImage("Surf", img);
|
|
48
|
+
cvWaitKey(0);
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
//-------------------------------------------------------
|
|
52
|
+
|
|
53
|
+
//! Show the provided image in titled window and wait for keypress
|
|
54
|
+
void showImage(char *title,const IplImage *img)
|
|
55
|
+
{
|
|
56
|
+
cvNamedWindow(title, CV_WINDOW_AUTOSIZE);
|
|
57
|
+
cvShowImage(title, img);
|
|
58
|
+
cvWaitKey(0);
|
|
59
|
+
}
|
|
60
|
+
|
|
61
|
+
//-------------------------------------------------------
|
|
62
|
+
|
|
63
|
+
// Convert image to single channel 32F
|
|
64
|
+
IplImage *getGray(const IplImage *img)
|
|
65
|
+
{
|
|
66
|
+
// Check we have been supplied a non-null img pointer
|
|
67
|
+
if (!img) error("Unable to create grayscale image. No image supplied");
|
|
68
|
+
|
|
69
|
+
IplImage* gray8, * gray32;
|
|
70
|
+
|
|
71
|
+
gray32 = cvCreateImage( cvGetSize(img), IPL_DEPTH_32F, 1 );
|
|
72
|
+
|
|
73
|
+
if( img->nChannels == 1 )
|
|
74
|
+
gray8 = (IplImage *) cvClone( img );
|
|
75
|
+
else {
|
|
76
|
+
gray8 = cvCreateImage( cvGetSize(img), IPL_DEPTH_8U, 1 );
|
|
77
|
+
cvCvtColor( img, gray8, CV_BGR2GRAY );
|
|
78
|
+
}
|
|
79
|
+
|
|
80
|
+
cvConvertScale( gray8, gray32, 1.0 / 255.0, 0 );
|
|
81
|
+
|
|
82
|
+
cvReleaseImage( &gray8 );
|
|
83
|
+
return gray32;
|
|
84
|
+
}
|
|
85
|
+
|
|
86
|
+
//-------------------------------------------------------
|
|
87
|
+
|
|
88
|
+
//! Draw all the Ipoints in the provided vector
|
|
89
|
+
void drawIpoints(IplImage *img, vector<Ipoint> &ipts, int tailSize)
|
|
90
|
+
{
|
|
91
|
+
Ipoint *ipt;
|
|
92
|
+
float s, o;
|
|
93
|
+
int r1, c1, r2, c2, lap;
|
|
94
|
+
|
|
95
|
+
for(unsigned int i = 0; i < ipts.size(); i++)
|
|
96
|
+
{
|
|
97
|
+
ipt = &ipts.at(i);
|
|
98
|
+
s = (2.5f * ipt->scale);
|
|
99
|
+
o = ipt->orientation;
|
|
100
|
+
lap = ipt->laplacian;
|
|
101
|
+
r1 = fRound(ipt->y);
|
|
102
|
+
c1 = fRound(ipt->x);
|
|
103
|
+
c2 = fRound(s * cos(o)) + c1;
|
|
104
|
+
r2 = fRound(s * sin(o)) + r1;
|
|
105
|
+
|
|
106
|
+
if (o) // Green line indicates orientation
|
|
107
|
+
cvLine(img, cvPoint(c1, r1), cvPoint(c2, r2), cvScalar(0, 255, 0));
|
|
108
|
+
else // Green dot if using upright version
|
|
109
|
+
cvCircle(img, cvPoint(c1,r1), 1, cvScalar(0, 255, 0),-1);
|
|
110
|
+
|
|
111
|
+
if (lap == 1)
|
|
112
|
+
{ // Blue circles indicate dark blobs on light backgrounds
|
|
113
|
+
cvCircle(img, cvPoint(c1,r1), fRound(s), cvScalar(255, 0, 0),1);
|
|
114
|
+
}
|
|
115
|
+
else if (lap == 0)
|
|
116
|
+
{ // Red circles indicate light blobs on dark backgrounds
|
|
117
|
+
cvCircle(img, cvPoint(c1,r1), fRound(s), cvScalar(0, 0, 255),1);
|
|
118
|
+
}
|
|
119
|
+
else if (lap == 9)
|
|
120
|
+
{ // Red circles indicate light blobs on dark backgrounds
|
|
121
|
+
cvCircle(img, cvPoint(c1,r1), fRound(s), cvScalar(0, 255, 0),1);
|
|
122
|
+
}
|
|
123
|
+
|
|
124
|
+
// Draw motion from ipoint dx and dy
|
|
125
|
+
if (tailSize)
|
|
126
|
+
{
|
|
127
|
+
cvLine(img, cvPoint(c1,r1),
|
|
128
|
+
cvPoint(int(c1+ipt->dx*tailSize), int(r1+ipt->dy*tailSize)),
|
|
129
|
+
cvScalar(255,255,255), 1);
|
|
130
|
+
}
|
|
131
|
+
}
|
|
132
|
+
}
|
|
133
|
+
|
|
134
|
+
//-------------------------------------------------------
|
|
135
|
+
|
|
136
|
+
//! Draw a single feature on the image
|
|
137
|
+
void drawIpoint(IplImage *img, Ipoint &ipt, int tailSize)
|
|
138
|
+
{
|
|
139
|
+
float s, o;
|
|
140
|
+
int r1, c1, r2, c2, lap;
|
|
141
|
+
|
|
142
|
+
s = (2.5f * ipt.scale);
|
|
143
|
+
o = ipt.orientation;
|
|
144
|
+
lap = ipt.laplacian;
|
|
145
|
+
r1 = fRound(ipt.y);
|
|
146
|
+
c1 = fRound(ipt.x);
|
|
147
|
+
|
|
148
|
+
// Green line indicates orientation
|
|
149
|
+
if (o) // Green line indicates orientation
|
|
150
|
+
{
|
|
151
|
+
c2 = fRound(s * cos(o)) + c1;
|
|
152
|
+
r2 = fRound(s * sin(o)) + r1;
|
|
153
|
+
cvLine(img, cvPoint(c1, r1), cvPoint(c2, r2), cvScalar(0, 255, 0));
|
|
154
|
+
}
|
|
155
|
+
else // Green dot if using upright version
|
|
156
|
+
cvCircle(img, cvPoint(c1,r1), 1, cvScalar(0, 255, 0),-1);
|
|
157
|
+
|
|
158
|
+
if (lap >= 0)
|
|
159
|
+
{ // Blue circles indicate light blobs on dark backgrounds
|
|
160
|
+
cvCircle(img, cvPoint(c1,r1), fRound(s), cvScalar(255, 0, 0),1);
|
|
161
|
+
}
|
|
162
|
+
else
|
|
163
|
+
{ // Red circles indicate light blobs on dark backgrounds
|
|
164
|
+
cvCircle(img, cvPoint(c1,r1), fRound(s), cvScalar(0, 0, 255),1);
|
|
165
|
+
}
|
|
166
|
+
|
|
167
|
+
// Draw motion from ipoint dx and dy
|
|
168
|
+
if (tailSize)
|
|
169
|
+
{
|
|
170
|
+
cvLine(img, cvPoint(c1,r1),
|
|
171
|
+
cvPoint(int(c1+ipt.dx*tailSize), int(r1+ipt.dy*tailSize)),
|
|
172
|
+
cvScalar(255,255,255), 1);
|
|
173
|
+
}
|
|
174
|
+
}
|
|
175
|
+
|
|
176
|
+
//-------------------------------------------------------
|
|
177
|
+
|
|
178
|
+
//! Draw a single feature on the image
|
|
179
|
+
void drawPoint(IplImage *img, Ipoint &ipt)
|
|
180
|
+
{
|
|
181
|
+
float s, o;
|
|
182
|
+
int r1, c1;
|
|
183
|
+
|
|
184
|
+
s = 3;
|
|
185
|
+
o = ipt.orientation;
|
|
186
|
+
r1 = fRound(ipt.y);
|
|
187
|
+
c1 = fRound(ipt.x);
|
|
188
|
+
|
|
189
|
+
cvCircle(img, cvPoint(c1,r1), fRound(s), COLOURS[ipt.clusterIndex%NCOLOURS], -1);
|
|
190
|
+
cvCircle(img, cvPoint(c1,r1), fRound(s+1), COLOURS[(ipt.clusterIndex+1)%NCOLOURS], 2);
|
|
191
|
+
|
|
192
|
+
}
|
|
193
|
+
|
|
194
|
+
//-------------------------------------------------------
|
|
195
|
+
|
|
196
|
+
//! Draw a single feature on the image
|
|
197
|
+
void drawPoints(IplImage *img, vector<Ipoint> &ipts)
|
|
198
|
+
{
|
|
199
|
+
float s, o;
|
|
200
|
+
int r1, c1;
|
|
201
|
+
|
|
202
|
+
for(unsigned int i = 0; i < ipts.size(); i++)
|
|
203
|
+
{
|
|
204
|
+
s = 3;
|
|
205
|
+
o = ipts[i].orientation;
|
|
206
|
+
r1 = fRound(ipts[i].y);
|
|
207
|
+
c1 = fRound(ipts[i].x);
|
|
208
|
+
|
|
209
|
+
cvCircle(img, cvPoint(c1,r1), fRound(s), COLOURS[ipts[i].clusterIndex%NCOLOURS], -1);
|
|
210
|
+
cvCircle(img, cvPoint(c1,r1), fRound(s+1), COLOURS[(ipts[i].clusterIndex+1)%NCOLOURS], 2);
|
|
211
|
+
}
|
|
212
|
+
}
|
|
213
|
+
|
|
214
|
+
//-------------------------------------------------------
|
|
215
|
+
|
|
216
|
+
//! Draw descriptor windows around Ipoints in the provided vector
|
|
217
|
+
void drawWindows(IplImage *img, vector<Ipoint> &ipts)
|
|
218
|
+
{
|
|
219
|
+
Ipoint *ipt;
|
|
220
|
+
float s, o, cd, sd;
|
|
221
|
+
int x, y;
|
|
222
|
+
CvPoint2D32f src[4];
|
|
223
|
+
|
|
224
|
+
for(unsigned int i = 0; i < ipts.size(); i++)
|
|
225
|
+
{
|
|
226
|
+
ipt = &ipts.at(i);
|
|
227
|
+
s = (10 * ipt->scale);
|
|
228
|
+
o = ipt->orientation;
|
|
229
|
+
y = fRound(ipt->y);
|
|
230
|
+
x = fRound(ipt->x);
|
|
231
|
+
cd = cos(o);
|
|
232
|
+
sd = sin(o);
|
|
233
|
+
|
|
234
|
+
src[0].x=sd*s+cd*s+x; src[0].y=-cd*s+sd*s+y;
|
|
235
|
+
src[1].x=sd*s+cd*-s+x; src[1].y=-cd*s+sd*-s+y;
|
|
236
|
+
src[2].x=sd*-s+cd*-s+x; src[2].y=-cd*-s+sd*-s+y;
|
|
237
|
+
src[3].x=sd*-s+cd*s+x; src[3].y=-cd*-s+sd*s+y;
|
|
238
|
+
|
|
239
|
+
if (o) // Draw orientation line
|
|
240
|
+
cvLine(img, cvPoint(x, y),
|
|
241
|
+
cvPoint(fRound(s*cd + x), fRound(s*sd + y)), cvScalar(0, 255, 0),1);
|
|
242
|
+
else // Green dot if using upright version
|
|
243
|
+
cvCircle(img, cvPoint(x,y), 1, cvScalar(0, 255, 0),-1);
|
|
244
|
+
|
|
245
|
+
|
|
246
|
+
// Draw box window around the point
|
|
247
|
+
cvLine(img, cvPoint(fRound(src[0].x), fRound(src[0].y)),
|
|
248
|
+
cvPoint(fRound(src[1].x), fRound(src[1].y)), cvScalar(255, 0, 0),2);
|
|
249
|
+
cvLine(img, cvPoint(fRound(src[1].x), fRound(src[1].y)),
|
|
250
|
+
cvPoint(fRound(src[2].x), fRound(src[2].y)), cvScalar(255, 0, 0),2);
|
|
251
|
+
cvLine(img, cvPoint(fRound(src[2].x), fRound(src[2].y)),
|
|
252
|
+
cvPoint(fRound(src[3].x), fRound(src[3].y)), cvScalar(255, 0, 0),2);
|
|
253
|
+
cvLine(img, cvPoint(fRound(src[3].x), fRound(src[3].y)),
|
|
254
|
+
cvPoint(fRound(src[0].x), fRound(src[0].y)), cvScalar(255, 0, 0),2);
|
|
255
|
+
|
|
256
|
+
}
|
|
257
|
+
}
|
|
258
|
+
|
|
259
|
+
//-------------------------------------------------------
|
|
260
|
+
|
|
261
|
+
// Draw the FPS figure on the image (requires at least 2 calls)
|
|
262
|
+
void drawFPS(IplImage *img)
|
|
263
|
+
{
|
|
264
|
+
static int counter = 0;
|
|
265
|
+
static clock_t t;
|
|
266
|
+
static float fps;
|
|
267
|
+
char fps_text[20];
|
|
268
|
+
CvFont font;
|
|
269
|
+
cvInitFont(&font,CV_FONT_HERSHEY_SIMPLEX|CV_FONT_ITALIC, 1.0,1.0,0,2);
|
|
270
|
+
|
|
271
|
+
// Add fps figure (every 10 frames)
|
|
272
|
+
if (counter > 10)
|
|
273
|
+
{
|
|
274
|
+
fps = (10.0f/(clock()-t) * CLOCKS_PER_SEC);
|
|
275
|
+
t=clock();
|
|
276
|
+
counter = 0;
|
|
277
|
+
}
|
|
278
|
+
|
|
279
|
+
// Increment counter
|
|
280
|
+
++counter;
|
|
281
|
+
|
|
282
|
+
// Get the figure as a string
|
|
283
|
+
sprintf(fps_text,"FPS: %.2f",fps);
|
|
284
|
+
|
|
285
|
+
// Draw the string on the image
|
|
286
|
+
cvPutText (img,fps_text,cvPoint(10,25), &font, cvScalar(255,255,0));
|
|
287
|
+
}
|
|
288
|
+
|
|
289
|
+
//-------------------------------------------------------
|
|
290
|
+
|
|
291
|
+
//! Save the SURF features to file
|
|
292
|
+
void saveSurf(char *filename, vector<Ipoint> &ipts)
|
|
293
|
+
{
|
|
294
|
+
ofstream outfile(filename);
|
|
295
|
+
|
|
296
|
+
// output descriptor length
|
|
297
|
+
outfile << "64\n";
|
|
298
|
+
outfile << ipts.size() << "\n";
|
|
299
|
+
|
|
300
|
+
// create output line as: scale x y des
|
|
301
|
+
for(unsigned int i=0; i < ipts.size(); i++)
|
|
302
|
+
{
|
|
303
|
+
outfile << ipts.at(i).scale << " ";
|
|
304
|
+
outfile << ipts.at(i).x << " ";
|
|
305
|
+
outfile << ipts.at(i).y << " ";
|
|
306
|
+
outfile << ipts.at(i).orientation << " ";
|
|
307
|
+
outfile << ipts.at(i).laplacian << " ";
|
|
308
|
+
outfile << ipts.at(i).scale << " ";
|
|
309
|
+
for(int j=0; j<64; j++)
|
|
310
|
+
outfile << ipts.at(i).descriptor[j] << " ";
|
|
311
|
+
|
|
312
|
+
outfile << "\n";
|
|
313
|
+
}
|
|
314
|
+
|
|
315
|
+
outfile.close();
|
|
316
|
+
}
|
|
317
|
+
|
|
318
|
+
//-------------------------------------------------------
|
|
319
|
+
|
|
320
|
+
//! Load the SURF features from file
|
|
321
|
+
void loadSurf(char *filename, vector<Ipoint> &ipts)
|
|
322
|
+
{
|
|
323
|
+
int descriptorLength, count;
|
|
324
|
+
ifstream infile(filename);
|
|
325
|
+
|
|
326
|
+
// clear the ipts vector first
|
|
327
|
+
ipts.clear();
|
|
328
|
+
|
|
329
|
+
// read descriptor length/number of ipoints
|
|
330
|
+
infile >> descriptorLength;
|
|
331
|
+
infile >> count;
|
|
332
|
+
|
|
333
|
+
// for each ipoint
|
|
334
|
+
for (int i = 0; i < count; i++)
|
|
335
|
+
{
|
|
336
|
+
Ipoint ipt;
|
|
337
|
+
|
|
338
|
+
// read vals
|
|
339
|
+
infile >> ipt.scale;
|
|
340
|
+
infile >> ipt.x;
|
|
341
|
+
infile >> ipt.y;
|
|
342
|
+
infile >> ipt.orientation;
|
|
343
|
+
infile >> ipt.laplacian;
|
|
344
|
+
infile >> ipt.scale;
|
|
345
|
+
|
|
346
|
+
// read descriptor components
|
|
347
|
+
for (int j = 0; j < 64; j++)
|
|
348
|
+
infile >> ipt.descriptor[j];
|
|
349
|
+
|
|
350
|
+
ipts.push_back(ipt);
|
|
351
|
+
|
|
352
|
+
}
|
|
353
|
+
}
|
|
354
|
+
|
|
355
|
+
//-------------------------------------------------------
|
|
356
|
+
|
|
357
|
+
//-------------------------------------------------------
|