【Halcon回顾之2D Metrology】

2023-10-07 01:20
文章标签 回顾 2d halcon metrology

本文主要是介绍【Halcon回顾之2D Metrology】,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

Halcon系统回顾之2D Metrology

  • 2D Metrology的适用场景
  • 文章的展开逻辑
  • 官方案例
    • 代码关键图像结果展示
  • 上述案例中核心算子的理解
  • 2D Metrology通用方案与测试代码

2D Metrology的适用场景

如果被测量的对象可以被直线、圆、椭圆、矩形表示,并且拥有已知的无限靠近这些被测量对象的边缘或其他参数(位置、方向、尺寸等),在这种情况下使用2D计量去提取被测量对象的相关参数将是可靠且有效的。

文章的展开逻辑

以一个具体的官方案例进行展开,先建立对2D Metrology的一个整体认识。然后再去拓展更多的相关算法。最后针对2D计量问题建立一个通用的解决方案流程。(自己使用1D检测算子实现直线和圆的检测------可以参考另一篇1D测量中有实现代码,如果感兴趣完全也可以实现各种几何形状的检测)

官方案例

* 实现圆和矩形的测量* step1:图像显示初始化
dev_update_off ()
read_image (Image, 'pads')
get_image_size (Image, Width, Height)
dev_close_window ()
dev_open_window_fit_image (Image, 0, 0, -1, -1, WindowHandle)
set_display_font (WindowHandle, 14, 'mono', 'true', 'false')* step2:定义近似的位置和测量圆圈的公差,其实就是手动设置圆存在的中心点位置
RowCircle := [52:89:500]
CircleInitRow := [RowCircle,RowCircle]
CircleInitColumn := [gen_tuple_const(6,348),gen_tuple_const(6,438)]
gen_cross_contour_xld (Cross1, CircleInitRow, CircleInitColumn, 6, 0.785398)
CircleInitRadius := [gen_tuple_const(6,23),gen_tuple_const(6,23)]
CircleRadiusTolerance := 12* step3:定义近似的位置和测量矩形的公差,设置矩形的轮廓区域
RectangleInitRow := [410,410]
RectangleInitColumn := [215,562]
RectangleInitPhi := [0,0]
RectangleInitLength1 := [85,85]
RectangleInitLength2 := [88,88]
RectangleTolerance := 10* step4:创建测量模型(数据结构)
create_metrology_model (MetrologyHandle)* step5:设置测量数据结构的待检测图像的宽高(提升检测时间).
set_metrology_model_image_size (MetrologyHandle, Width, Height)* step6:将上面的矩形对象添加到测量模型中
add_metrology_object_rectangle2_measure (MetrologyHandle, RectangleInitRow, RectangleInitColumn, RectangleInitPhi, RectangleInitLength1, RectangleInitLength2, RectangleTolerance, 5, .5, 1, [], [], MetrologyRectangleIndices)*step7:将上面的圆形对象添加到测量模型中
add_metrology_object_circle_measure (MetrologyHandle, CircleInitRow, CircleInitColumn, CircleInitRadius, CircleRadiusTolerance, 5, 1.5, 2, [], [], MetrologyCircleIndices)*step8:设置测量模型对象的检测对象相关参数(每个计量对象可以测量一个以上的圆/矩形/线/椭圆)
set_metrology_object_param (MetrologyHandle, MetrologyCircleIndices, 'num_instances', 2)
set_metrology_object_param (MetrologyHandle, MetrologyCircleIndices, 'measure_transition', 'uniform')
set_metrology_object_param (MetrologyHandle, MetrologyCircleIndices, 'min_score', .9)*step9: 实施测量
apply_metrology_model (Image, MetrologyHandle)*step10: 获取测量结果
get_metrology_object_result (MetrologyHandle, MetrologyRectangleIndices, 'all', 'result_type', 'all_param', RectangleParameter)1. 这里要知道RectangleParameter检测结果参数的数据结构信息
Sequence := [0:5:|RectangleParameter| - 1]
RectangleRow := RectangleParameter[Sequence]
RectangleColumn := RectangleParameter[Sequence + 1]
RectanglePhi := RectangleParameter[Sequence + 2]
RectangleLength1 := RectangleParameter[Sequence + 3]
RectangleLength2 := RectangleParameter[Sequence + 4]2. 获取圆形检测结果
get_metrology_object_result (MetrologyHandle, MetrologyCircleIndices, 'all', 'result_type', 'all_param', CircleParameter)3. 提取检测结果更加详细的信息
Sequence := [0:3:|CircleParameter| - 1]
CircleRow := CircleParameter[Sequence]
CircleColumn := CircleParameter[Sequence + 1]
CircleRadius := CircleParameter[Sequence + 2]4. 5. 结果展示6. 7. 获取测量conturs
get_metrology_object_result_contour (Contours, MetrologyHandle, 'all', 'all', 1.5)8. 获取到检测区域的conturs,以及轮廓坐标,并根据这些坐标去拟合成圆或矩形
get_metrology_object_measures (Contour, MetrologyHandle, 'all', 'all', Row1, Column1)
gen_cross_contour_xld (Cross, Row1, Column1, 6, 0.785398)9. Display everything
Color := ['gray','cyan','green']
dev_display (Image)
dev_set_line_width (1)
dev_set_color (Color[0])
dev_display (Contour)
dev_set_color (Color[1])
dev_display (Cross)
dev_set_line_width (2)
dev_set_color (Color[2])
dev_display (Contours)
Message := Color[2] + ': Measurement result'
Message[1] := Color[1] + ': Edge candidate points'
Message[2] := Color[0] + ': Measure regions'
disp_message (WindowHandle, Message, 'window', 12, 12, 'black', 'true')

