已知图像中有一个点集,求点集的包络线(给定一个点,寻找最近的点连线,直到连线封闭,
回到出发点)
,并用红色填充包络线包含的区域。
1.demo:
2.结果:
3.思路如下:
先二值化图像,取得所有黑点,确定一个点,寻找最近的点连线,直到连线封闭,回到出发点,
调用函数填充区域。(这里如果不按照我说的,而是找出黑点之后直接调用函数寻找区域,可能会出现不能很好贴合的问题)
4.代码如下:
import cv2
import numpy as np
import matplotlib.pyplot as plt
image='1.png'
img = cv2.imread(image, 0)
_, thresh = cv2.threshold(img, 0, 255, cv2.THRESH_BINARY_INV + cv2.THRESH_OTSU)
black_points = np.where(img == 0)
x = black_points[1]
y = black_points[0]
points=np.column_stack((x,y))
def find_closest_point(start_point, points):
min_distance = float('inf')
closest_point = None
for point in points:
distance = np.linalg.norm(start_point - point)
if distance < min_distance:
min_distance = distance
closest_point = point
return closest_point
def find_closed_loop(points):
start_point = points[0]
remaining_points = points[1:]
closed_loop = [start_point]
while len(remaining_points) > 0:
closest_point = find_closest_point(start_point, remaining_points)
closed_loop.append(closest_point)
remaining_points = np.delete(remaining_points, np.where((remaining_points == closest_point).all(axis=1)),
axis=0)
start_point = closest_point
closed_loop.append(closed_loop[0]) # 添加回到出发点
return np.array(closed_loop)
closed_loop = find_closed_loop(points)
x = points[:, 0]
y = points[:, 1]
img = cv2.imread(image, 1)
plt.imshow(img)
plt.fill(closed_loop[:, 0], closed_loop[:, 1], color='red', alpha=0.5)
plt.xlabel('x')
plt.ylabel('y')
plt.title('boundary')
plt.savefig("result.jpg")
plt.show()