简体   繁体   English

OpenCV:隐藏在面具后面的轮廓。 如何检测轮廓何时在掩模边缘附近移动?

[英]OpenCV: Contours hidden behind mask. How to detect when a contour is about to move near mask edge?

Summary of Question 问题摘要

I am detecting object silhouettes in front of a light source. 我正在检测光源前的物体轮廓。 To simplify the background and remove noise, I require masking everything that isn't the light source. 为了简化背景并消除噪音,我需要屏蔽不是光源的所有东西。 How can I tell when the object would be on the edge of the masked area? 如何辨别物体何时位于蒙面区域的边缘?

Assumptions 假设

Assume featureless (monochrome black and white for edge detection) and ambiguous (a square in image 1 may be a circle in image 2) in shape. 假设形状没有特征(用于边缘检测的单色黑白)和模糊(图像1中的正方形可以是图像2中的圆)。

Detailed Explanation of the Problem with "High Quality" Figures “高质量”人物问题的详细解释

Consider a silhouette in front of a light source. 考虑光源前的轮廓。 It is distinct and we can tell it is nested within the outer contour. 它是独特的,我们可以告诉它嵌套在外轮廓内。 Figure 1 depicts a simplified case. 图1描绘了一个简化的案例。

独特的轮廓

We can treat our outer circle as a mask in this case, and easily ignore everything NOT within the contour. 在这种情况下,我们可以将外圈视为蒙版,并且很容易忽略轮廓内的所有内容。 Figure 2 depicts the simplified case with some edge detection. 图2描绘了具有一些边缘检测的简化情况。

这里的轮廓很简单。好哇。

Everything works lovely until the silhouette moves to the edge of the light source. 一切都很美好,直到轮廓移动到光源的边缘。 Suddenly we run into problems. 突然间我们遇到了问题。 Figure 3 is an example of a shape on the edge. 图3是边缘上的形状的示例。

剪影与面具无法区分。

The silhouette is indistinguishable from the black of the background/masked area. 轮廓与背景/遮罩区域的黑色无法区分。 OpenCV either assumes that suddenly the contour of our light source is funny shaped and there is no other object to be detected. OpenCV要么假设我们的光源的轮廓突然变得有趣并且没有其他物体被检测到。

The Question Restated 问题重申了

What tools can I use to detect that there has been some sort of interruption of the edge shape? 我可以使用哪些工具来检测边缘形状是否存在某种中断? Is there a good/computational cheap way of determining if our silhouette is intersecting with another? 是否有一种好的/计算的廉价方法来确定我们的轮廓是否与另一个轮廓相交?

Graveyard of What I Know Does NOT Work 我所知道的墓地不起作用

  • Assuming a static or simple silhouette shape. 假设一个静态或简单的轮廓形状。 The figures are cartoons representing a more complicated real problem. 这些数字是代表更复杂的真实问题的漫画。
  • Assuming a perfectly round light source. 假设一个完美的圆形光源。 HoughCircles does not work. HoughCircles不起作用。

You can use the cv2.log_polar function to unwrap the circle/oval shape. 您可以使用cv2.log_polar函数来展开圆形/椭圆形。

log_polar

After that, np.argmax can be used to find the curve. 之后, np.argmax可用于查找曲线。 Try smoothing out the curve using Scipy's signal.savgol_filter() . 尝试使用Scipy的signal.savgol_filter()平滑曲线。 When the object blocks the light source, there will be a big difference between the smoothed line and the argmax data: 当对象阻挡光源时,平滑线和argmax数据之间会有很大差异: 图形

This is the code that I used: 这是我使用的代码:

import numpy as np
import cv2
# Read the image
img = cv2.imread('/home/stephen/Desktop/JkgJw.png', 0)
# Find the log_polar image
log_polar = cv2.logPolar(img, (img.shape[0]/2, img.shape[1]/2), 40, cv2.WARP_FILL_OUTLIERS)
# Create a background to draw on
bg = np.zeros_like(log_polar)
# Iterate through each row in the image and get the points on the edge
h,w = img.shape
points = []
for col in range(h-1):
    col_slice = log_polar[col:col+1, :]
    curve = np.argmax(255-col_slice)
    cv2.circle(bg, (curve, col), 0, 255, 1)
    points.append((curve, col))

cv2.imshow('log_polar', log_polar)
cv2.waitKey(0)
cv2.destroyAllWindows()


import scipy
from scipy import signal

x,y = zip(*points)
x_smooth = signal.savgol_filter(x,123,2)

import matplotlib.pyplot as plt
plt.plot(x)
plt.plot(x_smooth)
plt.show()

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM