QQ登录

只需一步,快速开始

1.11 halcon 实现圆孔孔径测量

[ 复制链接 ]
这个帖子举例实现对金属孔径的测量,演示二维测量的原理 。
二维测量主要是X,Y两个 方向 的距离 测量。
在前面 帖子里可以看到测量时是在剖面 线方向 度量的,我们在实际 项目中
经常会遇到 平面内的X,Y两个方向 的测量,在HALCON中的本质方法跟前面
是一样的。同时测量机理跟用源码实现 一样,先进行像素 和实际 物理尺寸
的标定,也就是计算每个像素 代表实际物理空间的距离 是多少,然后进行图像
预处理,边缘提取拟合,几盒 参数 计算显示 等。在HALCON中集成了很多
边缘提取片子和拟合 片子,可以灵活 的利用进行二维 测量,
得到像素 结果后根据 标定 的比例进行实际 物理尺寸的转换,在HALCON的二维
测量中经常会遇到 直线,圆,椭圆的拟合 ,然后求出对应的尺寸,
这些算子是基于亚像素精度计算。
下面实例为实现测量金属表面上力个圆孔直径。

halcon 实现圆孔孔径测量结果

halcon 实现圆孔孔径测量结果


  1. *所有窗口更新关闭
  2. dev_update_off ()
  3. *读取图片保存到image
  4. read_image (Image, 'rim')
  5. *获取图片长宽
  6. get_image_size (Image, Width, Height)
  7. dev_open_window_fit_image (Image, 0, 0, Width, Height, WindowID)
  8. set_display_font (WindowID, 14, 'mono', 'true', 'false')
  9. * ****
  10. *进行二值化处理,提取灰度值 在0和128范围内的像素到变量DARK中,
  11. *在halcon中可以只提取选中的区域而不是事由图像 ,这个区别于VC中图像 处理对整图的处理。
  12. threshold (Image, Dark, 0, 128)
  13. *计算连通域,将上步得到的单个区域进行分割,不相连的区域进行分开处理,得到不相连的多个连通域
  14. connection (Dark, DarkRegions)
  15. *在上所得的连通 域中进行筛选,选出圆度在0.85-1,面积在50-99999的全部区域。
  16. select_shape (DarkRegions, Circles, ['circularity','area'], 'and', [0.85,50], [1.0,99999])
  17. *获取区域边界,Circles为输入区域,RegionBorder为输出区域,inner为边界类型,是内边界
  18. *算了使用形态学牌子提取边界,内边界就是原图和腐蚀后图的差,外边界 是膨胀 后和原图之差。
  19. boundary (Circles, RegionBorder, 'inner')
  20. *用半径 为6.5的圆形结构元素对变量regionborder进行膨胀 ,得到的膨胀 结果赋给变量RegionDilation
  21. dilation_circle (RegionBorder, RegionDilation, 6.5)
  22. *将RegionBorder内的全部分开区域合并成为一个区域,存ROIEdges。和connection功能相反。
  23. union1 (RegionDilation, ROIEdges)
  24. dev_display (Image)
  25. dev_set_color ('yellow')
  26. dev_set_draw ('margin')
  27. dev_display (ROIEdges)
  28. disp_continue_message (WindowID, 'black', 'true')
  29. stop ()
  30. * ****
  31. * step: extract edges
  32. * ****
  33. *从Image图像中提取ROIEdges区域对应的图像。
  34. reduce_domain (Image, ROIEdges, ImageROI)
  35. *这个函数 在进行边缘拟合 时经常遇到,在测量时也经常用到,函数得到 亚像素 边缘。
  36. *ImageROI为输入 图像,Edges为得到亚像素 边缘图像,Lanser2为采用边缘检测 方式
  37. *一般是一阶,二阶导数算子,或是Canny算子,当前 是拉普拉斯算子,0.3为平滑系数,
  38. *值越小,平滑的越厉害,会减少边缘细节,如果使用canny方法,效果相反。10,30分别
  39. *为边缘检测 时的低阈值和高阈值。
  40. edges_sub_pix (ImageROI, Edges, 'lanser2', 0.3, 10, 30)
  41. *对输入 的轮廓进行分类,Edges为输入 的轮廓 图像,SortedContours为排序后的结果轮廓,
  42. *'upper_left'为排序 方式,以左上优先,true递增方式为升序, 'row排序时行优先
  43. sort_contours_xld (Edges, SortedContours, 'upper_left', 'true', 'row')
  44. dev_display (Image)
  45. colored_display (SortedContours, ['cyan','white'])
  46. disp_continue_message (WindowID, 'black', 'true')
  47. stop ()
  48. * ****
  49. *此函数用于椭圆拟合,在二维测量中经常遇到 ,也就是如前面所介绍,先提取轮廓 ,然后拟合 ,Edges为输入
  50. *轮廓 图像 ,ftukey为椭圆拟合 的算法 ,第三参数-1用于计算的最大轮廓 点数,-1是缺少值 ,自动 选取 ,最大轮廓 点是大于等于
  51. *5的,第四个参数 2为一个轮廓 的末尾 点最大间距 ,如果 一个轮廓的末尾 点之间最大间距 等于2则认为轮廓 是闭合 的,第五
  52. *个参数 0,表示 在逼近过程 中被忽略的开始 和末尾 点的个数 ,第六个参数200表示 用于椭圆的点的数量 ,第七个参数3
  53. *表示 迭代的最大次数 用于鲁棒加权拟合,第七个参数2表示 消除异常值的裁剪因子,后面剩余参数为输出值,
  54. *Row,column,phi,表示 椭圆长半轴,短半轴,起点角度,末尾 点角度 ,
  55. *这个角度 是中心点和它们的连线与水平向右的基准线的夹角,顺时针为负,PointOrder表示 边界点的顺序。
  56. fit_ellipse_contour_xld (Edges, 'ftukey', -1, 2, 0, 200, 3, 2, Row, Column, Phi, Ra, Rb, StartPhi, EndPhi, PointOrder)
  57. NumHoles := |Ra|
  58. gen_ellipse_contour_xld (ContEllipse, Row, Column, Phi, Ra, Rb, gen_tuple_const(NumHoles,0), gen_tuple_const(NumHoles,rad(360)), gen_tuple_const(NumHoles,'positive'), 1)
  59. dev_display (Image)
  60. sort_contours_xld (ContEllipse, SortedContEllipse, 'upper_left', 'true', 'row')
  61. colored_display (SortedContEllipse, ['cyan','white'])
  62. dev_set_color ('yellow')
  63. for i := 0 to NumHoles - 1 by 1
  64.     sinPhi := sin(Phi[i])
  65.     cosPhi := cos(Phi[i])
  66.     disp_arrow (WindowID, Row[i], Column[i], Row[i] - sinPhi * Ra[i], Column[i] + cosPhi * Ra[i], 1)
  67.     disp_arrow (WindowID, Row[i], Column[i], Row[i] - cosPhi * Rb[i], Column[i] - sinPhi * Rb[i], 1)
  68.     disp_arrow (WindowID, Row[i], Column[i], Row[i] + sinPhi * Ra[i], Column[i] - cosPhi * Ra[i], 1)
  69.     disp_arrow (WindowID, Row[i], Column[i], Row[i] + cosPhi * Rb[i], Column[i] + sinPhi * Rb[i], 1)
  70.     set_tposition (WindowID, Row[i] - Rb[i] - 50, Column[i] - 85)
  71.     write_string (WindowID, 'D1=' + 2 * Ra[i])
  72.     set_tposition (WindowID, Row[i] - Rb[i] - 30, Column[i] - 85)
  73.     write_string (WindowID, 'D2=' + 2 * Rb[i])
  74. endfor
复制代码
测量的思路和前面介绍一样,一般都是先采集图像,预处理滤波,边缘定位,边缘亚像素提取,边缘拟合 ,
最后 根据 拟合 的几何参数进行距离求解与显示。当采用halcon时,也可以更为直观的利用其测量助手 进行测量
然后自动插入代码 ,再根据 测量结果进行适当 的调整。



回复

使用道具 举报

点击查看
快速回复 返回列表 客服中心 搜索