[Opencv]テンプレートマッチングアルゴリズム(単一画像テンプレートマッチングとテンプレートマッチングに基づくターゲットトラッキング)


1.テンプレートマッチングopencv関数
リンク:http://www.opencv.org.cn/opencvdoc/2.3.2/html/modules/imgproc/doc/object_detection.html?highlight=matchtemplate#cv.MatchTemplate
matchTemplate
(
InputArray 
image
, InputArray 
temp
, OutputArray 
result
, int 
method
)
Parameters:
image – Image where the search is running. It must be 8-bit or 32-bit floating-point.
templ – Searched template. It must be not greater than the source image and have the same data type.
result – Map of comparison results. It must be single-channel 32-bit floating-point. If image is  W \times H and templ is  w \times h  , then result is  (W-w+1) \times (H-h+1)  .
method – Parameter specifying the comparison method (see below).
1番目のパラメータは入力ソース画像、2番目のパラメータは入力テンプレート画像、3番目のパラメータはマッチング結果であり、ソース画像にスライドウィンドウとテンプレートの類似度が記録され、4番目のパラメータはマッチング方法である.
照合方法:
CV_TM_SQDIEF二乗差マッチング法は、0が好ましく、値が大きいほどマッチングが悪くなる
CV_TM_SQDIEF_NORMED正規化二乗差整合法
CV_TM_CCORR相関整合法は、乗算操作を採用し、数値が大きいほど整合が良いことを示している.
CV_TM_CCORR_NORMED正規化相関整合法
CV_TM_CCOEFF相関係数マッチング法は,最適マッチングは1,最悪は−1である
CV_TM_CCOEFF_NORMED正規化相関係数マッチング法
各マッチング方法の原理は以上のリンクを参照してください.
リンク:http://www.opencv.org.cn/opencvdoc/2.3.2/html/modules/core/doc/operations_on_arrays.html?highlight=minmaxloc#cv.MinMaxLoc
minMaxLoc
(
InputArray 
src
, double* 
minVal
, double* 
maxVal
=0, Point* 
minLoc
=0, Point* 
maxLoc
=0, InputArray
mask
=noArray()
)
Parameters:
src – Source single-channel array.
minVal – Pointer to the returned minimum value. NULL is used if not required.
maxVal – Pointer to the returned maximum value. NULL is used if not required.
minLoc – Pointer to the returned minimum location (in 2D case). NULL is used if not required.
maxLoc – Pointer to the returned maximum location (in 2D case). NULL is used if not required.
mask – Optional mask used to select a sub-array.
行列の最大最小値と対応する座標を探します.
2.単一画像テンプレートマッチング
原図:
[opencv]模板匹配算法(单图像模板匹配和基于模板匹配的目标跟踪)_第1张图片
テンプレート画像:
[opencv]模板匹配算法(单图像模板匹配和基于模板匹配的目标跟踪)_第2张图片
コードは次のとおりです.
#include "stdafx.h"
#include "cv.h"
#include "highgui.h"
#include "cxcore.h"

using namespace std;
using namespace cv;

int _tmain(int argc, _TCHAR* argv[])
{
	Mat img,templ,result;
	img = imread("1.jpg");
	templ = imread("2.jpg");

	int result_cols = img.cols - templ.cols + 1;
	int result_rows = img.rows - templ.rows + 1;
	result.create(result_cols, result_rows, CV_32FC1);

	matchTemplate(img, templ, result, CV_TM_SQDIFF_NORMED);//CV_TM_SQDIFF_NORMED CV_TM_SQDIFF
	normalize(result, result, 0, 1, NORM_MINMAX, -1, Mat());

	double minVal;
	double maxVal;
	Point minLoc;
	Point maxLoc;
	Point matchLoc;

	minMaxLoc(result, &minVal, &maxVal, &minLoc, &maxLoc, Mat());

	matchLoc = minLoc;

	rectangle(img, matchLoc, Point(matchLoc.x + templ.cols, matchLoc.y + templ.rows), Scalar(0,255,0), 2, 8, 0);

	imshow("img", img);
	waitKey(0);

	return 0;
}

