51 #include "visp/vpConfig.h"
53 #ifdef VISP_HAVE_OPENCV
57 #include "vpKltOpencv.h"
59 void vpKltOpencv::clean()
61 if (image) cvReleaseImage(&image);
62 if (prev_image) cvReleaseImage(&prev_image);
63 if (pyramid) cvReleaseImage(&pyramid);
64 if (prev_pyramid) cvReleaseImage(&prev_pyramid);
73 countPrevFeatures = 0;
76 globalcountFeatures = 0;
79 void vpKltOpencv::cleanAll()
82 if (features) cvFree(&features);
83 if (prev_features) cvFree(&prev_features);
84 if (status) cvFree(&status);
85 if (lostDuringTrack) cvFree(&lostDuringTrack);
86 if (featuresid) cvFree(&featuresid);
87 if (prev_featuresid) cvFree(&prev_featuresid);
93 prev_featuresid = NULL;
96 void vpKltOpencv::reset()
106 : initialized(0), maxFeatures(50), globalcountFeatures(0), win_size(10), quality(0.01),
107 min_distance(10), harris_free_parameter(0.04), block_size(3), use_harris(1),
108 pyramid_level(3), _tid(-1), image(NULL), prev_image(NULL), pyramid(NULL),
109 prev_pyramid(NULL), swap_temp(NULL), countFeatures(0), countPrevFeatures(0),
110 features(NULL), prev_features(NULL), featuresid(NULL), prev_featuresid(NULL),
111 flags(0), initial_guess(false), lostDuringTrack(0), status(0), OnInitialize(0),
112 OnFeatureLost(0), OnNewFeature(0), OnMeasureFeature(0), IsFeatureValid(0)
114 features = (CvPoint2D32f*)cvAlloc((
unsigned int)maxFeatures*
sizeof(features[0]));
115 prev_features = (CvPoint2D32f*)cvAlloc((
unsigned int)maxFeatures*
sizeof(prev_features[0]));
116 status = (
char*)cvAlloc((
size_t)maxFeatures);
117 lostDuringTrack = (
bool*)cvAlloc((
size_t)maxFeatures);
118 featuresid = (
long*)cvAlloc((
unsigned int)maxFeatures*
sizeof(long));
119 prev_featuresid = (
long*)cvAlloc((
unsigned int)maxFeatures*
sizeof(long));
126 : initialized(0), maxFeatures(50), globalcountFeatures(0), win_size(10), quality(0.01),
127 min_distance(10), harris_free_parameter(0.04), block_size(3), use_harris(1),
128 pyramid_level(3), _tid(-1), image(NULL), prev_image(NULL), pyramid(NULL),
129 prev_pyramid(NULL), swap_temp(NULL), countFeatures(0), countPrevFeatures(0),
130 features(NULL), prev_features(NULL), featuresid(NULL), prev_featuresid(NULL),
131 flags(0), initial_guess(false), lostDuringTrack(0), status(0), OnInitialize(0),
132 OnFeatureLost(0), OnNewFeature(0), OnMeasureFeature(0), IsFeatureValid(0)
143 initialized = copy.initialized;
144 maxFeatures = copy.maxFeatures;
145 countFeatures = copy.countFeatures;
146 countPrevFeatures = copy.countPrevFeatures;
147 globalcountFeatures = copy.globalcountFeatures;
149 win_size = copy.win_size;
150 quality = copy.quality;
151 min_distance = copy.min_distance;
152 harris_free_parameter = copy.harris_free_parameter;
153 block_size = copy.block_size;
154 use_harris = copy.use_harris;
155 pyramid_level = copy.pyramid_level;
158 OnInitialize = copy.OnInitialize;
159 OnFeatureLost = copy.OnFeatureLost;
160 OnNewFeature = copy.OnNewFeature;
161 OnMeasureFeature = copy.OnMeasureFeature;
162 IsFeatureValid = copy.IsFeatureValid;
164 initial_guess = copy.initial_guess;
165 lostDuringTrack = copy.lostDuringTrack;
171 countPrevFeatures = 0;
174 globalcountFeatures = 0;
179 image = cvCreateImage(cvGetSize(copy.image), 8, 1);
181 cvCopy(copy.image, image, 0);
186 prev_image = cvCreateImage(cvGetSize(copy.prev_image), IPL_DEPTH_8U, 1);
188 cvCopy(copy.prev_image, prev_image, 0);
193 pyramid = cvCreateImage(cvGetSize(copy.pyramid), IPL_DEPTH_8U, 1);
195 cvCopy(copy.pyramid, pyramid, 0);
198 if (copy.prev_pyramid)
200 prev_pyramid = cvCreateImage(cvGetSize(copy.prev_pyramid), IPL_DEPTH_8U, 1);
202 cvCopy(copy.prev_pyramid, prev_pyramid, 0);
208 (CvPoint2D32f*)cvAlloc((
unsigned int)copy.maxFeatures*
sizeof(CvPoint2D32f));
209 for (
int i = 0; i < copy.maxFeatures; i++)
210 features[i] = copy.features[i];
213 if (copy.prev_features) {
215 (CvPoint2D32f*)cvAlloc((
unsigned int)copy.maxFeatures*
sizeof(CvPoint2D32f));
216 for (
int i = 0; i < copy.maxFeatures; i++)
217 prev_features[i] = copy.prev_features[i];
220 if (copy.featuresid) {
221 featuresid = (
long*)cvAlloc((
unsigned int)copy.maxFeatures*
sizeof(long));
222 for (
int i = 0; i < copy.maxFeatures; i++)
223 featuresid[i] = copy.featuresid[i];
226 if (copy.prev_featuresid) {
227 prev_featuresid = (
long*)cvAlloc((
unsigned int)copy.maxFeatures*
sizeof(long));
228 for (
int i = 0; i < copy.maxFeatures; i++)
229 prev_featuresid[i] = copy.prev_featuresid[i];
233 status = (
char*)cvAlloc((
unsigned int)copy.maxFeatures*
sizeof(char));
234 for (
int i = 0; i < copy.maxFeatures; i++)
235 status[i] = copy.status[i];
238 if (copy.lostDuringTrack) {
239 lostDuringTrack = (
bool*)cvAlloc((
unsigned int)copy.maxFeatures*
sizeof(bool));
240 for (
int i = 0; i < copy.maxFeatures; i++)
241 lostDuringTrack[i] = copy.lostDuringTrack[i];
260 initialized = 0; maxFeatures=input;
262 if (features) cvFree(&features);
263 if (prev_features) cvFree(&prev_features);
264 if (status) cvFree(&status);
265 if (lostDuringTrack) cvFree(&lostDuringTrack);
266 if (featuresid) cvFree(&featuresid);
267 if (prev_featuresid) cvFree(&prev_featuresid);
270 features = (CvPoint2D32f*)cvAlloc((
unsigned int)maxFeatures*
sizeof(CvPoint2D32f));
271 prev_features = (CvPoint2D32f*)cvAlloc((
unsigned int)maxFeatures*
sizeof(CvPoint2D32f));
272 status = (
char*)cvAlloc((
unsigned int)maxFeatures*
sizeof(char));
273 lostDuringTrack = (
bool*)cvAlloc((
unsigned int)maxFeatures*
sizeof(bool));
274 featuresid = (
long*)cvAlloc((
unsigned int)maxFeatures*
sizeof(long));
275 prev_featuresid = (
long*)cvAlloc((
unsigned int)maxFeatures*
sizeof(long));
294 if (I->depth != IPL_DEPTH_8U || I->nChannels != 1) {
299 if (mask->depth != IPL_DEPTH_8U || I->nChannels != 1) {
305 CvSize Sizeim, SizeI;
306 SizeI = cvGetSize(I);
309 Sizeim = cvGetSize(image);
310 if(SizeI.width != Sizeim.width || SizeI.height != Sizeim.height) b_imOK =
false;
312 if(image == NULL || prev_image == NULL || pyramid==NULL || prev_pyramid ==NULL || !b_imOK){
314 image = cvCreateImage(cvGetSize(I), 8, 1);image->origin = I->origin;
315 prev_image = cvCreateImage(cvGetSize(I), IPL_DEPTH_8U, 1);
316 pyramid = cvCreateImage(cvGetSize(I), IPL_DEPTH_8U, 1);
317 prev_pyramid = cvCreateImage(cvGetSize(I), IPL_DEPTH_8U, 1);
321 countPrevFeatures = 0;
324 globalcountFeatures = 0;
333 countFeatures = maxFeatures;
334 countPrevFeatures = 0;
335 IplImage* eig = cvCreateImage(cvGetSize(image), 32, 1);
336 IplImage* temp = cvCreateImage(cvGetSize(image), 32, 1);
337 cvGoodFeaturesToTrack(image, eig, temp, features,
338 &countFeatures, quality, min_distance,
339 mask, block_size, use_harris, harris_free_parameter);
340 cvFindCornerSubPix(image, features, countFeatures, cvSize(win_size, win_size),
341 cvSize(-1,-1),cvTermCriteria(CV_TERMCRIT_ITER|
342 CV_TERMCRIT_EPS,20,0.03));
343 cvReleaseImage(&eig);
344 cvReleaseImage(&temp);
350 for (
int boucle=0; boucle<countFeatures;boucle++) {
351 featuresid[boucle] = globalcountFeatures;
352 globalcountFeatures++;
355 OnNewFeature(_tid, boucle, featuresid[boucle], features[boucle].x,
367 "KLT Not initialized")) ;
372 "Image Not initialized")) ;
375 if (I->depth != IPL_DEPTH_8U || I->nChannels != 1) {
377 "Bad Image format")) ;
382 CV_SWAP(prev_image, image, swap_temp);
383 CV_SWAP(prev_pyramid, pyramid, swap_temp);
389 countPrevFeatures = countFeatures;
390 for (
int boucle=0; boucle<countFeatures;boucle++) {
391 prev_featuresid[boucle] = featuresid[boucle];
394 CvPoint2D32f *swap_features = 0;
395 CV_SWAP(prev_features, features, swap_features);
398 if (countFeatures <= 0)
return;
400 cvCalcOpticalFlowPyrLK( prev_image, image, prev_pyramid, pyramid,
401 prev_features, features, countFeatures,
402 cvSize(win_size, win_size), pyramid_level,
403 status, 0, cvTermCriteria(CV_TERMCRIT_ITER
404 |CV_TERMCRIT_EPS,20,0.03),
408 flags |= CV_LKFLOW_PYR_A_READY;
410 flags = CV_LKFLOW_PYR_A_READY;
411 initial_guess =
false;
415 for (i = k = 0; i < countFeatures ; i++) {
417 lostDuringTrack[i] = 1;
419 OnFeatureLost(_tid, i, featuresid[i], features[i].x,
424 if (IsFeatureValid) {
425 if (!IsFeatureValid(_tid, features[i].x, features[i].y)) {
426 lostDuringTrack[i] = 1;
428 OnFeatureLost(_tid, i, featuresid[i], features[i].x, features[i].y);
432 features[k] = features[i];
433 featuresid[k] = featuresid[i];
435 if (OnMeasureFeature) OnMeasureFeature(_tid, k, featuresid[k], features[k].x, features[k].y);
437 lostDuringTrack[i] = 0;
451 vpColor color,
unsigned int thickness)
453 if ((features == 0) || (I.
bitmap==0) || (!initialized))
477 if (index >= countFeatures)
483 x = features[index].x;
484 y = features[index].y;
485 id = featuresid[index];
500 countPrevFeatures = countFeatures;
501 for (
int boucle=0; boucle<countFeatures;boucle++) {
502 prev_featuresid[boucle] = featuresid[boucle];
505 CvPoint2D32f *swap_features = NULL;
506 CV_SWAP(prev_features, *guess_pts, swap_features);
508 CV_SWAP(features, prev_features, swap_features);
510 flags |= CV_LKFLOW_INITIAL_GUESSES;
512 initial_guess =
true;
525 if (index >= countPrevFeatures)
531 x = prev_features[index].x;
532 y = prev_features[index].y;
533 id = prev_featuresid[index];
543 const float &x,
const float &y)
545 if (maxFeatures == countFeatures)
554 features[countFeatures] = f;
555 featuresid[countFeatures] = id;
561 if (index >= countFeatures)
569 for (
int i=index ; i < countFeatures; i ++) {
570 features[i] = features[i+1];
571 featuresid[i] = featuresid[i+1];
590 const int &nbFeatures,
vpColor color,
unsigned int thickness)
593 for (
int i = 0 ; i < nbFeatures ; i++)
615 const int &nbFeatures,
vpColor color,
unsigned int thickness)
618 for (
int i = 0 ; i < nbFeatures ; i++)
643 const long *featuresid_list,
const int &nbFeatures,
644 vpColor color,
unsigned int thickness)
647 for (
int i = 0 ; i < nbFeatures ; i++)
654 sprintf(
id,
"%ld", featuresid_list[i]);
677 const long *featuresid_list,
const int &nbFeatures,
678 vpColor color,
unsigned int thickness)
681 for (
int i = 0 ; i < nbFeatures ; i++)
688 sprintf(
id,
"%ld", featuresid_list[i]);
void track(const IplImage *I)
Type * bitmap
points toward the bitmap
vpKltOpencv & operator=(const vpKltOpencv ©)
Class to define colors available for display functionnalities.
void addFeature(const int &id, const float &x, const float &y)
void display(const vpImage< unsigned char > &I, vpColor color=vpColor::red, unsigned int thickness=1)
error that can be emited by ViSP classes.
void setInitialGuess(CvPoint2D32f **guess_pts)
static int round(const double x)
void getFeature(int index, int &id, float &x, float &y) const
void set_u(const double u)
virtual void displayCross(const vpImagePoint &ip, unsigned int size, const vpColor &color, unsigned int thickness=1)=0
void set_v(const double v)
void getPrevFeature(int index, int &id, float &x, float &y) const
void initTracking(const IplImage *I, const IplImage *mask=NULL)
virtual void displayCharString(const vpImagePoint &ip, const char *text, const vpColor &color=vpColor::green)=0
Wrapper for the KLT (Kanade-Lucas-Tomasi) feature tracker implemented in OpenCV.
void suppressFeature(int index)
Class that defines a 2D point in an image. This class is useful for image processing and stores only ...
void setMaxFeatures(const int input)