在计算机视觉中,检测图像中的直线交叉点是一个常见的任务。本篇博客将介绍一种使用Python的机器视觉实用工具集来查找手绘棋盘直线交叉点的方法。这个工具集使用了OpenCV库和NumPy库。
原图如下:
在开始之前,我们需要准备以下条件:
下面是查找手绘棋盘直线交叉点的步骤:
import cv2
import numpy as np
def merge_lines(lines, e0, e1):
merged_lines = []
# 遍历每条直线
for i, line in enumerate(lines):
if len(merged_lines) == 0:
merged_lines.append(line)
else:
merged = False
# 遍历已合并的直线
for i, merged_line in enumerate(merged_lines):
theta = line[1]
distan= line[0]
mtheta = merged_line[1]
mdistan= merged_line[0]
dtheta=abs(np.sin(theta))-abs(np.sin(mtheta))
ds=abs(abs(mdistan)-abs(distan))
# 判断两条直线是否可合并
if dtheta < e0 and ds < e1 :
merged_lines[i] = [(line[0] + merged_line[0]) / 2, (line[1] + merged_line[1]) / 2]
merged = True
break
# 如果不能合并,则将直线添加到已合并的直线列表中
if not merged:
merged_lines.append(line)
return merged_lines
def extend_lines(lines, img_shape):
extended_lines = []
# 遍历每条直线
for line in lines:
rho = line[0]
theta = line[1]
a = np.cos(theta)
b = np.sin(theta)
x0 = a * rho
y0 = b * rho
x1 = int(x0 + 1000 * (-b))
y1 = int(y0 + 1000 * (a))
x2 = int(x0 - 1000 * (-b))
y2 = int(y0 - 1000 * (a))
extended_lines.append([(x1, y1), (x2, y2)])
return extended_lines
def find_intersections(lines):
intersections = []
# 遍历每条直线的组合
for i in range(len(lines)):
for j in range(i+1, len(lines)):
line1 = lines[i]
line2 = lines[j]
x1, y1 = line1[0]
x2, y2 = line1[1]
x3, y3 = line2[0]
x4, y4 = line2[1]
denominator = (x1 - x2) * (y3 - y4) - (y1 - y2) * (x3 - x4)
# 判断两条直线是否相交
if denominator != 0:
x = ((x1 * y2 - y1 * x2) * (x3 - x4) - (x1 - x2) * (x3 * y4 - y3 * x4)) / denominator
y = ((x1 * y2 - y1 * x2) * (y3 - y4) - (y1 - y2) * (x3 * y4 - y3 * x4)) / denominator
intersections.append((int(x), int(y)))
return intersections
def draw_lines(img, lines):
for line in lines:
cv2.line(img, line[0], line[1], (0, 0, 255), 2)
def draw_intersections(img, intersections):
for intersection in intersections:
cv2.circle(img, intersection, 5, (0, 255, 0), -1)
def detect_lines(img, e0, e1, rho, threshold):
gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
edges = cv2.Canny(gray, 50, 150, apertureSize=3)
lines = cv2.HoughLines(edges, rho, np.pi/180, threshold)
lines = lines[:, 0, :]
merged_lines = merge_lines(lines, e0, e1)
extended_lines = extend_lines(merged_lines, img.shape)
intersections = find_intersections(extended_lines)
draw_lines(img, extended_lines)
draw_intersections(img, intersections)
return img
e0 = 10 # 角度误差阈值
e1 = 10 # 距离误差阈值
rho = 2 # 像素偏差
threshold = 260 # 投票数阈值
img = cv2.imread('jing.png')
result = detect_lines(img, np.sin(e0/180*np.pi/2), e1, rho, threshold)
cv2.imshow('Result', result)
cv2.waitKey(0)
cv2.destroyAllWindows()
本篇博客介绍了使用Python的机器视觉实用工具集来查找手绘棋盘直线交叉点的方法。通过利用OpenCV库和NumPy库,我们可以很轻松地实现直线合并、直线延长和直线交叉点查找操作。这个工具集可以帮助我们在图像处理中更好地处理直线交叉点的检测任务。
本站源码链接:
或入下方公众号获取: