はじめに
先日OpenCV3.1をopencv_contrib付きでインストールしてTracking APIを試したので簡単に結果だけ記しておきます。
トラッキングオブジェクト
トラッキングオブジェクトは「opencv2/tracking.hpp」の「cv::Tracker」のスタティックで定義されているcreateメソッドで生成します。
cv::Ptr<cv::Tracker> tracker = cv::Tracker::create("KCF");
トラッキング手法をcreateメソッドの引数から文字列で指定することができます。指定できるのは「MIL」,「BOOSTING」,「MEDIANFLOW」,「TLD」,「KCF」の5つのようです。今回はサンプルで指定されている「KCF」を使ってみました。
追跡結果サンプル
指定の動画を読み込んで1フレーム目で追跡対象物体を矩形を選択したらトラッキングを開始するようなものを作りました。トラッキングの結果は別途動画で保存させいます。下記がその一例です。
1フレーム目でてんとうむしに青い矩形を手動で指定して追跡させました。この動画自体は元の動画に青い矩形を追加して表示しています。
今回は対象の動画が単純ということもありますが、物体(てんとうむし)の移動や回転だけでなく、カメラの手ぶれにも対応できているようです。
ソースコード
#include <opencv2/core/utility.hpp> #include <opencv2/tracking.hpp> #include <opencv2/videoio.hpp> #include <opencv2/highgui.hpp> #include <iostream> #include <cstring> #ifdef _DEBUG #pragma comment(lib, "opencv_core310d.lib") #pragma comment(lib, "opencv_videoio310d.lib") #pragma comment(lib, "opencv_highgui310d.lib") #pragma comment(lib, "opencv_tracking310d.lib") #pragma comment(lib, "opencv_imgproc310d.lib") #else #pragma comment(lib, "opencv_core310.lib") #pragma comment(lib, "opencv_videoio310.lib") #pragma comment(lib, "opencv_highgui310.lib") #pragma comment(lib, "opencv_tracking310.lib") #pragma comment(lib, "opencv_imgproc310.lib") #endif //動画ファイル #define VIDEO_NAME "sample.avi" #define OUTPUT_VIDEO_NAME "output.avi" int main(int argc, char** argv){ //変数定義 cv::Rect2d roi; cv::Mat frame; //トラッキングオブジェクト生成 cv::Ptr<cv::Tracker> tracker = cv::Tracker::create("KCF"); //動画読み込み cv::VideoCapture cap(VIDEO_NAME); cap >> frame; //初期物体の矩形指定 roi = selectROI("tracker", frame); if (roi.width == 0 || roi.height == 0){ return 0; } //トラッカーの初期化 tracker->init(frame, roi); //動画の保存 std::string filename = OUTPUT_VIDEO_NAME; int fourcc = cv::VideoWriter::fourcc('X', 'V', 'I', 'D'); double fps = 30.0; cv::VideoWriter writer(filename, fourcc, fps, frame.size()); //トラッキング開始 printf("Start the tracking process, press ESC to quit.\n"); for (;;){ //動画からフレームの切り出し cap >> frame; //フレームが切り出せなくなったら終了 if (frame.rows == 0 || frame.cols == 0){ break; } //更新 tracker->update(frame, roi); //矩形の描画 rectangle(frame, roi, cv::Scalar(255, 0, 0), 2, 1); //動画保存 writer << frame; //結果のGUI表示 imshow("tracker", frame); //ESCを押したら終了 if (cv::waitKey(1) == 27){ break; } } return 0; }