1. 程式人生 > >萌新學習手冊:openCV中Hassi角點檢測

萌新學習手冊:openCV中Hassi角點檢測

createTrackbar(const string& trackbarname, 
               const string& winname,                              
               int* value, int count,                              
               TrackbarCallback onChange = 0,                              
               void* userdata = 0);

用於建立一個滑動空間,可以動態調動閾值;

trackbarname:滑動空間的名稱;

winname:滑動空間用於依附的影象視窗的名稱;

value:初始化閾值;

count:滑動控制元件的刻度範圍;

TrackbarCallback是回撥函式,調動閾值後會執行

超級推薦Mat類詳解:

dst = Mat::zeros(Size size, int type);

例如本程式碼中用到dst = Mat::zeros(gray_src.size(), CV_32FC1);

Mat::zeros是初始化的一種用於生成一張全黑的影象

關於CV_32FC1等類似的引數的解釋

其中CV_32FC1表示每一個畫素點在記憶體中佔32位,型別為float(還有S和U分別代表有符號整型和無符號整型)C1表示單通道影象

cornerHarris(InputArray src, OutputArray dst, int blockSize, int ksize, double k, int borderType=BORDER_DEFAULT)

用於Harris角點檢測

src 輸入影象

dst儲存檢測的影象

blockSize傳入鄰域的大小

ksize用於求導的視窗大小

k Harris 角點檢測方程中的自由引數

BORDER_DEFAULT 影象卷積的時候邊界畫素不能被卷積操作,因為邊界畫素沒有完全跟kernel重疊,這種是openCV的預設操作,即在卷積開始之前增加邊緣畫素以確保影象的邊緣被處理,在卷積處理之後再去掉這些邊緣。

normalize(InputArry src,InputOutputArray dst,double alpha=1,double beta=0,int norm_type=NORM_L2,

normalsize用於歸一化資料,分為資料歸一化和範圍歸一化

引數說明

src               輸入陣列;

dst               輸出陣列,陣列的大小和原陣列一致;

alpha           1,用來規範值,2.規範範圍,並且是下限;

beta             只用來規範範圍並且是上限;

norm_type   歸一化選擇的數學公式型別;

dtype           當為負,輸出在大小深度通道數都等於輸入,當為正,輸出只在深度與輸入不同,不同的地方由dtype決定;

mark            掩碼。選擇感興趣區域,選定後只能對該區域進行操作。

#include<iostream>
#include<opencv2/opencv.hpp>
using namespace std;
using namespace cv;
const char* output_title = "HarrisCornerDetectionResult";
Mat src,gray_src;
int thresh = 130;//設定閾值
int max_counter = 255;
void Harris_Demo(int, void*);

int main(int argc,char** argv)
{

	src = imread("C:/Users/pbiha/Desktop/image/1.png");
	if (src.empty())
	{
		printf("can not load image\n");
		return -1;
	}
	
	namedWindow("input", CV_WINDOW_AUTOSIZE);
	imshow("input", src);

	namedWindow(output_title, CV_WINDOW_AUTOSIZE);
	cvtColor(src, gray_src, COLOR_BGR2GRAY);

	createTrackbar("Threshold:", output_title, &thresh, max_counter, Harris_Demo);
	Harris_Demo(0, 0);

	waitKey(0);
	return 0;
}

void Harris_Demo(int, void*)
{
	Mat dst,norm_dst,normScaleDst;
	dst = Mat::zeros(gray_src.size(), CV_32FC1);

	int ksize = 3;
	int blockSize = 2;
	double k = 0.04;
	cornerHarris(gray_src, dst, blockSize,ksize, k, BORDER_DEFAULT);//用Harris演算法計算並儲存在輸出陣列中
	normalize(dst, norm_dst, 0, 255, NORM_MINMAX,CV_32FC1,Mat());//把需要處理的資料經過歸一化限制在你需要的一定範圍內
	convertScaleAbs(norm_dst, normScaleDst);//使用線性變換轉換輸入陣列元素成8位無符號整型

	Mat resultImage = src.clone();
	for(int row = 0; row < resultImage.rows; row++) {
		uchar* currentRow = normScaleDst.ptr(row);//直接提取出當前這一行的所有的畫素點
		for (int col = 0; col < resultImage.cols; col++) {
			int value = (int)*currentRow;
			if (value>thresh) {
				circle(resultImage, Point(col, row), 1, Scalar(0, 0, 255), 2, 8, 0);
			}
			currentRow++;
		}
	}
	imshow(output_title, resultImage);
}