欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

1024程序员节~

程序员文章站 2022-04-28 18:32:28
...

#include
#include <core/core.hpp>
#include<opencv2/core/saturate.hpp>
#include <opencv2/highgui.hpp>
#include <opencv2/imgproc.hpp>
#include
using namespace std;
using namespace cv;

Mat image;
Mat imageCopy; //缁樺埗鐭╁舰妗嗘椂鐢ㄦ潵鎷疯礉鍘熷浘鐨勫浘鍍?
Mat targetImage;//鎴彇鐨勭洰鏍囧浘鍍?
bool leftButtonDownFlag=false; //宸﹂敭鍗曞嚮鍚庤棰戞殏鍋滄挱鏀剧殑鏍囧織浣?
Point originalPoint; //鐭╁舰妗嗚捣鐐?
Point processPoint; //鐭╁舰妗嗙粓鐐?
const char* videoPath = “c505.mp4”;

//灏嗕竴閮ㄥ垎鍙橀噺璁句负鍏ㄥ眬鍑芥暟锛屾彁楂樿繍琛屾晥鐜?
int cccc = 0;//鍒ゆ柇鐩爣鏍囪瀹屾垚
//H銆丼閫氶亾
int channels[] = { 0, 1 };
int histSize[] = { 30, 32 };
float HRanges[] = { 0, 180 };
float SRanges[] = { 0, 256 };
const float *ranges[] = { HRanges, SRanges };

void onMouse(int event, int x, int y, int flags, void* ustc); //榧犳爣鍥炶皟鍑芥暟
void getTarget();
void drawHist(Mat rectImage);
void tracing(const MatND srcHist);
double compHist(const MatND srcHist, Mat compareImage);

int main()
{
getTarget();
imshow(“Target object”, targetImage);
cout << originalPoint << processPoint << endl;
drawHist(targetImage);
Mat srcHsvImage;
cvtColor(targetImage, srcHsvImage, CV_BGR2HSV);
//閲囩敤H-S鐩存柟鍥捐繘琛屽鐞?
//棣栧厛寰楅厤缃洿鏂瑰浘鐨勫弬鏁?
MatND srcHist;
//杩涜鍘熷浘鐩存柟鍥剧殑璁$畻
calcHist(&srcHsvImage, 1, channels, Mat(), srcHist, 2, histSize, ranges, true, false);
//褰掍竴鍖?
normalize(srcHist, srcHist, 0, 1, NORM_MINMAX);

tracing(srcHist);
waitKey(0);
return 0;

}

void tracing(const MatND srcHist) {
int width = abs(processPoint.x - originalPoint.x);
int height = abs(processPoint.y - originalPoint.y);
cout << width << height << endl;
//鐩爣鎼滅储鍖哄煙璁惧畾涓哄師鍖哄煙鐨勫懆鍥翠笖闈㈢Н涓哄師鏉ヤ笁鍊?
int X1 = originalPoint.x - width;
int X2 = originalPoint.x + width;
int Y1 = originalPoint.y - height;
int Y2 = originalPoint.y + height;
//瓒婄晫妫€鏌?
if (X1 < 0)
X1 = 0;
if (Y1 < 0)
Y1 = 0;

Point preStart;
Point preEnd;

Point get1(0, 0);
Point get2(0, 0);

VideoCapture video(videoPath);
if (!video.isOpened())
{
	cout << "video not open.error!" << std::endl;
	return;
}
double fps = video.get(CV_CAP_PROP_FPS); //鑾峰彇瑙嗛甯х巼
double pauseTime = 1000 / fps; //涓ゅ箙鐢婚潰涓棿闂撮殧
int w = static_cast<int>(video.get(CV_CAP_PROP_FRAME_WIDTH));
int h = static_cast<int>(video.get(CV_CAP_PROP_FRAME_HEIGHT));
cv::Size S(w, h);
namedWindow("targetTracing");

VideoWriter write;
write.open("c501_test.avi", -1, fps, S, true);
while (true)
{
	//鍙栬棰戠殑涓€甯?
	video >> image;
	if (!image.data || waitKey(pauseTime) == 27)  //鍥惧儚涓虹┖鎴朎sc閿寜涓嬮€€鍑烘挱鏀?
	{
		break;
	}
	//鐩存柟鍥惧姣旂殑鐩镐技鍊?
	double comnum = 1.0;
	//鍒濆鍖栨悳绱㈠尯鍩?
	for (int Cy = Y1; Cy <= Y2; Cy += 10) {
		for (preStart.x = X1, preStart.y = Cy; preStart.x <= X2; preStart.x += 10) {

			if ((preStart.x + width) < image.cols)
				preEnd.x = preStart.x + width;
			else
				preEnd.x = image.cols - 1;
			if ((preStart.y + height) < image.rows)
				preEnd.y = preStart.y + height;
			else
				preEnd.y = image.rows - 1;
			//cout << preStart << preEnd << endl;

			Mat compareImg;
			compareImg = image(Rect(preStart, preEnd));
			double c = compHist(srcHist, compareImg);
			if (comnum > c) {
				get1 = preStart;
				get2 = preEnd;
				comnum = c;
			}
		}
	}
	//鍦ㄥ師濮嬭棰戝浘鍍忎笂鍒锋柊鐭╁舰锛屽彧鏈夊綋涓庣洰鏍囩洿鏂瑰浘寰堢浉浼兼椂鎵嶆洿鏂拌捣鐐规悳绱㈠尯鍩燂紝婊¤冻鐩爣杩涜绉诲姩鐨勫満鏅?
	if (comnum < 0.15) {
		X1 = get1.x - width;
		X2 = get1.x + width;
		Y1 = get1.y - height;
		Y2 = get1.y + height;

		if (X1 < 0)
			X1 = 0;
		if (Y1 < 0)
			Y1 = 0;
		
	}
	if(comnum<0.5)
		rectangle(image, get1, get2, Scalar(0, 0, 255), 2);
	//鍐欏叆涓€甯?
	write.write(image);
	imshow("targetTracing", image);
}
video.release();
write.release();

}

