【发布时间】:2014-08-31 21:44:29
【问题描述】:
所以,这是我的情况。我创建了一个基于颜色对象检测的对象检测程序。我的程序检测到红色并且效果很好。但这是我面临的问题:-
当周围有多个红色物体时,我的程序会检测到它们,并且当时它无法真正跟踪一个物体(即它在背景中跟踪其他各种大小的红色物体。它向我显示错误“背景中有太多噪音”。正如您在附加的“阈值图像”中看到的,它检测到圆形物体(这是我的跟踪对象)和我的红色帽子。我希望我的程序只检测我的跟踪对象(“这是一个圆形的可乐盖”)。我怎样才能做到这一点?请帮帮我。几天后我有我的工程设计比赛,我必须在我的讲师面前演示我的程序。我的程序应该只是能够检测和跟踪我想要的对象。谢谢
我的对象检测程序代码有点长。因此,我在此解释代码如下-我从网络摄像头帧捕获了一个帧-将其转换为 HSV-使用 HSV Inrange 过滤器过滤掉其他颜色,但对过滤后的图像应用红色应用形态学操作。这一切都在我的主要功能中
我的网络摄像头框架使用 1280*720 的帧分辨率。这有点减慢我的程序,但这是我必须为执行手势控制操作而做的权衡。无论如何,这里是我的 drawobjectfunction 和 trackfilteredobjectfunction。
int H_MIN = 0;
int H_MAX = 256;
int S_MIN = 0;
int S_MAX = 256;
int V_MIN = 0;
int V_MAX = 256;
//default capture width and height
const int FRAME_WIDTH = 1280;
const int FRAME_HEIGHT = 720;
//max number of objects to be detected in frame
const int MAX_NUM_OBJECTS=50;
//minimum and maximum object area
const int MIN_OBJECT_AREA = 20*20;
const int MAX_OBJECT_AREA = FRAME_HEIGHT*FRAME_WIDTH/1.5;
void drawObject(int x, int y,Mat &frame){
circle(frame,Point(x,y),20,Scalar(0,255,0),2);
if(y-25>0)
line(frame,Point(x,y),Point(x,y-25),Scalar(0,255,0),2);
else line(frame,Point(x,y),Point(x,0),Scalar(0,255,0),2);
if(y+25<FRAME_HEIGHT)
line(frame,Point(x,y),Point(x,y+25),Scalar(0,255,0),2);
else line(frame,Point(x,y),Point(x,FRAME_HEIGHT),Scalar(0,255,0),2);
if(x-25>0)
line(frame,Point(x,y),Point(x-25,y),Scalar(0,255,0),2);
else line(frame,Point(x,y),Point(0,y),Scalar(0,255,0),2);
if(x+25<FRAME_WIDTH)
line(frame,Point(x,y),Point(x+25,y),Scalar(0,255,0),2);
else line(frame,Point(x,y),Point(FRAME_WIDTH,y),Scalar(0,255,0),2);
putText(frame,intToString(x)+","+intToString(y),Point(x,y+30),1,1,Scalar(0,255,0),2);
}
void trackFilteredObject(int &x, int &y, Mat threshold, Mat &cameraFeed){
Mat temp;
threshold.copyTo(temp);
//these two vectors needed for output of findContours
vector< vector<Point> > contours;
vector<Vec4i> hierarchy;
//find contours of filtered image using openCV findContours function
findContours(temp,contours,hierarchy,CV_RETR_CCOMP,CV_CHAIN_APPROX_SIMPLE );
//use moments method to find our filtered object
double refArea = 0;
bool objectFound = false;
if (hierarchy.size() > 0) {
int numObjects = hierarchy.size();
//if number of objects greater than MAX_NUM_OBJECTS we have a noisy filter
if(numObjects<MAX_NUM_OBJECTS){
for (int index = 0; index >= 0; index = hierarchy[index][0]) {
Moments moment = moments((cv::Mat)contours[index]);
double area = moment.m00;
//if the area is less than 20 px by 20px then it is probably just noise
//if the area is the same as the 3/2 of the image size, probably just a bad filter
//we only want the object with the largest area so we safe a reference area each
//iteration and compare it to the area in the next iteration.
if(area>MIN_OBJECT_AREA && area<MAX_OBJECT_AREA && area>refArea){
x = moment.m10/area;
y = moment.m01/area;
objectFound = true;
refArea = area;
}else objectFound = false;
}
//let user know you found an object
if(objectFound ==true){
putText(cameraFeed,"Tracking Object",Point(0,50),2,1,Scalar(0,255,0),2);
//draw object location on screen
drawObject(x,y,cameraFeed);}
}else putText(cameraFeed,"TOO MUCH NOISE! ADJUST FILTER",Point(0,50),1,2,Scalar(0,0,255),2);
}
}
这是图片的链接;如您所见,它还检测到背景中的红色帽子以及可乐瓶的红色盖子。
我的观察:- 这是我的想法,以实现我不检测未知大小的红色物体的预期目标。我想我必须编辑我在上述程序中声明的最大对象区域的值(const int MAX_OBJECT_AREA = FRAME_HEIGHT*FRAME_WIDTH/1.5;)。我想我必须改变这个值,这可能会消除对更大的连续红色图片的检测。但是,还有另一个问题,一些物体不是完全红色的,它们有红色和其他颜色的斑块。因此,如果检测到的区域在我的程序中指定的范围内,那么我的程序也会检测到这些红色补丁。我的意思是我穿着一件混合颜色的 T 恤,当我穿着那件 T 恤测试我的程序时,我的程序能够从其他颜色中检测出红色。现在,我该如何解决这个问题?
【问题讨论】:
-
嗯...有点难以帮助。你的链接挂在我的 iPad 上,你没有提供任何代码或任何关于你正在使用的工具、平台和算法的指示。
-
@MarkSetchell:- 标记我不允许在 stackoverflow 中上传图片,因为我是新用户。所以,我不得不把它上传到 photobucket 中,并在这里链接。至于我的代码和规范,我现在要更新我的问题。谢谢
-
@MarkSetchell:- 用代码更新了我的问题
-
如果您尝试跟踪
moving红色物体,您可以计算每个物体的速度并拒绝任何不移动的物体(如帽子),或者使用图像差分技术检测运动。 -
查看我对您上一个问题的帖子:stackoverflow.com/questions/25576995/…
标签: opencv image-processing computer-vision