代码关键图像结果展示

原始图像,以及检测结果图像显示:
原始图像自动生成的检测矩形
关键边缘点检测结果
这里其实可以结合一维测量中的gen_measure_rectangle2和measure_pos算子来进行理解。下面是我用一维检测中的方法实现的直线和圆的检测代码可供参考:

上述案例中核心算子的理解

  • create_metrology_model(MetrologHandle) 创建2D计量模型,该模型对应的数据结构用于存储所有的几何对象,以及所有测量所需的参数和最终测量结果数据。
  • get_metrology_object_result(MetrologyHandle,Index,Instance,GenParamName,GenParamValue,Parameter) 获取测量结果----侧面窥探计量模型的数据结构:
    1. GenParamName:
    2. GenParamValue:

2D Metrology通用方案与测试代码

step1: 创建2dMetrology计量模型,并指定待测量图像的尺寸;

  • 使用create_metrology_model创建计量模型;(该模型将会存储被测量对象的所有相关参数)
  • 使用set_metrology_model_image_size设置计量模型数据结构中的图像尺寸;

step2: 将计量对象的相关数据添加到计量模型中;

  • add_metrology_object_circle_measure()添加圆对象到计量模型中;
  • add_metrology_object_ellipse_measure()添加椭圆对象到计量模型中;
  • add_metrology_object_rectangle2_measure()添加矩形对象到计量模型中;
  • add_metrology_object_line_measure()添加线对象到模型中;
  • 当然也可以使用add_metrology_object_generic()直接配置任意形状的对象类型到计量模型中;

step3: 检查或可视化添加到计量模型中的几何对象的contour;以及查看创建的测量rectangle2的contour;

  • get_metrology_object_model_contour(); 获取添加到模型中的对象XLD轮廓
  • get_metrology_object_measures(); 获取生成的用于测量的矩形XLD轮廓;

step4(可选): 使用set_metrology_object_param修改添加到模型中对象的参数;

step5: 在使用过定义的模型后,想要直接继续使用该模型,可以通过使用align_metrology_model()将创建的模型对齐到新的检测目标对象,该算子的相关对齐参数,一般是使用基于shape的模板匹配方法所得,当然也可以使用其他检测方法。

step6: 实施模型的测量

  • 使用apply_metrology_model()应用创建的测量模型,其实这里的内部机制是使用了1D检测中的 measure_pos()或fuzzy_measure_pos()检测算子去检测边缘。
  • 获取测量结果:
    1. get_metrology_object_result可以返回拟合后的集合对象的相关参数,也可以只返回拟合的边缘和振幅。
    2. get_metrology_object_measures()可以获取所有边缘的行列坐标;
    3. get_metrology_object_result_contour()可以可视化拟合后的目标集合对象的轮廓,并且可以获取这些拟合几何形状的XLD轮廓。

step7: 若要反复使用定义好的model,最好的方式是将定义好的model进行保存等操作。

step8:(对step5中内容的补充) 若要实现将在一个图像中定义的计量模型应用到其他的图像,需要使用align_metrology_model(), 其实现核心就是将生成检测矩形的参考点参数进行的更改,具体的方法如下所示:
1. 获取新图像中待测量对象的位置:
1.1. 使用基于shape-based匹配方法;
1.2. 使用区域分割的方法;
1.3. 使用点之间的对应关系对定义的模型进行仿射变换();
2. 获取关键参数,并使用set_metrology_model_param()将参数写入。并应用计量模型检测算子。