効果は次のとおりです.
[opencv]模板匹配算法(单图像模板匹配和基于模板匹配的目标跟踪)_第3张图片
3.テンプレートマッチングに基づく目標追跡
マウスで矩形枠を描く方式でテンプレート画像の抽出を行うため、マウス応答関数について説明する.
cvSetMouseCallback
(
const char* 
name
, CvMouseCallback 
onMouse
, void* 
param
=NULL 
)
Parameters:
name – Window name
onMouse – Mouse callback. See OpenCV samples, such ashttps://code.ros.org/svn/opencv/trunk/opencv/samples/cpp/ffilldemo.cpp, on how to specify and use the callback.
param – The optional parameter passed to the callback.
1番目のパラメータはウィンドウ名を使用し、2番目はonMouseマウスメッセージ処理関数、3番目はマウスメッセージに送信される任意のパラメータです.
ここでonMouse関数を追加すると、次のようになります.
void onMouse(int event,int x,int y,int flags,void*param)//      ,  ,  ,Mouse       
{
	if (pause)
	{
		switch (event)
		{
		case CV_EVENT_MOUSEMOVE:
			if (drawbox){
				box.width = x - box.x;
				box.height = y - box.y;
			}
			break;
		case CV_EVENT_LBUTTONDOWN:
			drawbox = true;
			box = Rect(x, y, 0, 0);
			break;
		case CV_EVENT_LBUTTONUP:
			drawbox = false;
			if (box.width < 0){
				box.x += box.width;
				box.width *= -1;
			}
			if (box.height < 0){
				box.y += box.height;
				box.height *= -1;
			}

			cvtColor(img,imggray,CV_RGB2GRAY);
			templ = imggray(box);
			tracking = true;	
			rectangle(frame, box, Scalar(0, 255, 0), 3);
			imshow("ORI", frame);	
			imshow("Templ", templ);

			break;
		}
	}
}

Event:  #define CV_EVENT_MOUSEMOVE 0                    スライド 
#define CV_EVENT_LBUTTONDOWN 1              左クリック 
#define CV_EVENT_RBUTTONDOWN 2             右クリック
 #define CV_EVENT_MBUTTONDOWN 3            中ボタンクリック 
#define CV_EVENT_LBUTTONUP 4                     左ボタンを離す 
#define CV_EVENT_RBUTTONUP 5                    右クリック 
#define CV_EVENT_MBUTTONUP 6                    中ボタン開放 
#define CV_EVENT_LBUTTONDBLCLK 7           左クリックダブルクリック
 #define CV_EVENT_RBUTTONDBLCLK 8         右クリック
 #define CV_EVENT_MBUTTONDBLCLK 9         中ボタンダブルクリック
flags: 
#define CV_EVENT_FLAG_LBUTTON 1             左ドラッグ
 #define CV_EVENT_FLAG_RBUTTON 2           右ドラッグ
 #define CV_EVENT_FLAG_MBUTTON 4           中キードラッグ 
#define CV_EVENT_FLAG_CTRLKEY 8            (8~15)Ctrlを押してイベントを置かない
 #define CV_EVENT_FLAG_SHIFTKEY 16        (16~31)Shiftを押してイベントを放さない
 #define CV_EVENT_FLAG_ALTKEY 32            (32~39)Altを押してイベントを置かない
テンプレートマッチングトレース関数は次のとおりです.
void track(Mat gray, Mat &templ, Rect &box)
{
	double minVal;
	double maxVal;
	Point minLoc;
	Point maxLoc;
	matchTemplate(gray, templ, result, CV_TM_SQDIFF);
	minMaxLoc(result, &minVal, &maxVal, &minLoc, &maxLoc, Mat());
	matchLoc = minLoc;
	rectangle(gray, matchLoc, Point(matchLoc.x + templ.cols, matchLoc.y + templ.rows), Scalar(0,0,255), 2, 8, 0);
}

GIF効果は以下の通りです.