c++ - 快速可靠的反射球检测方法

标签 c++ opencv image-processing

我在图像中有一个高度反光的球,看起来像这样:

enter image description here

实时检测球的稳健方法是什么? (5-10 帧/秒)

我尝试了几种分割算法,但它们无法将球与背景分开,而是将球切成碎片,因为球本身有许多不同的区域。

由于反射特性,简单的圆形霍夫变换效果不佳。这同样适用于任何简单的阈值或形态学操作。

对于一般处理反光表面,您有什么建议吗?

最佳答案

HoughCircles建议很好,只要您大致了解球将如何在框架中移动,因此大致了解您所考虑的最小、最大半径:

import numpy as np
import cv2
import cv2.cv as cv

img = cv2.imread('wcEXm.jpg',0)


#Method 1: Hough Circles
img = cv2.medianBlur(img,5)
cimg = cv2.cvtColor(img,cv2.COLOR_GRAY2BGR)

# HoughCircles(image, method, dp, minDist[, circles[, param1[, param2[, minRadius[, maxRadius]]]]])
circles = cv2.HoughCircles(img,cv.CV_HOUGH_GRADIENT,dp=1,minDist=50,param1=127,param2=30,minRadius=50,maxRadius=150)

circles = np.uint16(np.around(circles))
for i in circles[0,:]:
    # draw the outer circle
    cv2.circle(cimg,(i[0],i[1]),i[2],(0,255,0),2)
    # draw the center of the circle
    cv2.circle(cimg,(i[0],i[1]),2,(0,0,255),3)

cv2.imshow('detected circles',cimg)

Hough Circles

另一种选择是使用 findContours() .使用正确的选项和一些过滤(例如 dilate()erode()),您可以从背景中分割球以及宽度和高度之间的比率(更接近到正方形)会有帮助。

dilated and eroded threshold

但是,如果您对球的大小不感兴趣,只知道它在哪里,那么有一件小事可以大大简化这个过程。 你的球是反光的,甚至要开始检测你都需要光源,因此,即使颜色/环境看起来不同,球也会有亮点。假设光源不在画面中,您的反光球可能是场景中下一个最亮的东西:

import cv2

img = cv2.imread('wcEXm.jpg',0)

minVal, maxVal, minLoc, maxLoc = cv2.minMaxLoc(img)
cv2.circle(img, maxLoc, 20, (0,192,0),10)

minMaxLoc

在 RaspberryPi 上的性能方面,我推荐如下:

  1. 使用 Adrian 的 tutorial on using PiCam with OpenCV in Python
  2. 如果您打算使用 minMaxLoc() 或其他处理灰度图像的函数,您可以使用 'yuv'颜色空间,只需使用 Y(亮度) channel 即可节省一些时间,无需将 RGB 转换为亮度/灰度
  3. 使用较小的分辨率(例如 320x240 或 160x120)。如果您需要将球的 x,y 位置映射到其他位置,您可以按比例放大结果。

更新: 另一件可能有帮助的事情是 Canny edge detection因为场景简单,球会很突出:

edges = cv2.Canny(img,100,200)

Canny Edge Detection

Canny Edge Contours

关于c++ - 快速可靠的反射球检测方法,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/42706085/

相关文章:

c++ - 找到第二个最小值

opencv - OpenCV(和其他地方)中使用的 Scharr-Filter 中的值的解释

MATLAB 中的图像上采样使用 image() 和 imshow() 生成白色图像

python - 将图像编辑为 tensorflow 张量 python

android如何在jpeg上创建鱼眼效果

c++ - WCOUT 和 COUT 中未打印的 ASCII 字符

c++ - 不连续的嵌套命名空间

c++ - 为 tile 中的线程将数据复制到 tile_static

python - 如何统计模板匹配检测到的对象数量?

visual-studio-2010 - cxcore210.dll 的问题