python - 如何使用 OpenCV 从图像(射击目标)中裁剪出最大的圆圈
问题描述
正如标题所述,我正在尝试从图像中裁剪出最大的圆圈。我在 python 中使用 OpenCV。确切地说,它是一个射击目标,它始终具有相同的格式,但可以使用任何移动设备在不同的光照条件下拍摄它的照片(我将在下面提供一些示例)。
我对图像识别完全陌生,所以我一直在尝试许多不同的方法来做到这一点,但无法找到一个适用于我所有目标图像的通用解决方案。
为什么我要这样做:
我的任务是计算给定目标图像上的一个或多个镜头的得分。我尝试过颜色分割来查找镜头,但由于镜头可以在不同的背景上,这将无法正常工作。所以现在我想看看空的拍摄目标图像和已经拍摄的目标图像之间的区别。另外,我需要能够分辨出它是在哪个目标上射击的(有两种目标类型)。因此,我尝试仅从图像中裁剪出目标以消除背景干扰,然后继续进行镜头识别。
到目前为止我已经尝试过:
1) 用 HoughCircles 找到最大的圆。我的下一步是以某种方式移除找到的圆圈的外部。我已经使用 HoughCircles 方法的配置有一段时间了,但总是有一个示例图像没有正确突出最外圈或没有突出任何圆圈:/。
我的最终配置看起来像这样:
img = cv2.GaussianBlur(img, (3, 3), 0)
cv2.HoughCircles(img, cv2.HOUGH_GRADIENT, 2, 10000, param1=50, param2=100, minRadius=200, maxRadius=0)
似乎使用 HoughCircles 不是正确的方法,所以我转向了我在互联网上找到的另一种可能的解决方案。
2)通过过滤圆圈似乎在图片上的“黑色”颜色范围来查找所有计数,而不是找到最大的计数。这个解决方案的问题似乎是有时图片有一个阴影破坏了外圈,因此似乎无法通过它进行裁剪。
我的代码如下所示:
# black color boundaries [B, G, R]
lower = [0, 0, 0]
upper = [150, 150, 150]
# create NumPy arrays from the boundaries
lower = np.array(lower, dtype="uint8")
upper = np.array(upper, dtype="uint8")
# find the colors within the specified boundaries and apply the mask
mask = cv2.inRange(img, lower, upper)
output = cv2.bitwise_and(img, img, mask=mask)
ret, thresh = cv2.threshold(mask, 40, 255, 0)
contours, hierarchy = cv2.findContours(thresh, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_NONE)
if len(contours) != 0:
# draw in blue the contours that were founded
cv2.drawContours(output, contours, -1, 255, 3)
# find the biggest countour (c) by the area
c = max(contours, key=cv2.contourArea)
x, y, w, h = cv2.boundingRect(c)
之后,我会尝试用找到的最大轮廓 (c) 画一个圆并按它裁剪。但是我已经看到绘制的圆圈不完整(可能是由于图片上的一些阴影),因此无论如何这都行不通。
在这些失败之后,我在这里尝试了很多其他问题的解决方案,但没有一个能解决我的问题。
示例图像:
老实说,我真的不知道该怎么做。我将不胜感激任何帮助,建议,任何事情。
解决方案
您的样本中有两种不同类型的目标。您可能希望单独处理它们或询问用户输入,它是什么类型的目标。基本上,你想知道目标的黑色部分有多大,它是覆盖 7-10 还是 4-10。
二值化你的图像。沿 X 和 Y 构建直方图 - 您会发现目标黑色部分的位置为(x_left, x_right, y_top, y_bottom)
。一旦你知道了,你就可以计算中心((top+bottom)/2, (left+right)/2)
。之后,您可以轻松计算图像每个像素的分数,因为您知道中心、黑点大小和其中不同分数区域的数量。
推荐阅读
- java - I-net Clear Report 缓存旧数据
- powerbi - 将前导 0(零)添加到 Power BI 中的月份数
- qemu - 在 Windows 10(64 位)下为 Windows 10(64 位)编译 QEMU
- javascript - 具有多个字符串输入的切换案例
- python - 使用两个循环将结果写入 csv 文件
- javascript - 使用 Javascript 为动态生成的文本区域实现漂亮的编辑器
- javascript - 没有从 NodeJS / JavaScript 触发 SQLite FOREIGN KEY 约束
- ruby-on-rails - MongoDB聚合在分组时将键推为零
- html - 在图像顶部添加颜色
- excel - 仅在保存工作簿时根据单元格中的值发送电子邮件