Note: 下面是对step8中重新利用计量模型的简单案例:
在两张不同的图像中使用同一个计量模型进行测量。
请添加图片描述
请添加图片描述

// 案例1: 使用基于模板匹配的方式重用计量模型
read_image (Image, 'C:/Users/620H/Desktop/博客代码/3.jpg')
rgb1_to_gray (Image, Image3)dev_get_window (WindowHandle)
dev_display (Image3)* step1: 创建测量对象的逼近轮廓
draw_circle (WindowHandle, Row, Column, Radius)
gen_circle (Circle, Row, Column, Radius)* step2: 创建2D计量模型
create_metrology_model (MetrologyHandle)
get_image_size (Image3, Width, Height)
set_metrology_model_image_size (MetrologyHandle, Width, Height)* step3: 查验添加到计量模型中的预检测轮廓
add_metrology_object_circle_measure (MetrologyHandle, Row, Column, Radius, 20, 5, 1, 30, [], [], Index)get_metrology_object_model_contour (Contour, MetrologyHandle, 0, 1.5)   // 传入到计量模型中的集合轮廓
get_metrology_object_measures (Contours, MetrologyHandle, 'all', 'all', Row1, Column1)   // 测量矩形轮廓* step4: 应用计量模型
apply_metrology_model (Image3, MetrologyHandle)* step6: 查看测量结果
get_metrology_object_result (MetrologyHandle, 0, 'all', 'result_type', 'all_param', Parameter)   //Parameter:中心点和半径
gen_cross_contour_xld (Cross, Parameter[0], Parameter[1], 16, 0.785398)get_metrology_object_result_contour (Contour1, MetrologyHandle, 0, 'all', 1.5)    // 获取的最终拟合到的轮廓* spart1: 使用模板匹配方式重用上面计量模型* 7.1: 获取模板图像
set_system ('border_shape_models', 'false')dev_clear_window ()
dev_display (Image3)draw_circle (WindowHandle, Row3, Column3, Radius1)
gen_circle (ModelRegion, Row3, Column3, Radius1)
reduce_domain (Image3, ModelRegion, TemplateImage)* 7.2: 创建模板
create_shape_model (TemplateImage, 5,rad(-45), rad(180), rad(0.7394), ['none','no_pregeneration'], 'use_polarity', [21,47,4], 8, ModelID)
* 获取创建模板的轮廓* 将模板的中心点作为计量生成检测矩形区域的参考中心点
area_center (ModelRegion, Area, Row2, Column2)
set_metrology_model_param (MetrologyHandle, 'reference_system', [Row2,Column2,0])get_shape_model_contours (ModelContours, ModelID, 1)* 读取待检测图像
read_image (Image5, 'C:/Users/620H/Desktop/博客代码/5.jpg')
rgb1_to_gray (Image5, GrayImage)
dev_display (GrayImage)* 7.3: 搜索目标
find_shape_model (GrayImage, ModelID, rad(-45), rad(180), 0.8, 0, 0.5, 'least_squares', [5,1], 1, Row, Column, Angle, Score)* 如果检测到了才执行,只选匹配度最高的目标
if(|Score| > 0)tuple_sort_index (Row, Indices)tuple_inverse (Indices, Inverted)index_max := Inverted[0]*7.4 生成仿射变换矩阵hom_mat2d_identity (HomMat2D) hom_mat2d_rotate (HomMat2D, Angle[index_max], 0, 0, HomMat2D)hom_mat2d_translate (HomMat2D, Row[index_max], Column[index_max], HomMat2D)affine_trans_contour_xld (ModelContours, TransContours, HomMat2D)dev_set_color ('green')dev_display (TransContours)* 7.5 将计量模型生成测量矩形的参考点替换为新检测目标的中心点align_metrology_model (MetrologyHandle,Row[index_max], Column[index_max], Angle[index_max])* 检查传入的轮廓是否合理get_metrology_object_model_contour (Contour3, MetrologyHandle, 0, 1.5)get_metrology_object_measures (Contours1, MetrologyHandle, 'all', 'all', Row4, Column4)* 7.6 应用计量模型到新的图片上apply_metrology_model (GrayImage, MetrologyHandle)get_metrology_object_result_contour (Contour2, MetrologyHandle, 0, 'all', 1.5)    // 获取的最终拟合到的轮廓
endif
clear_shape_model (ModelID)

