缺陷检测在机器视觉中还是比较常见的,故查看了大神东城青年的博客,自己跟着做了一遍,效果达到了,也有些不明之处有待解决。不废话直接上代码:
*图像采集
read_image (Image, 'C:/Users/LWJ/Desktop/AS_1/缺陷检测.jpg')
get_image_size (Image, Width, Height)
dev_close_window ()
dev_open_window (0, 0, Width/2, Height/2, 'black', WindowHandle)
dev_display (Image)
*采用快速二值化算子,可自动取阈值,最后一个参数相当于select_shape作用
fast_threshold (Image, Region, 128, 255, 20)
*采用形态学提取边界
boundary (Region, RegionBorder, 'inner') //使区域往边界缩小
*用矩形结构元素膨胀区域
dilation_rectangle1 (RegionBorder, RegionDilation, 7, 7)
reduce_domain (Image, RegionDilation, ImageReduced) //选取区域
*采用canny过滤器提取亚像素轮廓,1.7为平滑系数
edges_sub_pix (ImageReduced, Edges, 'canny', 1.8, 20, 40) //过滤器选择为canny
select_shape_xld (Edges, SelectedXLD, 'area', 'and', 150, 99999) //选择轮廓
count_obj (SelectedXLD, Number) //计算提取的轮廓区域数量
*采用最小外接矩形拟合提取的亚像素轮廓
fit_rectangle2_contour_xld (SelectedXLD, 'regression', -1, 0, 0, 3, 2, Row, Column, Phi, Length1, Length2, PointOrder)
dev_set_draw ('margin') //定义区域填充模式
*生成拟合的亚像素矩形轮廓
gen_rectangle2_contour_xld (Rectangle, Row, Column, Phi, Length1, Length2)
dev_display (Rectangle)
set_display_font (WindowHandle, 16, 'mono', 'true', 'false') //设置字体
dev_display (Image)
for i := 0 to Number-1 by 1
*依次提取图中的亚像素轮廓
select_obj (SelectedXLD, ObjectSelected, i+1)
*获取每个亚像素轮廓的每一个点坐标
get_contour_xld (ObjectSelected, Row1, Col)
gen_rectangle2_contour_xld (Rectangle1, Row[i], Column[i], Phi[i], Length1[i], Length2[i])
get_contour_xld (Rectangle1, Row2, Col1)
*筛选缺陷。即计算轮廓上每一点到拟合矩形四个角点的最小距离,对四周的点比较宽松,如果在拟合矩形以角点为圆心,
*半径为7的圆内,认为是正常的,对于边缘比较严格,如果某点离其拟合矩形对应点之间的距离大于1认为有缺陷
D1:=sqrt((Row1-Row2[1])*(Row1-Row2[1]) + (Col-Col1[1])*(Col-Col1[1]))
D2:=sqrt((Row1-Row2[2])*(Row1-Row2[2]) + (Col-Col1[2])*(Col-Col1[2]))
D3:=sqrt((Row1-Row2[3])*(Row1-Row2[3]) + (Col-Col1[3])*(Col-Col1[3]))
D4:=sqrt((Row1-Row2[4])*(Row1-Row2[4]) + (Col-Col1[4])*(Col-Col1[4]))
DistConor:=min2(min2(D1,D2),min2(D3,D4))
*计算轮廓上每一点与其拟合矩形对应点之间的距离
dist_rectangle2_contour_points_xld (ObjectSelected, 0, Row[i], Column[i], Phi[i], Length1[i], Length2[i], Distances)
flag:=true
for j:=0 to |Distances|-1 by 1
if (DistConor[j] > 7 and Distances[j] > 1)
flag:=false
break
endif
endfor
if(flag)
disp_message (WindowHandle, 'OK', 'Image', Row[i], Column[i]- Length2[i]/2, 'black', 'true')
else
disp_message (WindowHandle, 'Not OK', 'Image', Row[i], Column[i]- Length2[i]/2, 'red', 'true')
endif
stop ()
endfor
效果:连续按F5键可一一检测图像中的缺陷,效果图如下:
总结:采用快速二值化算子把我吓到了,真的够快,就是直接打出算子代码,参数就默认不改,然后出来的二值化效果非常地好。接着就是提取边界,这里用到形态学(这里用到矩形结构元素)提取。然后到了我不明白的地方了——提取亚像素轮廓并拟合轮廓,我自己来来回回调试观察了好几遍,这步大致的作用就是:提取亚像素轮廓然后用矩形代替亚像素轮廓,那么不是平直的轮廓就平直了(也不知道为什么要这样???)。最重要的一步到了,就是筛选缺陷,这一步更加不懂了,我自己都不好描述(大家就自己脑补吧,已懂的可以在下方评论让我也懂吧。哈哈哈),最后就是显示缺陷检测结果。