项目需求
现需要使用工业摄像头对非标物体进行尺寸测量,在本文中我们将使用其他标注物进行替代。实验器材如下所示:
- 摄像头一个
- 待测物体
- 标准尺
需求分解
考虑到相机拍摄图像畸变,我们不妨设想一下:我们不进行畸变矫正,所有的检测都是建立在“畸变”后测量的数据,那么在进行计算的话,数据也是经过“畸变”后处理的数据了。这里我们可以参考地图的绘制中的“比例尺”,借用比例尺的思想进行工件的尺寸测量。
这里我们简化一下,在白纸上使用签字笔绘制一条线段替代被测物,使用摄像头拍摄后计算长度。这里我们可以简化一下模型:
待测物实体尺寸 = K · 待测物像素尺寸
K = 待测物实体尺寸 / 待测物像素尺寸
实验步骤:
- 准备好标准工件;
- 固定角度拍摄标准工件
- 分别测量标准工件尺寸与图像中的像素尺寸
- 应用上述公式得到比例系数:K
- 采集新数据使用比例系数和像素尺寸进行计算实体尺寸
代码设计
这里我们需要注意的一个地方是计算比例系数时候图像的大小与后续测量工件尺寸需保持一致。
计算图像尺寸代码:
这里我们可以得到图像的像素尺寸,使用方法为点击线段的两个端点即可获取两端点的图像坐标,进一步可以计算出自己的K值。
import cv2
img = cv2.imread('test.jpg')
def mouse_click(event, x, y, flags, para):
if event == cv2.EVENT_LBUTTONDOWN: # 左边鼠标点击
print('PIX:', x, y)
if __name__ == '__main__':
cv2.namedWindow("img")
cv2.setMouseCallback("img", mouse_click)
while True:
cv2.imshow('img', img)
if cv2.waitKey() == ord('q'):
break
cv2.destroyAllWindows()
使用K值计算新待测物的标准尺寸
这里的X1,X2,Y1,Y2分别使用上述的计算图像尺寸的代码计算得到,使用勾股定理可以得到线段的长度(这里以直线段做例子)
import math
x1, y1 = (386, 170)
x2, y2 = (552, 227)
num = (x2 - x1) * (x2 - x1) + (y2 - y1) * (y2 - y1)
L = math.sqrt(num)
print("像素尺寸", L)
S = L/(41.667) # 替换成自己计算的K值
print("实体尺寸", S)