这篇关于【Halcon回顾之2D Metrology】的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/155182

相关文章

基于WinForm+Halcon实现图像缩放与交互功能

《基于WinForm+Halcon实现图像缩放与交互功能》本文主要讲述在WinForm中结合Halcon实现图像缩放、平移及实时显示灰度值等交互功能,包括初始化窗口的不同方式,以及通过特定事件添加相应... 目录前言初始化窗口添加图像缩放功能添加图像平移功能添加实时显示灰度值功能示例代码总结最后前言本文将

Java基础回顾系列-第七天-高级编程之IO

Java基础回顾系列-第七天-高级编程之IO 文件操作字节流与字符流OutputStream字节输出流FileOutputStream InputStream字节输入流FileInputStream Writer字符输出流FileWriter Reader字符输入流字节流与字符流的区别转换流InputStreamReaderOutputStreamWriter 文件复制 字符编码内存操作流(

Java基础回顾系列-第五天-高级编程之API类库

Java基础回顾系列-第五天-高级编程之API类库 Java基础类库StringBufferStringBuilderStringCharSequence接口AutoCloseable接口RuntimeSystemCleaner对象克隆 数字操作类Math数学计算类Random随机数生成类BigInteger/BigDecimal大数字操作类 日期操作类DateSimpleDateForma

Java基础回顾系列-第三天-Lambda表达式

Java基础回顾系列-第三天-Lambda表达式 Lambda表达式方法引用引用静态方法引用实例化对象的方法引用特定类型的方法引用构造方法 内建函数式接口Function基础接口DoubleToIntFunction 类型转换接口Consumer消费型函数式接口Supplier供给型函数式接口Predicate断言型函数式接口 Stream API 该篇博文需重点了解:内建函数式

Java基础回顾系列-第二天-面向对象编程

面向对象编程 Java类核心开发结构面向对象封装继承多态 抽象类abstract接口interface抽象类与接口的区别深入分析类与对象内存分析 继承extends重写(Override)与重载(Overload)重写(Override)重载(Overload)重写与重载之间的区别总结 this关键字static关键字static变量static方法static代码块 代码块String类特

Java基础回顾系列-第六天-Java集合

Java基础回顾系列-第六天-Java集合 集合概述数组的弊端集合框架的优点Java集合关系图集合框架体系图java.util.Collection接口 List集合java.util.List接口java.util.ArrayListjava.util.LinkedListjava.util.Vector Set集合java.util.Set接口java.util.HashSetjava

Java基础回顾系列-第九天-数据库编程

Java基础回顾系列-第九天-数据库编程 数据库简介工具包java.sql API 内容与数据库建立连接执行SQL语句数据库检索和更新查询结果SQL类型对应Java类型映射元数据异常 API方法DriverManagerConnectionStatementPreparedStatementCallableStatementResultSetjava.sql.Date批处理、存储过程、事务

Java基础回顾系列-第一天-基本语法

基本语法 Java基础回顾系列-第一天-基本语法基础常识人机交互方式常用的DOS命令什么是计算机语言(编程语言) Java语言简介Java程序运行机制Java虚拟机(Java Virtual Machine)垃圾收集机制(Garbage Collection) Java语言的特点面向对象健壮性跨平台性 编写第一个Java程序什么是JDK, JRE下载及安装 JDK配置环境变量 pathHe

Vue2电商项目(二) Home模块的开发;(还需要补充js节流和防抖的回顾链接)

文章目录 一、Home模块拆分1. 三级联动组件TypeNav2. 其余组件 二、发送请求的准备工作1. axios的二次封装2. 统一管理接口API----跨域3. nprogress进度条 三、 vuex模块开发四、TypeNav三级联动组件开发1. 动态展示三级联动数据2. 三级联动 动态背景(1)、方式一:CSS样式(2)、方式二:JS 3. 控制二三级数据隐藏与显示--绑定styl

Matter.js:Web开发者的2D物理引擎

Matter.js:Web开发者的2D物理引擎 前言 在现代网页开发中,交互性和动态效果是提升用户体验的关键因素。 Matter.js,一个专为网页设计的2D物理引擎,为开发者提供了一种简单而强大的方式,来实现复杂的物理交互效果。 无论是模拟重力、碰撞还是复杂的物体运动,Matter.js 都能轻松应对。 本文将带你深入了解 Matter.js ,并提供实际的代码示例,让你一窥其强大功能