This little example evaluates a TrackerBase class against synthetically generated ground truth data. Synthetically generated ground truth data can be found in the TestData repository in our cvs.ExampleTrackerBase 157 157 ~/cvs/TestData/tracker_noise/image*.pgm
#include <Matcher2D/TrackerBaseSimple.hh>
#include <Base/Image/Image.hh>
#include <Base/ImageUtils/ImageDraw.hh>
#include <Base/Image/ImageIO.hh>
#include <Base/Image/ImageConvert.hh>
#include <Base/Geometry/HomgPoint2D.hh>
#include <Base/Debug/TimeMeasure.hh>
#include <Filter/GradientSobel3x3.hh>
#include <Filter/GradientGauss.hh>
#include <Filter/GradientGaussAsymmetric.hh>
#include <Filter/Binomial.hh>
#include <iostream>
#include <iomanip>
using namespace BIAS;
using namespace std;
#define StorageType float
#define DEFAULT_PARA_FILE_NAME "TrackerBase.ini"
{
BIASERR("error loading image "<<name);
return -1;
}
BIASERR("error converting image "<<name);
return -2;
}
BIASERR("error converting image to grey "<<name);
return -3;
}
}
return 0;
}
char *name)
{
unsigned uip[2], radius=1;
unsigned char color[]={255,0,0};
string file;
float cov_scale=1e5;
bool draw_cov=true;
BIASERR("error converting image to unsigned char "<<name);
BIASABORT;
}
BIASERR("error converting image to RGB "<<name);
BIASABORT;
}
}
uip[0]=(unsigned int)rint(p[0]);
uip[1]=(unsigned int)rint(p[1]);
if (draw_cov){
double center[2], a[2], b[2], eva, evb;
center[0]=p[0];
center[1]=p[1];
cout << eva<<", "<<evb<<"\n";
a[0]=na[0]*eva*cov_scale;
a[1]=na[1]*eva*cov_scale;
b[0]=nb[0]*evb*cov_scale;
b[1]=nb[1]*evb*cov_scale;
}
file=name;
file+=".tracked";
cout << "wrote "<<file<<endl;
}
int main(int argc, char*argv[])
{
KLT_TYPE error, err, residuumMAD, residuumMSD, errorsum=0.0;
int newim, oldim, iter;
int res, counter;
bool debug=false;
bool draw=true;
ggaussasymmetric(para);
int *gradienttype = AddGradientType(para);
if (argc-argind<4 || argind<1){
cerr << argv[0] << " : <x-coo> <y-coo> <image> <image> ..."<< endl;
return -5;
}
switch (*gradienttype){
grad = &gsobel3x3;
cerr <<"Sobel3x3\n";
break;
grad = &ggauss;
cerr <<"GradientGauss\n";
break;
grad = &ggaussasymmetric;
cerr <<"GradientGaussAsymmetric\n";
break;
default:
BIASERR("unknown gradient type");
grad = NULL;
break;
}
p[0][2]=p[1][2]=1.0;
p[0][0]=atof(argv[argind]);
p[0][1]=atof(argv[argind+1]);
cout << "attempt to track point "<<p[0] << endl;
if (LoadImage(argv[argind+2], im[0])!=0){
BIASERR("error loading image "<<argv[argind+2]);
return -1;
}
binomial.Filter3x3(im[0], fim[0]);
grad->Filter(fim[0], gradx[0], grady[0]);
counter=argind+2;
newim=0;
while (counter < argc-1){
counter++;
newim=(newim==0)?(1):(0);
oldim=(newim==0)?(1):(0);
if (LoadImage(argv[counter], im[newim])!=0){
BIASERR("error loading image "<<argv[counter]);
return -1;
} else {
if (debug)
cout << "\n------- newim: " << argv[counter]
<< "\n------- oldim: " << argv[counter-1] << endl;
if (debug) cerr << appdata.
stag <<
" : "<<appdata.
sdata<<endl;
sscanf(appdata.
sdata.c_str(),
"[ %lf %lf %lf ]",
&realpoint[0], &realpoint[1], &realpoint[2]);
} else {
}
if (debug) cerr <<"realpoint is at "<<realpoint<<endl;
} else {
BIASERR("cannot find HomgPoint2D in meta data");
}
}
binomial.Filter3x3(im[newim], fim[newim]);
grad->Filter(fim[newim], gradx[newim], grady[newim]);
#ifdef BIAS_DEBUG
cerr << "Tracking from "<<p[oldim]<<" --> "<<p[oldim]<<endl;
#endif
tracker->
Init(fim[oldim], fim[newim], gradx[oldim], grady[oldim],
gradx[newim], grady[newim]);
res =
tracker->
Track(p[oldim], p[oldim], p[newim], error, iter,
residuumMAD, residuumMSD, cov);
if (res<0){
if (res==-2){
cout << "point ("<<p[oldim][0]<<", "<<p[oldim][1]<<") too close to "
<<"image border, stopping"<<endl;
break;
}
BIASERR("error matching "<<res);
assert(false);
}
err=sqrt((p[newim][0]-realpoint[0])*(p[newim][0]-realpoint[0])+
(p[newim][1]-realpoint[1])*(p[newim][1]-realpoint[1]));
errorsum+=err;
if (draw)
Draw(im[newim], p[newim], cov, argv[counter]);
cout << setw(2) << counter-3 << " : (" << p[oldim][0]<<", "<<p[oldim][1]
<< ") -> ("<< p[newim][0]<<", "<<p[newim][1]<<") klt-error: "<<error
<<" real: ("<<realpoint[0]<<", "<<realpoint[1]
<<") dist-err: "<<err<<" residuumMAD: "<<residuumMAD
<<" residuumMSD: "<<residuumMSD<<endl;
}
cerr << "errorsum over "<<counter-3<<" images: "<<errorsum<<endl
<< " mean error "<<errorsum/(double)(counter-3)<<endl;
cerr <<
"KLT trackin over "<<argc-3<<
" images took "<<timer.
GetRealTime()
<<" us"
<<
"\n this is equal to "<<timer.
GetRealTime()/double(argc-3)
<<" us per image and corner" << endl;
return 0;
}