如何使用 C++ 在 OpenCV 中追踪颜色?
opencvc++server side programmingprogramming
颜色追踪与颜色检测类似。为了实现追踪,我们额外添加了几条线来计算被检测物体的面积,然后追踪该区域的当前位置,最后使用 OpenCV 的 line() 函数显示物体的运动路径。
以下程序演示了如何使用 C++ 在 OpenCV 中追踪颜色。
示例
#include<iostream> #include<opencv2/highgui/highgui.hpp> #include<opencv2/imgproc/imgproc.hpp> using namespace std; using namespace cv; int main(int argc, char** argv) { VideoCapture video_load(0);//从默认摄像头捕获视频// namedWindow("Adjust");//声明显示图像的窗口// int Hue_Low= 0;//色相下限// int Hue_high = 22;//色相上限// int Sat_Low =99;//饱和度下限// int Sat_high = 255;//饱和度上限// int Val_Low = 0;//数值下限// int Val_high = 255;//值的上限// createTrackbar(&"LowH";, &"Adjust";, &Hue_Low, 179);//最小色相的跟踪条// createTrackbar(&"HighH";, &"Adjust";, &Hue_high, 179);//最大色相的跟踪条// createTrackbar(&"LowS";, &"Adjust";, &Sat_Low, 255);//最小饱和度的跟踪条// createTrackbar(&"HighS";, &"Adjust";, &Sat_high, 255);// 最大饱和度的滑动条// createTrackbar(&"LowV";, &"Adjust";, &Val_Low,255);// 最小值滑动条// createTrackbar(&"HighV";, &"Adjust";, &Val_high, 255);// 最大值的滑动条// int Horizontal_Last = -1;// 初始水平位置// int Vertical_Last = -1;// 初始垂直位置// Mat temp;//声明一个矩阵,用于从视频流加载帧// video_load.read(temp);//从视频流加载帧// Mat track_motion = Mat::zeros(temp.size(), CV_8UC3);//创建用于检测的黑色矩阵// while (true) { Mat actual_Image;//声明一个用于实际图像的矩阵// bool temp_load= video_load.read(actual_Image);//将视频中的帧加载到矩阵// Mat convert_to_HSV;//声明一个矩阵,用于存储转换后的图像// cvtColor(actual_Image, convert_to_HSV, COLOR_BGR2HSV);//将 BGR 图像转换为 HSV// Mat adjusted_frame;//声明检测到的颜色的矩阵// inRange(converted_to_HSV,Scalar(Hue_Low, Sat_Low, Val_Low), Scalar(Hue_high, Sat_high, Val_high), adjusted_frame);//应用轨迹条值的更改// erode(adjusted_frame,adjusted_frame,getStructuringElement(MORPH_ELLIPSE, Size(5, 5)));//形态学开运算,用于从前景中移除小物体// dilate(adjusted_frame, adjusted_frame,getStructuringElement(MORPH_ELLIPSE, Size(5, 5)));//形态学开运算,用于从前景中移除小物体// dilate(adjusted_frame, adjusted_frame,getStructuringElement(MORPH_ELLIPSE, Size(5, 5)));//形态学闭运算,用于填充前景中的小洞// erode(adjusted_frame, adjusted_frame, getStructuringElement(MORPH_ELLIPSE, Size(5, 5)));//形态学闭包填充前景小孔// Moments determining_object = moments(adjusted_frame);//根据检测到的彩色帧创建对象// double Vertical_moment = Detection_object.m01;//获取垂直位置值// double Horizontal_moment = Detection_object.m10;//获取水平位置值// double tracking_area = detecting_object.m00;//获取物体面积// if (tracking_area > 10000){ //当物体面积大于 10000 像素时// int posX = Horizontal_moment / Tracking_area;//计算物体的水平位置// int posY = Vertical_moment / Tracking_area;//计算物体的垂直位置// if (Horizontal_Last >= 0 && Vertical_Last >= 0 && posX >= 0 && posY >= 0){ //当检测到的物体移动时// line(track_motion, Point(posX, posY), Point(Horizontal_Last, Vertical_Last), Scalar(0, 0, 255), 2);//在检测到的物体运动的路径上绘制红色线条// } Horizontal_Last = posX;//获取新的水平位置// vertical_Last = posY;//获取新的垂直位置值// } imshow(&"Detected_Object", adjusted_frame);//显示检测到的物体// actual_Image = actual_Image + track_motion;//在原始视频帧中绘制连续线// imshow(&"Actual",actual_Image);//显示原始视频// cout << "position of the object is:" << Horizontal_Last << "," << vertical_Last << endl;//显示跟踪的坐标值// if(waitKey(30)==27){//如果按下esc键,循环将中断// cout << "esc key is pressed by user" << endl; break; } } return 0; }