//鐢诲嚭鐩存柟鍥?
void drawHist(const Mat rectImage)
{
//瀹氫箟鍑芥暟闇€瑕佺殑涓€浜涘彉閲?
//鍥剧墖鏁伴噺nimages
int nimages = 1;
//閫氶亾鏁伴噺,鎴戜滑鎬绘槸涔犳儻鐢ㄦ暟缁勬潵琛ㄧず锛屽悗闈細璁插師鍥?
int channels[3] = { 0,1,2 };
//杈撳嚭鐩存柟鍥?
cv::Mat outputHist_red, outputHist_green, outputHist_blue;
//缁存暟
int dims = 1;
//瀛樻斁姣忎釜缁村害鐩存柟鍥惧昂瀵革紙bin鏁伴噺锛夌殑鏁扮粍histSize
int histSize[3] = { 256,256,256 };
//姣忎竴缁存暟鍊肩殑鍙栧€艰寖鍥磖anges
float hranges[2] = { 0, 255 };
//鍊艰寖鍥寸殑鎸囬拡
const float *ranges[3] = { hranges,hranges,hranges };
//鏄惁鍧囧寑
bool uni = true;
//鏄惁绱Н
bool accum = false;

//璁$畻鍥惧儚鐨勭洿鏂瑰浘(绾㈣壊閫氶亾閮ㄥ垎)
cv::calcHist(&rectImage, nimages, &channels[0], cv::Mat(), outputHist_red, dims, &histSize[0], &ranges[0], uni, accum);
//璁$畻鍥惧儚鐨勭洿鏂瑰浘(缁胯壊閫氶亾閮ㄥ垎)
cv::calcHist(&rectImage, nimages, &channels[1], cv::Mat(), outputHist_green, dims, &histSize[1], &ranges[1], uni, accum);
//璁$畻鍥惧儚鐨勭洿鏂瑰浘(钃濊壊閫氶亾閮ㄥ垎)
cv::calcHist(&rectImage, nimages, &channels[2], cv::Mat(), outputHist_blue, dims, &histSize[2], &ranges[2], uni, accum);

//閬嶅巻姣忎釜绠卞瓙(bin)妫€楠岋紝杩欓噷鐨勬槸鍦ㄦ帶鍒跺彴杈撳嚭鐨勩€?
//for (int i = 0; i < 256; i++)
	//std::cout << "bin/value:" << i << "=" << outputHist_red.at<float>(i) << std::endl;

//鐢诲嚭鐩存柟鍥?
int scale = 1;
//鐩存柟鍥剧殑鍥剧墖,鍥犱负灏哄鏄竴鏍峰ぇ鐨?鎵€浠ュ氨浠istSize[0]鏉ヨ〃绀哄叏閮ㄤ簡.
cv::Mat histPic(histSize[0], histSize[0] * scale * 3, CV_8UC3, cv::Scalar(0, 0, 0));
//鎵惧埌鏈€澶у€煎拰鏈€灏忓€?绱㈠紩浠?鍒?鍒嗗埆鏄孩,缁?钃?
double maxValue[3] = { 0, 0, 0 };
double minValue[3] = { 0, 0, 0 };
cv::minMaxLoc(outputHist_red, &minValue[0], &maxValue[0], NULL, NULL);
cv::minMaxLoc(outputHist_green, &minValue[1], &maxValue[1], NULL, NULL);
cv::minMaxLoc(outputHist_blue, &minValue[2], &maxValue[2], NULL, NULL);
//娴嬭瘯
std::cout << minValue[0] << " " << minValue[1] << " " << minValue[2] << std::endl;
std::cout << maxValue[0] << " " << maxValue[1] << " " << maxValue[2] << std::endl;

//绾靛潗鏍囩缉鏀炬瘮渚?
double rate_red = (histSize[0] / maxValue[0])*0.9;
double rate_green = (histSize[0] / maxValue[1])*0.9;
double rate_blue = (histSize[0] / maxValue[2])*0.9;

for (int i = 0; i < histSize[0]; i++)
{
	float value_red = outputHist_red.at<float>(i);
	float value_green = outputHist_green.at<float>(i);
	float value_blue = outputHist_blue.at<float>(i);
	//鍒嗗埆鐢诲嚭鐩寸嚎
	cv::line(histPic, cv::Point(i*scale, histSize[0]), cv::Point(i*scale, histSize[0] - value_red * rate_red), cv::Scalar(0, 0, 255));
	cv::line(histPic, cv::Point((i + 256)*scale, histSize[0]), cv::Point((i + 256)*scale, histSize[0] - value_green * rate_green), cv::Scalar(0, 255, 0));
	cv::line(histPic, cv::Point((i + 512)*scale, histSize[0]), cv::Point((i + 512)*scale, histSize[0] - value_blue * rate_blue), cv::Scalar(255, 0, 0));
}
cv::imshow("histgram", histPic);

}

//鍚姩鍑芥暟鍔犺浇瑙嗛锛屽苟浜や簰妗嗗嚭鐩爣鍥惧儚
void getTarget() {
VideoCapture video(videoPath);
if (!video.isOpened())
{
cout << “video not open.error!” << std::endl;
return;
}
double fps = video.get(CV_CAP_PROP_FPS); //鑾峰彇瑙嗛甯х巼
double pauseTime = 1000 / fps; //涓ゅ箙鐢婚潰涓棿闂撮殧
namedWindow(“Friends”);
setMouseCallback(“Friends”, onMouse);
while (true)
{
if (!leftButtonDownFlag) //鍒ゅ畾榧犳爣宸﹂敭娌℃湁鎸変笅锛岄噰鍙栨挱鏀捐棰戯紝鍚﹀垯鏆傚仠
{
video >> image;
}
if (!image.data || waitKey(pauseTime) == 27) //鍥惧儚涓虹┖鎴朎sc閿寜涓嬮€€鍑烘挱鏀?
{
break;
}
//涓ょ鎯呭喌涓嬩笉鍦ㄥ師濮嬭棰戝浘鍍忎笂鍒锋柊鐭╁舰
//1. 璧风偣绛変簬缁堢偣
//2. 宸﹂敭鎸変笅涓旀湭鎶捣
if (originalPoint != processPoint && !leftButtonDownFlag)
{
rectangle(image, originalPoint, processPoint, Scalar(255, 0, 0), 2);
}
imshow(“Friends”, image);
if (cccc == 1) {
destroyWindow(“Friends”);
break;
}

}
video.release();

}

//榧犳爣鍥炶皟鍑芥暟
void onMouse(int event, int x, int y, int flags, void *ustc)
{
if (event == CV_EVENT_LBUTTONDOWN)
{
leftButtonDownFlag = true; //鏍囧織浣?
originalPoint = Point(x, y); //璁剧疆宸﹂敭鎸変笅鐐圭殑鐭╁舰璧风偣
processPoint = originalPoint;
}
if (event == CV_EVENT_MOUSEMOVE && leftButtonDownFlag)
{
imageCopy = image.clone();
processPoint = Point(x, y);

	if (originalPoint != processPoint)
	{
		//鍦ㄥ鍒剁殑鍥惧儚涓婄粯鍒剁煩褰?
		rectangle(imageCopy, originalPoint, processPoint, Scalar(255, 0, 0), 2);
	}
	imshow("Friends", imageCopy);
	
}
if (event == CV_EVENT_LBUTTONUP)
{
	leftButtonDownFlag = false;
	targetImage = image(Rect(originalPoint, processPoint)); //鑾峰彇鐩爣鍥惧儚targetImage
	cccc = 1;
}

}

double compHist(const MatND srcHist,Mat compareImage)
{
//鍦ㄦ瘮杈冪洿鏂瑰浘鏃讹紝鏈€浣虫搷浣滄槸鍦℉SV绌洪棿涓搷浣滐紝鎵€浠ラ渶瑕佸皢BGR绌洪棿杞崲涓篐SV绌洪棿
Mat compareHsvImage;
cvtColor(compareImage, compareHsvImage, CV_BGR2HSV);
//閲囩敤H-S鐩存柟鍥捐繘琛屽鐞?
//棣栧厛寰楅厤缃洿鏂瑰浘鐨勫弬鏁?
MatND compHist;
//杩涜鍘熷浘鐩存柟鍥剧殑璁$畻

//瀵归渶瑕佹瘮杈冪殑鍥捐繘琛岀洿鏂瑰浘鐨勮绠?
calcHist(&compareHsvImage, 1, channels, Mat(), compHist, 2, histSize, ranges, true, false);
//娉ㄦ剰锛氳繖閲岄渶瑕佸涓や釜鐩存柟鍥捐繘琛屽綊涓€鍖栨搷浣?

normalize(compHist, compHist, 0, 1, NORM_MINMAX);
//瀵瑰緱鍒扮殑鐩存柟鍥惧姣?
double g_dCompareRecult = compareHist(srcHist, compHist, 3);//3琛ㄧず閲囩敤宸存皬璺濈杩涜涓や釜鐩存柟鍥剧殑姣旇緝
return g_dCompareRecult;

}