Commit 3ac9e242 authored by Vladislav Sovrasov's avatar Vladislav Sovrasov

tracking: improve public API

Use ROI selector in python samples
parent 4317e27d
......@@ -155,7 +155,7 @@ PERF_TEST_P(tracking, mil, testing::Combine(TESTSET_NAMES, SEGMENTS))
bool initialized = false;
vector<Rect> bbs;
Ptr<Tracker> tracker = Tracker::create( "MIL" );
Ptr<Tracker> tracker = TrackerMIL::create();
string folder = TRACKING_DIR + "/" + video + "/" + FOLDER_IMG;
int numSegments = ( sizeof ( SEGMENTS)/sizeof(int) );
int endFrame = 0;
......@@ -226,7 +226,7 @@ PERF_TEST_P(tracking, boosting, testing::Combine(TESTSET_NAMES, SEGMENTS))
bool initialized = false;
vector<Rect> bbs;
Ptr<Tracker> tracker = Tracker::create( "BOOSTING" );
Ptr<Tracker> tracker = TrackerBoosting::create();
string folder = TRACKING_DIR + "/" + video + "/" + FOLDER_IMG;
int numSegments = ( sizeof ( SEGMENTS)/sizeof(int) );
int endFrame = 0;
......@@ -296,7 +296,7 @@ PERF_TEST_P(tracking, tld, testing::Combine(TESTSET_NAMES, SEGMENTS))
bool initialized = false;
vector<Rect> bbs;
Ptr<Tracker> tracker = Tracker::create( "TLD" );
Ptr<Tracker> tracker = TrackerTLD::create();
string folder = TRACKING_DIR + "/" + video + "/" + FOLDER_IMG;
int numSegments = ( sizeof ( SEGMENTS)/sizeof(int) );
int endFrame = 0;
......@@ -366,7 +366,7 @@ PERF_TEST_P(tracking, GOTURN, testing::Combine(TESTSET_NAMES, SEGMENTS))
bool initialized = false;
vector<Rect> bbs;
Ptr<Tracker> tracker = Tracker::create("GOTURN");
Ptr<Tracker> tracker = TrackerGOTURN::create();
string folder = TRACKING_DIR + "/" + video + "/" + FOLDER_IMG;
int numSegments = (sizeof(SEGMENTS) / sizeof(int));
int endFrame = 0;
......
......@@ -3,6 +3,7 @@
#include "opencv2/tracking.hpp"
#include "opencv2/videoio.hpp"
#include "opencv2/plot.hpp"
#include "samples_utility.hpp"
#include <fstream>
#include <iomanip>
#include <iostream>
......@@ -75,10 +76,11 @@ const int LTRC_COUNT = 100;
struct AlgoWrap
{
AlgoWrap(const string &name_)
: tracker(Tracker::create(name_)), lastState(NotFound), name(name_), color(getNextColor()),
: lastState(NotFound), name(name_), color(getNextColor()),
numTotal(0), numResponse(0), numPresent(0), numCorrect_0(0), numCorrect_0_5(0),
timeTotal(0), auc(LTRC_COUNT + 1, 0)
{
tracker = createTrackerByName(name);
}
enum State
......
......@@ -140,7 +140,7 @@ int main(int argc, char *argv[])
setMouseCallback("GOTURN Tracking", onMouse, 0);
//Create GOTURN tracker
Ptr<Tracker> tracker = Tracker::create("GOTURN");
Ptr<Tracker> tracker = TrackerGOTURN::create();
//Load and init full ALOV300++ dataset with a given datasetID, as alternative you can use loadAnnotatedOnly(..)
//to load only frames with labled ground truth ~ every 5-th frame
......
......@@ -52,7 +52,7 @@ int main( int argc, char** argv ){
BoxExtractor box;
// create the tracker
Ptr<Tracker> tracker = Tracker::create( "KCF" );
Ptr<Tracker> tracker = TrackerKCF::create();
// set input video
std::string video = argv[1];
......
......@@ -48,6 +48,7 @@
#include <opencv2/tracking.hpp>
#include <opencv2/videoio.hpp>
#include <opencv2/highgui.hpp>
#include "samples_utility.hpp"
#include <iostream>
using namespace std;
......@@ -184,7 +185,7 @@ int main(int argc, char *argv[])
//Initialize the tracker and add targets
for (int i = 0; i < (int)boundingBoxes.size(); i++)
{
if (!mt.addTarget(frame, boundingBoxes[i], tracker_algorithm))
if (!mt.addTarget(frame, boundingBoxes[i], createTrackerByName(tracker_algorithm)))
{
cout << "Trackers Init Error!!!";
return 0;
......
......@@ -24,7 +24,7 @@
#include <iostream>
#include <cstring>
#include <ctime>
#include "roiSelector.hpp"
#include "samples_utility.hpp"
#ifdef HAVE_OPENCV
#include <opencv2/flann.hpp>
......@@ -62,38 +62,46 @@ int main( int argc, char** argv ){
// for showing the speed
double fps;
std::string text;
String text;
char buffer [50];
// set the default tracking algorithm
std::string trackingAlg = "KCF";
String trackingAlg = "KCF";
// set the tracking algorithm from parameter
if(argc>2)
trackingAlg = argv[2];
// create the tracker
MultiTracker trackers(trackingAlg);
MultiTracker trackers;
// container of the tracked objects
vector<Rect> ROIs;
vector<Rect2d> objects;
// set input video
std::string video = argv[1];
String video = argv[1];
VideoCapture cap(video);
Mat frame;
// get bounding box
cap >> frame;
selectROI("tracker",frame,objects);
selectROIs("tracker",frame,ROIs);
//quit when the tracked object(s) is not provided
if(objects.size()<1)
return 0;
std::vector<Ptr<Tracker> > algorithms;
for (size_t i = 0; i < ROIs.size(); i++)
{
algorithms.push_back(createTrackerByName(trackingAlg));
objects.push_back(ROIs[i]);
}
// initialize the tracker
trackers.add(frame,objects);
trackers.add(algorithms,frame,objects);
// do the tracking
printf(GREEN "Start the tracking process, press ESC to quit.\n" RESET);
......@@ -128,8 +136,8 @@ int main( int argc, char** argv ){
#endif
// draw the tracked object
for(unsigned i=0;i<trackers.objects.size();i++)
rectangle( frame, trackers.objects[i], Scalar( 255, 0, 0 ), 2, 1 );
for(unsigned i=0;i<trackers.getObjects().size();i++)
rectangle( frame, trackers.getObjects()[i], Scalar( 255, 0, 0 ), 2, 1 );
// draw the processing speed
sprintf (buffer, "speed: %.0f fps", fps);
......
import numpy as np
import cv2
import sys
if len(sys.argv) != 2:
print('Input video name is missing')
exit()
print('Select 3 tracking targets')
cv2.namedWindow("tracking")
camera = cv2.VideoCapture("E:/code/opencv/samples/data/768x576.avi")
tracker = cv2.MultiTracker("MIL")
bbox1 = (638.0,230.0,56.0,101.0)
bbox2 = (240.0,210.0,60.0,104.0)
bbox3 = (486.0,149.0,54.0,83.0)
camera = cv2.VideoCapture(sys.argv[1])
tracker = cv2.MultiTracker_create()
init_once = False
ok, image=camera.read()
if not ok:
print('Failed to read video')
exit()
bbox1 = cv2.selectROI('tracking', image)
bbox2 = cv2.selectROI('tracking', image)
bbox3 = cv2.selectROI('tracking', image)
while camera.isOpened():
ok, image=camera.read()
if not ok:
print 'no image read'
print 'no image to read'
break
if not init_once:
# add a list of boxes:
ok = tracker.add(image, (bbox1,bbox2))
# or add single box:
ok = tracker.add(image, bbox3)
ok = tracker.add(cv2.TrackerMIL_create(), image, bbox1)
ok = tracker.add(cv2.TrackerMIL_create(), image, bbox2)
ok = tracker.add(cv2.TrackerMIL_create(), image, bbox3)
init_once = True
ok, boxes = tracker.update(image)
......@@ -30,6 +42,6 @@ while camera.isOpened():
p2 = (int(newbox[0] + newbox[2]), int(newbox[1] + newbox[3]))
cv2.rectangle(image, p1, p2, (200,0,0))
cv2.imshow("tracking", image)
k = cv2.waitKey(1) & 0xff
cv2.imshow('tracking', image)
k = cv2.waitKey(1)
if k == 27 : break # esc pressed
#ifndef _ROISELECTOR_HPP_
#define _ROISELECTOR_HPP_
#include "opencv2/core.hpp"
#include "opencv2/highgui.hpp"
#include "opencv2/imgproc.hpp"
cv::Rect2d selectROI(cv::Mat img, bool fromCenter = true);
cv::Rect2d selectROI(const cv::String& windowName, cv::Mat img, bool showCrossair = true, bool fromCenter = true);
void selectROI(const cv::String& windowName, cv::Mat img, std::vector<cv::Rect2d> & boundingBox, bool fromCenter = true);
//==================================================================================================
class ROISelector
{
public:
cv::Rect2d select(cv::Mat img, bool fromCenter = true)
{
return select("ROI selector", img, fromCenter);
}
cv::Rect2d select(const cv::String &windowName, cv::Mat img, bool showCrossair = true, bool fromCenter = true)
{
key = 0;
// set the drawing mode
selectorParams.drawFromCenter = fromCenter;
// show the image and give feedback to user
cv::imshow(windowName, img);
// copy the data, rectangle should be drawn in the fresh image
selectorParams.image = img.clone();
// select the object
cv::setMouseCallback(windowName, mouseHandler, (void *)&selectorParams);
// end selection process on SPACE (32) ESC (27) or ENTER (13)
while (!(key == 32 || key == 27 || key == 13))
{
// draw the selected object
cv::rectangle(selectorParams.image, selectorParams.box, cv::Scalar(255, 0, 0), 2, 1);
// draw cross air in the middle of bounding box
if (showCrossair)
{
// horizontal line
cv::line(selectorParams.image,
cv::Point((int)selectorParams.box.x,
(int)(selectorParams.box.y + selectorParams.box.height / 2)),
cv::Point((int)(selectorParams.box.x + selectorParams.box.width),
(int)(selectorParams.box.y + selectorParams.box.height / 2)),
cv::Scalar(255, 0, 0), 2, 1);
// vertical line
cv::line(selectorParams.image,
cv::Point((int)(selectorParams.box.x + selectorParams.box.width / 2),
(int)selectorParams.box.y),
cv::Point((int)(selectorParams.box.x + selectorParams.box.width / 2),
(int)(selectorParams.box.y + selectorParams.box.height)),
cv::Scalar(255, 0, 0), 2, 1);
}
// show the image bouding box
cv::imshow(windowName, selectorParams.image);
// reset the image
selectorParams.image = img.clone();
// get keyboard event, extract lower 8 bits for scancode comparison
key = cv::waitKey(1) & 0xFF;
}
return selectorParams.box;
}
void select(const cv::String &windowName, cv::Mat img, std::vector<cv::Rect2d> &boundingBox, bool fromCenter = true)
{
std::vector<cv::Rect2d> box;
cv::Rect2d temp;
key = 0;
// show notice to user
printf("Select an object to track and then press SPACE or ENTER button!\n");
printf("Finish the selection process by pressing ESC button!\n");
// while key is not ESC (27)
for (;;)
{
temp = select(windowName, img, true, fromCenter);
if (key == 27)
break;
if (temp.width > 0 && temp.height > 0)
box.push_back(temp);
}
boundingBox = box;
}
struct handlerT
{
// basic parameters
bool isDrawing;
cv::Rect2d box;
cv::Mat image;
// parameters for drawing from the center
bool drawFromCenter;
cv::Point2f center;
// initializer list
handlerT() : isDrawing(false), drawFromCenter(true){};
} selectorParams;
// to store the tracked objects
std::vector<handlerT> objects;
private:
static void mouseHandler(int event, int x, int y, int flags, void *param)
{
ROISelector *self = static_cast<ROISelector *>(param);
self->opencv_mouse_callback(event, x, y, flags, param);
}
void opencv_mouse_callback(int event, int x, int y, int, void *param)
{
handlerT *data = (handlerT *)param;
switch (event)
{
// update the selected bounding box
case cv::EVENT_MOUSEMOVE:
if (data->isDrawing)
{
if (data->drawFromCenter)
{
data->box.width = 2 * (x - data->center.x) /*data->box.x*/;
data->box.height = 2 * (y - data->center.y) /*data->box.y*/;
data->box.x = data->center.x - data->box.width / 2.0;
data->box.y = data->center.y - data->box.height / 2.0;
}
else
{
data->box.width = x - data->box.x;
data->box.height = y - data->box.y;
}
}
break;
// start to select the bounding box
case cv::EVENT_LBUTTONDOWN:
data->isDrawing = true;
data->box = cv::Rect2d(x, y, 0, 0);
data->center = cv::Point2f((float)x, (float)y);
break;
// cleaning up the selected bounding box
case cv::EVENT_LBUTTONUP:
data->isDrawing = false;
if (data->box.width < 0)
{
data->box.x += data->box.width;
data->box.width *= -1;
}
if (data->box.height < 0)
{
data->box.y += data->box.height;
data->box.height *= -1;
}
break;
}
}
// save the keypressed characted
int key;
};
//==================================================================================================
static ROISelector _selector;
cv::Rect2d selectROI(cv::Mat img, bool fromCenter)
{
return _selector.select("ROI selector", img, true, fromCenter);
};
cv::Rect2d selectROI(const cv::String &windowName, cv::Mat img, bool showCrossair, bool fromCenter)
{
printf("Select an object to track and then press SPACE or ENTER button!\n");
return _selector.select(windowName, img, showCrossair, fromCenter);
};
void selectROI(const cv::String &windowName, cv::Mat img, std::vector<cv::Rect2d> &boundingBox, bool fromCenter)
{
return _selector.select(windowName, img, boundingBox, fromCenter);
}
#endif // _ROISELECTOR_HPP_
#ifndef _SAMPLES_UTILITY_HPP_
#define _SAMPLES_UTILITY_HPP_
#include <opencv2/tracking.hpp>
inline cv::Ptr<cv::Tracker> createTrackerByName(cv::String name)
{
cv::Ptr<cv::Tracker> tracker;
if (name == "KCF")
tracker = cv::TrackerKCF::create();
else if (name == "TLD")
tracker = cv::TrackerTLD::create();
else if (name == "BOOSTING")
tracker = cv::TrackerBoosting::create();
else if (name == "MEDIAN_FLOW")
tracker = cv::TrackerMedianFlow::create();
else if (name == "MIL")
tracker = cv::TrackerMIL::create();
else if (name == "GOTURN")
tracker = cv::TrackerGOTURN::create();
else
CV_Error(cv::Error::StsBadArg, "Invalid tracking algorithm name\n");
return tracker;
}
#endif
......@@ -4,56 +4,17 @@
#include <opencv2/highgui.hpp>
#include <iostream>
#include <cstring>
#include "samples_utility.hpp"
using namespace std;
using namespace cv;
static Mat image;
static Rect2d boundingBox;
static bool paused;
static bool selectObject = false;
static bool startSelection = false;
static const char* keys =
{ "{@tracker_algorithm | | Tracker algorithm }"
"{@video_name | | video name }"
"{@start_frame |0| Start frame }"
"{@start_frame |0| Start frame }"
"{@bounding_frame |0,0,0,0| Initial bounding frame}"};
static void onMouse( int event, int x, int y, int, void* )
{
if( !selectObject )
{
switch ( event )
{
case EVENT_LBUTTONDOWN:
//set origin of the bounding box
startSelection = true;
boundingBox.x = x;
boundingBox.y = y;
break;
case EVENT_LBUTTONUP:
//sei with and height of the bounding box
boundingBox.width = std::abs( x - boundingBox.x );
boundingBox.height = std::abs( y - boundingBox.y );
paused = false;
selectObject = true;
break;
case EVENT_MOUSEMOVE:
if( startSelection && !selectObject )
{
//draw the bounding box
Mat currentFrame;
image.copyTo( currentFrame );
rectangle( currentFrame, Point((int) boundingBox.x, (int)boundingBox.y ), Point( x, y ), Scalar( 255, 0, 0 ), 2, 1 );
imshow( "Tracking API", currentFrame );
}
break;
}
}
}
static void help()
{
cout << "\nThis example shows the functionality of \"Long-term optical tracking API\""
......@@ -124,12 +85,14 @@ int main( int argc, char** argv ){
}
Mat frame;
paused = true;
namedWindow( "Tracking API", 1 );
setMouseCallback( "Tracking API", onMouse, 0 );
Mat image;
Rect2d boundingBox;
bool paused = false;
//instantiates the specific Tracker
Ptr<Tracker> tracker = Tracker::create( tracker_algorithm );
Ptr<Tracker> tracker = createTrackerByName(tracker_algorithm);
if( tracker == NULL )
{
cout << "***Error in the instantiation of the tracker...***\n";
......@@ -140,8 +103,6 @@ int main( int argc, char** argv ){
cap >> frame;
frame.copyTo( image );
if(initBoxWasGivenInCommandLine){
selectObject=true;
paused=false;
boundingBox.x = coords[0];
boundingBox.y = coords[1];
boundingBox.width = std::abs( coords[2] - coords[0] );
......@@ -149,6 +110,9 @@ int main( int argc, char** argv ){
printf("bounding box with vertices (%d,%d) and (%d,%d) was given in command line\n",coords[0],coords[1],coords[2],coords[3]);
rectangle( image, boundingBox, Scalar( 255, 0, 0 ), 2, 1 );
}
else
boundingBox = selectROI("Tracking API", image);
imshow( "Tracking API", image );
bool initialized = false;
......@@ -166,7 +130,7 @@ int main( int argc, char** argv ){
frame.copyTo( image );
}
if( !initialized && selectObject )
if( !initialized )
{
//initializes the tracker
if( !tracker->init( frame, boundingBox ) )
......@@ -193,7 +157,6 @@ int main( int argc, char** argv ){
break;
if( c == 'p' )
paused = !paused;
}
return 0;
......
import numpy as np
import cv2
import sys
if len(sys.argv) != 2:
print('Input video name is missing')
exit()
cv2.namedWindow("tracking")
camera = cv2.VideoCapture("E:/code/opencv/samples/data/768x576.avi")
bbox = (638.0,230.0,56.0,101.0)
tracker = cv2.Tracker_create("MIL")
camera = cv2.VideoCapture(sys.argv[1])
ok, image=camera.read()
if not ok:
print('Failed to read video')
exit()
bbox = cv2.selectROI("tracking", image)
tracker = cv2.TrackerMIL_create()
init_once = False
while camera.isOpened():
ok, image=camera.read()
if not ok:
print 'no image read'
print 'no image to read'
break
if not init_once:
......@@ -27,4 +36,4 @@ while camera.isOpened():
cv2.imshow("tracking", image)
k = cv2.waitKey(1) & 0xff
if k == 27 : break # esc pressed
\ No newline at end of file
if k == 27 : break # esc pressed
......@@ -53,6 +53,7 @@
#include <opencv2/videoio.hpp>
#include <opencv2/highgui.hpp>
#include <opencv2/imgproc.hpp>
#include "samples_utility.hpp"
#include <iostream>
......@@ -143,7 +144,7 @@ int main(int argc, char *argv[])
setMouseCallback("Tracking API", onMouse, 0);
//Create Tracker
Ptr<Tracker> tracker = Tracker::create(tracker_algorithm);
Ptr<Tracker> tracker = createTrackerByName(tracker_algorithm);
if (tracker == NULL)
{
cout << "***Error in the instantiation of the tracker...***\n";
......
......@@ -4,7 +4,7 @@
#include <opencv2/highgui.hpp>
#include <iostream>
#include <cstring>
#include "roiSelector.hpp"
#include "samples_utility.hpp"
using namespace std;
using namespace cv;
......@@ -38,7 +38,7 @@ int main( int argc, char** argv ){
// create a tracker object
//! [create]
Ptr<TrackerKCF> tracker = TrackerKCF::createTracker(param);
Ptr<TrackerKCF> tracker = TrackerKCF::create(param);
//! [create]
//! [setextractor]
......
......@@ -4,7 +4,6 @@
#include <opencv2/highgui.hpp>
#include <iostream>
#include <cstring>
#include "roiSelector.hpp"
using namespace std;
using namespace cv;
......@@ -31,7 +30,7 @@ int main( int argc, char** argv ){
// create a tracker object
//! [create]
Ptr<Tracker> tracker = Tracker::create( "KCF" );
Ptr<Tracker> tracker = TrackerKCF::create();
//! [create]
// set input video
......
......@@ -14,7 +14,7 @@
#include <iostream>
#include <cstring>
#include <ctime>
#include "roiSelector.hpp"
#include "samples_utility.hpp"
using namespace std;
using namespace cv;
......@@ -40,7 +40,7 @@ int main( int argc, char** argv ){
// create the tracker
//! [create]
MultiTracker trackers(trackingAlg);
MultiTracker trackers;
//! [create]
// container of the tracked objects
......@@ -57,7 +57,8 @@ int main( int argc, char** argv ){
// get bounding box
cap >> frame;
//! [selectmulti]
selectROI("tracker",frame,objects);
vector<Rect> ROIs;
selectROIs("tracker",frame,ROIs);
//! [selectmulti]
//quit when the tracked object(s) is not provided
......@@ -66,7 +67,14 @@ int main( int argc, char** argv ){
// initialize the tracker
//! [init]
trackers.add(frame,objects);
std::vector<Ptr<Tracker> > algorithms;
for (size_t i = 0; i < objects.size(); i++)
{
algorithms.push_back(createTrackerByName(trackingAlg));
objects.push_back(ROIs[i]);
}
trackers.add(algorithms,frame,objects);
//! [init]
// do the tracking
......@@ -86,8 +94,8 @@ int main( int argc, char** argv ){
//! [result]
// draw the tracked object
for(unsigned i=0;i<trackers.objects.size();i++)
rectangle( frame, trackers.objects[i], Scalar( 255, 0, 0 ), 2, 1 );
for(unsigned i=0;i<trackers.getObjects().size();i++)
rectangle( frame, trackers.getObjects()[i], Scalar( 255, 0, 0 ), 2, 1 );
//! [result]
// show image with the tracked object
......
......@@ -52,7 +52,7 @@ void TrackerGOTURN::Params::read(const cv::FileNode& /*fn*/){}
void TrackerGOTURN::Params::write(cv::FileStorage& /*fs*/) const {}
Ptr<TrackerGOTURN> TrackerGOTURN::createTracker(const TrackerGOTURN::Params &parameters)
Ptr<TrackerGOTURN> TrackerGOTURN::create(const TrackerGOTURN::Params &parameters)
{
#ifdef HAVE_OPENCV_DNN
return Ptr<gtr::TrackerGOTURNImpl>(new gtr::TrackerGOTURNImpl(parameters));
......@@ -61,6 +61,10 @@ Ptr<TrackerGOTURN> TrackerGOTURN::createTracker(const TrackerGOTURN::Params &par
CV_ErrorNoReturn(cv::Error::StsNotImplemented , "to use GOTURN, the tracking module needs to be built with opencv_dnn !");
#endif
}
Ptr<TrackerGOTURN> TrackerGOTURN::create()
{
return TrackerGOTURN::create(TrackerGOTURN::Params());
}
#ifdef HAVE_OPENCV_DNN
......
......@@ -44,9 +44,9 @@
namespace cv
{
//Multitracker
bool MultiTracker_Alt::addTarget(const Mat& image, const Rect2d& boundingBox, String tracker_algorithm_name)
bool MultiTracker_Alt::addTarget(InputArray image, const Rect2d& boundingBox, Ptr<Tracker> tracker_algorithm)
{
Ptr<Tracker> tracker = Tracker::create(tracker_algorithm_name);
Ptr<Tracker> tracker = tracker_algorithm;
if (tracker == NULL)
return false;
......@@ -73,7 +73,7 @@ namespace cv
return true;
}
bool MultiTracker_Alt::update(const Mat& image)
bool MultiTracker_Alt::update(InputArray image)
{
for (int i = 0; i < (int)trackers.size(); i++)
if (!trackers[i]->update(image, boundingBoxes[i]))
......@@ -84,8 +84,9 @@ namespace cv
//Multitracker TLD
/*Optimized update method for TLD Multitracker */
bool MultiTrackerTLD::update_opt(const Mat& image)
bool MultiTrackerTLD::update_opt(InputArray _image)
{
Mat image = _image.getMat();
//Get parameters from first object
//TLD Tracker data extraction
Tracker* trackerPtr = trackers[0];
......@@ -99,7 +100,7 @@ namespace cv
cvtColor(image, image_gray, COLOR_BGR2GRAY);
if (scale > 1.0)
resize(image_gray, imageForDetector, Size(cvRound(image.cols*scale), cvRound(image.rows*scale)), 0, 0, tld::DOWNSCALE_MODE);
resize(image_gray, imageForDetector, Size(cvRound(image_gray.cols*scale), cvRound(image_gray.rows*scale)), 0, 0, tld::DOWNSCALE_MODE);
else
imageForDetector = image_gray;
GaussianBlur(imageForDetector, image_blurred, tld::GaussBlurKernelSize, 0.0);
......@@ -653,4 +654,4 @@ namespace cv
}
#endif
}
\ No newline at end of file
}
......@@ -44,29 +44,15 @@
namespace cv {
// constructor
MultiTracker::MultiTracker(const String& trackerType):defaultAlgorithm(trackerType){};
MultiTracker::MultiTracker(){};
// destructor
MultiTracker::~MultiTracker(){};
// add an object to be tracked, defaultAlgorithm is used
bool MultiTracker::add(const Mat& image, const Rect2d& boundingBox){
// quit if defaultAlgorithm has not been configured
if(defaultAlgorithm==""){
printf("Default algorithm was not defined!\n");
return false;
}
// add a new tracked object
return add(defaultAlgorithm.c_str(), image, boundingBox);
};
// add a new tracked object
bool MultiTracker::add( const String& trackerType, const Mat& image, const Rect2d& boundingBox ){
// declare a new tracker
Ptr<Tracker> newTracker = Tracker::create( trackerType );
// add the created tracker algorithm to the trackers list
bool MultiTracker::add( Ptr<Tracker> newTracker, InputArray image, const Rect2d& boundingBox )
{
// add the tracker algorithm to the trackers list
trackerList.push_back(newTracker);
// add the ROI to the bounding box list
......@@ -77,13 +63,13 @@ namespace cv {
};
// add a set of objects to be tracked
bool MultiTracker::add(const String& trackerType, const Mat& image, std::vector<Rect2d> boundingBox){
bool MultiTracker::add(std::vector<Ptr<Tracker> > newTrackers, InputArray image, std::vector<Rect2d> boundingBox){
// status of the tracker addition
bool stat=false;
// add tracker for all input objects
for(unsigned i =0;i<boundingBox.size();i++){
stat=add(trackerType,image,boundingBox[i]);
stat=add(newTrackers[i],image,boundingBox[i]);
if(!stat)break;
}
......@@ -91,30 +77,32 @@ namespace cv {
return stat;
};
// add a set of object to be tracked, defaultAlgorithm is used.
bool MultiTracker::add(const Mat& image, std::vector<Rect2d> boundingBox){
// quit if defaultAlgorithm has not been configured
if(defaultAlgorithm==""){
printf("Default algorithm was not defined!\n");
return false;
}
return add(defaultAlgorithm.c_str(), image, boundingBox);
};
// update position of the tracked objects, the result is stored in internal storage
bool MultiTracker::update( const Mat& image){
bool MultiTracker::update(InputArray image)
{
bool status = true;
for(unsigned i=0;i< trackerList.size(); i++){
trackerList[i]->update(image, objects[i]);
status &= trackerList[i]->update(image, objects[i]);
}
return true;
return status;
};
// update position of the tracked objects, the result is copied to external variable
bool MultiTracker::update( const Mat& image, std::vector<Rect2d> & boundingBox ){
update(image);
bool MultiTracker::update(InputArray image, std::vector<Rect2d> & boundingBox )
{
bool status = update(image);
boundingBox=objects;
return true;
return status;
};
} /* namespace cv */
\ No newline at end of file
const std::vector<Rect2d>& MultiTracker::getObjects() const
{
return objects;
}
Ptr<MultiTracker> MultiTracker::create()
{
return makePtr<MultiTracker>();
}
} /* namespace cv */
......@@ -52,10 +52,14 @@ namespace cv
void TrackerTLD::Params::write(cv::FileStorage& /*fs*/) const {}
Ptr<TrackerTLD> TrackerTLD::createTracker(const TrackerTLD::Params &parameters)
Ptr<TrackerTLD> TrackerTLD::create(const TrackerTLD::Params &parameters)
{
return Ptr<tld::TrackerTLDImpl>(new tld::TrackerTLDImpl(parameters));
}
Ptr<TrackerTLD> TrackerTLD::create()
{
return Ptr<tld::TrackerTLDImpl>(new tld::TrackerTLDImpl());
}
namespace tld
{
......
......@@ -98,7 +98,7 @@ public:
TrackerProxyImpl(Tparams params = Tparams()) :params_(params){}
bool init(const Mat& image, const Rect2d& boundingBox)
{
trackerPtr = T::createTracker();
trackerPtr = T::create();
return trackerPtr->init(image, boundingBox);
}
bool update(const Mat& image, Rect2d& boundingBox)
......
......@@ -41,12 +41,6 @@
#include "precomp.hpp"
#undef BOILERPLATE_CODE
#define BOILERPLATE_CODE(name,classname)\
if(trackerType==name){\
return classname::createTracker();\
}
namespace cv
{
......@@ -58,7 +52,7 @@ Tracker::~Tracker()
{
}
bool Tracker::init( const Mat& image, const Rect2d& boundingBox )
bool Tracker::init( InputArray image, const Rect2d& boundingBox )
{
if( isInit )
......@@ -73,7 +67,7 @@ bool Tracker::init( const Mat& image, const Rect2d& boundingBox )
featureSet = Ptr<TrackerFeatureSet>( new TrackerFeatureSet() );
model = Ptr<TrackerModel>();
bool initTracker = initImpl( image, boundingBox );
bool initTracker = initImpl( image.getMat(), boundingBox );
//check if the model component is initialized
if( model == 0 )
......@@ -90,7 +84,7 @@ bool Tracker::init( const Mat& image, const Rect2d& boundingBox )
return initTracker;
}
bool Tracker::update( const Mat& image, Rect2d& boundingBox )
bool Tracker::update( InputArray image, Rect2d& boundingBox )
{
if( !isInit )
......@@ -101,19 +95,7 @@ bool Tracker::update( const Mat& image, Rect2d& boundingBox )
if( image.empty() )
return false;
return updateImpl( image, boundingBox );
}
Ptr<Tracker> Tracker::create( const String& trackerType )
{
BOILERPLATE_CODE("MIL",TrackerMIL);
BOILERPLATE_CODE("BOOSTING",TrackerBoosting);
BOILERPLATE_CODE("MEDIANFLOW",TrackerMedianFlow);
BOILERPLATE_CODE("TLD",TrackerTLD);
BOILERPLATE_CODE("KCF",TrackerKCF);
BOILERPLATE_CODE("GOTURN", TrackerGOTURN);
return Ptr<Tracker>();
return updateImpl( image.getMat(), boundingBox );
}
} /* namespace cv */
......@@ -97,9 +97,12 @@ void TrackerBoosting::Params::write( cv::FileStorage& fs ) const
/*
* Constructor
*/
Ptr<TrackerBoosting> TrackerBoosting::createTracker(const TrackerBoosting::Params &parameters){
Ptr<TrackerBoosting> TrackerBoosting::create(const TrackerBoosting::Params &parameters){
return Ptr<TrackerBoostingImpl>(new TrackerBoostingImpl(parameters));
}
Ptr<TrackerBoosting> TrackerBoosting::create(){
return Ptr<TrackerBoostingImpl>(new TrackerBoostingImpl());
}
TrackerBoostingImpl::TrackerBoostingImpl( const TrackerBoostingImpl::Params &parameters ) :
params( parameters )
{
......
......@@ -160,9 +160,12 @@ namespace cv{
/*
* Constructor
*/
Ptr<TrackerKCF> TrackerKCF::createTracker(const TrackerKCF::Params &parameters){
Ptr<TrackerKCF> TrackerKCF::create(const TrackerKCF::Params &parameters){
return Ptr<TrackerKCFImpl>(new TrackerKCFImpl(parameters));
}
Ptr<TrackerKCF> TrackerKCF::create(){
return Ptr<TrackerKCFImpl>(new TrackerKCFImpl());
}
TrackerKCFImpl::TrackerKCFImpl( const TrackerKCF::Params &parameters ) :
params( parameters )
{
......@@ -894,7 +897,4 @@ namespace cv{
fs << "compressed_size" << compressed_size;
fs << "pca_learning_rate" << pca_learning_rate;
}
void TrackerKCF::setFeatureExtractor(void (*)(const Mat, const Rect, Mat&), bool ){};
} /* namespace cv */
......@@ -105,9 +105,12 @@ void TrackerMIL::Params::write( cv::FileStorage& fs ) const
/*
* Constructor
*/
Ptr<TrackerMIL> TrackerMIL::createTracker(const TrackerMIL::Params &parameters){
Ptr<TrackerMIL> TrackerMIL::create(const TrackerMIL::Params &parameters){
return Ptr<TrackerMILImpl>(new TrackerMILImpl(parameters));
}
Ptr<TrackerMIL> TrackerMIL::create(){
return Ptr<TrackerMILImpl>(new TrackerMILImpl());
}
TrackerMILImpl::TrackerMILImpl( const TrackerMIL::Params &parameters ) :
params( parameters )
{
......
......@@ -73,7 +73,7 @@ using namespace cv;
class TrackerMedianFlowImpl : public TrackerMedianFlow{
public:
TrackerMedianFlowImpl(TrackerMedianFlow::Params paramsIn) {params=paramsIn;isInit=false;}
TrackerMedianFlowImpl(TrackerMedianFlow::Params paramsIn = TrackerMedianFlow::Params()) {params=paramsIn;isInit=false;}
void read( const FileNode& fn );
void write( FileStorage& fs ) const;
private:
......@@ -482,8 +482,11 @@ void TrackerMedianFlow::Params::write( cv::FileStorage& fs ) const{
fs << "maxMedianLengthOfDisplacementDifference" << maxMedianLengthOfDisplacementDifference;
}
Ptr<TrackerMedianFlow> TrackerMedianFlow::createTracker(const TrackerMedianFlow::Params &parameters){
Ptr<TrackerMedianFlow> TrackerMedianFlow::create(const TrackerMedianFlow::Params &parameters){
return Ptr<TrackerMedianFlowImpl>(new TrackerMedianFlowImpl(parameters));
}
Ptr<TrackerMedianFlow> TrackerMedianFlow::create(){
return Ptr<TrackerMedianFlowImpl>(new TrackerMedianFlowImpl());
}
} /* namespace cv */
......@@ -439,100 +439,100 @@ PARAM_TEST_CASE(DistanceAndOverlap, string)
TEST_P(DistanceAndOverlap, MedianFlow)
{
TrackerTest test( Tracker::create( "MEDIANFLOW" ), dataset, 35, .5f, NoTransform, 1, 1);
TrackerTest test( TrackerMedianFlow::create(), dataset, 35, .5f, NoTransform, 1, 1);
test.run();
}
TEST_P(DistanceAndOverlap, MIL)
{
TrackerTest test( Tracker::create( "MIL" ), dataset, 30, .65f, NoTransform);
TrackerTest test( TrackerMIL::create(), dataset, 30, .65f, NoTransform);
test.run();
}
TEST_P(DistanceAndOverlap, Boosting)
{
TrackerTest test( Tracker::create( "BOOSTING" ), dataset, 70, .7f, NoTransform);
TrackerTest test( TrackerBoosting::create(), dataset, 70, .7f, NoTransform);
test.run();
}
TEST_P(DistanceAndOverlap, KCF)
{
TrackerTest test( Tracker::create( "KCF" ), dataset, 20, .35f, NoTransform, 5);
TrackerTest test( TrackerKCF::create(), dataset, 20, .35f, NoTransform, 5);
test.run();
}
TEST_P(DistanceAndOverlap, DISABLED_TLD)
{
TrackerTest test( Tracker::create( "TLD" ), dataset, 60, .4f, NoTransform);
TrackerTest test( TrackerTLD::create(), dataset, 60, .4f, NoTransform);
test.run();
}
/***************************************************************************************/
//Tests with shifted initial window
TEST_P(DistanceAndOverlap, Shifted_Data_MedianFlow)
{
TrackerTest test( Tracker::create( "MEDIANFLOW" ), dataset, 80, .2f, CenterShiftLeft, 1, 1);
TrackerTest test( TrackerMedianFlow::create(), dataset, 80, .2f, CenterShiftLeft, 1, 1);
test.run();
}
TEST_P(DistanceAndOverlap, Shifted_Data_MIL)
{
TrackerTest test( Tracker::create( "MIL" ), dataset, 30, .6f, CenterShiftLeft);
TrackerTest test( TrackerMIL::create(), dataset, 30, .6f, CenterShiftLeft);
test.run();
}
TEST_P(DistanceAndOverlap, Shifted_Data_Boosting)
{
TrackerTest test( Tracker::create( "BOOSTING" ), dataset, 80, .65f, CenterShiftLeft);
TrackerTest test( TrackerBoosting::create(), dataset, 80, .65f, CenterShiftLeft);
test.run();
}
TEST_P(DistanceAndOverlap, Shifted_Data_KCF)
{
TrackerTest test( Tracker::create( "KCF" ), dataset, 20, .4f, CenterShiftLeft, 5);
TrackerTest test( TrackerKCF::create(), dataset, 20, .4f, CenterShiftLeft, 5);
test.run();
}
TEST_P(DistanceAndOverlap, DISABLED_Shifted_Data_TLD)
{
TrackerTest test( Tracker::create( "TLD" ), dataset, 120, .2f, CenterShiftLeft);
TrackerTest test( TrackerTLD::create(), dataset, 120, .2f, CenterShiftLeft);
test.run();
}
/***************************************************************************************/
//Tests with scaled initial window
TEST_P(DistanceAndOverlap, Scaled_Data_MedianFlow)
{
TrackerTest test( Tracker::create( "MEDIANFLOW" ), dataset, 25, .5f, Scale_1_1, 1, 1);
TrackerTest test( TrackerMedianFlow::create(), dataset, 25, .5f, Scale_1_1, 1, 1);
test.run();
}
TEST_P(DistanceAndOverlap, Scaled_Data_MIL)
{
TrackerTest test( Tracker::create( "MIL" ), dataset, 30, .7f, Scale_1_1);
TrackerTest test( TrackerMIL::create(), dataset, 30, .7f, Scale_1_1);
test.run();
}
TEST_P(DistanceAndOverlap, Scaled_Data_Boosting)
{
TrackerTest test( Tracker::create( "BOOSTING" ), dataset, 80, .7f, Scale_1_1);
TrackerTest test( TrackerBoosting::create(), dataset, 80, .7f, Scale_1_1);
test.run();
}
TEST_P(DistanceAndOverlap, Scaled_Data_KCF)
{
TrackerTest test( Tracker::create( "KCF" ), dataset, 20, .4f, Scale_1_1, 5);
TrackerTest test( TrackerKCF::create(), dataset, 20, .4f, Scale_1_1, 5);
test.run();
}
TEST_P(DistanceAndOverlap, DISABLED_Scaled_Data_TLD)
{
TrackerTest test( Tracker::create( "TLD" ), dataset, 120, .45f, Scale_1_1);
TrackerTest test( TrackerTLD::create(), dataset, 120, .45f, Scale_1_1);
test.run();
}
TEST_P(DistanceAndOverlap, DISABLED_GOTURN)
{
TrackerTest test(Tracker::create("GOTURN"), dataset, 0, 100, NoTransform);
TrackerTest test(TrackerGOTURN::create(), dataset, 0, 100, NoTransform);
test.run();
}
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment