当前位置: 首页 > news >正文

Halcon检测项目

对该图像中圆的部分进行检测

最终效果为

*******************************************Halcon部分的代码**********************************************

*加载文件夹中的图像
list_files ('F:/halcon/素材/img', 'files', ImageFiles)

*获取第一张图像用来制作模板
read_image (Image, ImageFiles[0])

*获取图像大小
get_image_size (Image, Width, Height)

dev_open_window (0, 0, Width/4, Height/4, 'black', WindowHandle)

*创建测量模型
create_metrology_model (MetrologyHandle)
*设置测量模型的大小
set_metrology_model_image_size (MetrologyHandle, Width, Height)

*定义圆的半径:注意:这个值是可变的
NewRadius:=324


*也可以配置其他的参数,例如测量对象的宽度允许范围
CirCleRadiusToleance:=100

*对多张图像进行测量
for Index := 0 to |ImageFiles|-1 by 1
    read_image (ResultImage, ImageFiles[Index])
    *阈值分割,挑选出来配件部分
    threshold (ResultImage, ResultRegion, 3,60)
    *连通
    connection (ResultRegion, ResuleConnectedRegions)
    *特征提取
    select_shape (ResuleConnectedRegions, ResultSelectedRegions1, ['area','roundness'], 'and', [250000,0.9163], [310000,1])
    *获取
    area_center (ResultSelectedRegions1, ResultArea, ResultRow, ResultColumn)
    *设置输出的颜色
    dev_set_color ('red')
    dev_set_draw ('margin')
    dev_display (ResultImage)
    
    *生成圆
    gen_circle (ResultCircle, ResultRow, ResultColumn, NewRadius)
    *把圆添加到模型中
    add_metrology_object_circle_measure (MetrologyHandle, ResultRow, ResultColumn, NewRadius, CirCleRadiusToleance, 5, 1.5, 30, ['measure_transition','min_score'], ['all',0.4], MetrologyCircleIndice)
    *测量并拟合集合形状
    apply_metrology_model (ResultImage, MetrologyHandle)
    *获取测量模型中的测量轮廓,方便后期显示
    get_metrology_object_result_contour (ResuleContour, MetrologyHandle, 'all', 'all', 1.5)
    *在轮廓基础上获得此次测量的结果:第二个参数是每个图像的索引
    get_metrology_object_result (MetrologyHandle, MetrologyCircleIndice, 'all', 'result_type', 'radius', CirCleRadiusResult)
    
    *显示图像
    dev_display (ResultImage)
    *显示测量的轮廓
    dev_display (ResuleContour)
    -
    *设置文字的位置
    set_tposition (WindowHandle, 0, 0)
    *在指定的位置显示信息
    write_string (WindowHandle, '圆的半径:'+CirCleRadiusResult)
    stop ()
endfor
*清除测量模型
clear_metrology_model (MetrologyHandle)

*******************************************Winform部分代码***********************************************

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.IO;
using System.Linq;
using System.Security.AccessControl;
using System.Text;
using System.Threading;
using System.Threading.Tasks;
using System.Windows.Forms;
using HalconDotNet;namespace Halcon检测项目
{public partial class Form1 : Form{HObject image;HTuple windowID;Thread t1;//优化了halcon中的数组HObject[] ImageArr = new HObject[8];bool t1_Stop = false;//线程的状态private const string SAVE_ROOT = "SaveImages";  // 根保存目录private const string FOLDER_OK = "OK";          // OK子目录private const string FOLDER_NG = "NG";          // NG子目录public Form1(){InitializeComponent();}#region 加载资源private void LoadBateImage(){for (int i = 0; i < 8; i++){HOperatorSet.ReadImage(out ImageArr[i], $"img/{i}.bmp");}}#endregion#region 加载窗体private void CreateHalconWindow(){HTuple winforms = this.pictureBox1.Handle;HOperatorSet.SetWindowAttr("background_color", "red");HOperatorSet.OpenWindow(0, 0, this.pictureBox1.Width, this.pictureBox1.Height, winforms, "", "", out windowID);}#endregion#region 加载默认图片private void LoadImage(){HOperatorSet.ReadImage(out image, "img/0.bmp");HOperatorSet.GetImageSize(image, out HTuple Width, out HTuple Height);HOperatorSet.SetColor(windowID, "red");HOperatorSet.SetPart(windowID, 0, 0, Height, Width);HOperatorSet.DispObj(image, windowID);}#endregion#region 加载配置环境//加载配置环境private void Form1_Load(object sender, EventArgs e){//读图LoadBateImage();//加载窗体CreateHalconWindow();//加载默认图片LoadImage();t1 = new Thread(new ThreadStart(PlayThread));}#endregion#region 开始测量private void button1_Click(object sender, EventArgs e){//在分线程中加载图像//线程未开启,开启线程if (t1.ThreadState == ThreadState.Unstarted){t1.Start();}//如果线程停止或者线程为空if (t1.ThreadState == ThreadState.Stopped || t1.ThreadState == ThreadState.Aborted){//开启线程测量t1 = new Thread(new ThreadStart(PlayThread));t1.Start();}}private void PlayThread(){//测量,存储,一起执行//1.先获得测量半径int i = 0;t1_Stop = false;HTuple Width = null, Height = null;while (!t1_Stop){HOperatorSet.DispObj(ImageArr[i], windowID);HOperatorSet.GetImageSize(ImageArr[i], out Width, out Height);HOperatorSet.SetPart(windowID, 0, 0, Height, Height);//渲染窗体double CriRead = ImageMeasure(ImageArr[i]);//2.处理结果ListViewItem item = new ListViewItem(i.ToString());if (CriRead>311&&CriRead<313){item.SubItems.Add(CriRead.ToString("F2"));item.SubItems.Add("OK");SaveImageToFolder(ImageArr[i], FOLDER_OK, i);  // 保存OK图片}else{item.SubItems.Add(CriRead.ToString("F2"));item.SubItems.Add("NG");SaveImageToFolder(ImageArr[i], FOLDER_NG, i);  // 保存NG图片}listView1.Items.Add(item);Thread.Sleep(1000);i++;if (i > 7){i = 0;}}}//获取模型测量的结果private double ImageMeasure(HObject ho_ResultImage){HObject ho_Image, ho_ResultRegion = null;HObject ho_ResuleConnectedRegions = null, ho_ResultSelectedRegions1 = null;HObject ho_ResultCircle = null, ho_ResuleContour = null;// Local control variables HTuple hv_ImageFiles = null, hv_Width = null;HTuple hv_Height = null, hv_WindowHandle = null, hv_MetrologyHandle = null;HTuple hv_NewRadius = null, hv_CirCleRadiusToleance = null;HTuple hv_Index = null, hv_ResultArea = new HTuple(), hv_ResultRow = new HTuple();HTuple hv_ResultColumn = new HTuple(), hv_MetrologyCircleIndice = new HTuple();HTuple hv_CirCleRadiusResult = new HTuple();HOperatorSet.GenEmptyObj(out ho_Image);HOperatorSet.GenEmptyObj(out ho_ResultRegion);HOperatorSet.GenEmptyObj(out ho_ResuleConnectedRegions);HOperatorSet.GenEmptyObj(out ho_ResultSelectedRegions1);HOperatorSet.GenEmptyObj(out ho_ResultCircle);HOperatorSet.GenEmptyObj(out ho_ResuleContour);HOperatorSet.GetImageSize(ho_ResultImage, out hv_Width, out hv_Height);//创建测量模型HOperatorSet.CreateMetrologyModel(out hv_MetrologyHandle);//设置测量模型的大小HOperatorSet.SetMetrologyModelImageSize(hv_MetrologyHandle, hv_Width, hv_Height);//定义圆的半径:注意:这个值是可变的hv_NewRadius = 324;//也可以配置其他的参数,例如测量对象的宽度允许范围hv_CirCleRadiusToleance = 100;//ho_ResultImage.Dispose();//HOperatorSet.ReadImage(out , hv_ImageFiles.TupleSelect(hv_Index));//阈值分割,挑选出来配件部分ho_ResultRegion.Dispose();HOperatorSet.Threshold(ho_ResultImage, out ho_ResultRegion, 3, 60);//连通ho_ResuleConnectedRegions.Dispose();HOperatorSet.Connection(ho_ResultRegion, out ho_ResuleConnectedRegions);//特征提取ho_ResultSelectedRegions1.Dispose();HOperatorSet.SelectShape(ho_ResuleConnectedRegions, out ho_ResultSelectedRegions1,(new HTuple("area")).TupleConcat("roundness"), "and", (new HTuple(250000)).TupleConcat(0.9163), (new HTuple(310000)).TupleConcat(1));//获取HOperatorSet.AreaCenter(ho_ResultSelectedRegions1, out hv_ResultArea, out hv_ResultRow,out hv_ResultColumn);HOperatorSet.SetColor(windowID, "red");HOperatorSet.SetDraw(windowID, "margin");HOperatorSet.DispObj(ho_ResultImage, windowID);//生成圆ho_ResultCircle.Dispose();HOperatorSet.GenCircle(out ho_ResultCircle, hv_ResultRow, hv_ResultColumn,hv_NewRadius);//把圆添加到模型中HOperatorSet.AddMetrologyObjectCircleMeasure(hv_MetrologyHandle, hv_ResultRow,hv_ResultColumn, hv_NewRadius, hv_CirCleRadiusToleance, 5, 1.5, 30, (new HTuple("measure_transition")).TupleConcat("min_score"), (new HTuple("all")).TupleConcat(0.4), out hv_MetrologyCircleIndice);//测量并拟合集合形状HOperatorSet.ApplyMetrologyModel(ho_ResultImage, hv_MetrologyHandle);//获取测量模型中的测量轮廓,方便后期显示ho_ResuleContour.Dispose();HOperatorSet.GetMetrologyObjectResultContour(out ho_ResuleContour, hv_MetrologyHandle,"all", "all", 1.5);//在轮廓基础上获得此次测量的结果:第二个参数是每个图像的索引HOperatorSet.GetMetrologyObjectResult(hv_MetrologyHandle, hv_MetrologyCircleIndice,"all", "result_type", "radius", out hv_CirCleRadiusResult);HOperatorSet.DispObj(ho_ResultImage, windowID);HOperatorSet.DispObj(ho_ResuleContour, windowID);//设置文字的位置HOperatorSet.SetTposition(windowID, 0, 0);//在指定的位置显示信息HOperatorSet.WriteString(windowID, "圆的半径:" + hv_CirCleRadiusResult);HOperatorSet.ClearMetrologyModel(hv_MetrologyHandle);//释放资源ho_Image.Dispose();ho_ResultRegion.Dispose();ho_ResuleConnectedRegions.Dispose();ho_ResultSelectedRegions1.Dispose();ho_ResultCircle.Dispose();ho_ResuleContour.Dispose();return hv_CirCleRadiusResult;}#endregion#region 保存图片的方法private void SaveImageToFolder(HObject image, string folderName, int index){try{// 构建完整保存路径string saveRootPath = Path.Combine(Application.StartupPath, SAVE_ROOT);string targetFolder = Path.Combine(saveRootPath, folderName);// 创建目录(如果不存在)if (!Directory.Exists(targetFolder)){Directory.CreateDirectory(targetFolder);}// **文件名后缀改为 .bmp**string fileName = $"Image{index}.bmp";string savePath = Path.Combine(targetFolder, fileName);// **Halcon保存格式参数改为 "bmp"**HOperatorSet.WriteImage(image, "bmp", 0, savePath);  // BMP格式不需要质量参数(第三个参数固定为0)// 可选:输出保存成功信息Console.WriteLine($"BMP图片已保存到:{savePath}");}catch (HOperatorException ex){MessageBox.Show($"Halcon图片保存错误:{ex.Message}", "错误",MessageBoxButtons.OK, MessageBoxIcon.Error);}catch (Exception ex){MessageBox.Show($"保存失败:{ex.Message}", "错误",MessageBoxButtons.OK, MessageBoxIcon.Error);}}#endregion#region 停止测量private void button2_Click(object sender, EventArgs e){t1_Stop=true;}#endregion#region 关闭窗体private void button4_Click(object sender, EventArgs e){this.Close();}#endregion}}


 

相关文章:

  • 深入浅出之STL源码分析3_类模版实例化与特化
  • Shell 脚本编程1(常用命令+概述)
  • 金丝猴食品:智能中枢AI-COP构建全链路数智化运营体系
  • C++ 异常捕获 try 和 __try的区别笔记
  • Python环境搭建指南
  • 慈缘基金会“蝴蝶飞”助西藏女孩白玛卓嘎“折翼重生”
  • 基于STM32的居家环境监测报警Proteus仿真+程序设计+设计报告+讲解视频
  • smbd:快速拉取服務端SMB共享文件脚本工具
  • SAM详解3.2(关于2和3的题)
  • 黑马k8s(二)
  • 子串简写(JAVA)一维前缀和, 蓝桥杯
  • 学习黑客5 分钟深入浅出理解cron [特殊字符]
  • 基于阿伦尼斯模型的电池寿命预测:原理、应用与挑战
  • 【智能指针】
  • SD06_前后端分离项目部署流程(采用Nginx)
  • SAP Commerce(Hybris)开发实战(一)
  • linux-----------Ext系列⽂件系统(上)
  • 进阶 DFS 学习笔记
  • 链表头插法的优化补充、尾插法完结!
  • DNS负载均衡和CDN的区别
  • 多省市已开展现房销售试点,去年全国现房销售面积占比超30%
  • 美众议院通过法案将“墨西哥湾”更名为“美国湾”
  • 警惕“全网最低价”等宣传,市监总局和中消协发布直播消费提示
  • 重庆党政代表团在沪考察,陈吉宁龚正与袁家军胡衡华共商两地深化合作工作
  • 加力、攻坚、借力、问效,上海为优化营商环境推出增量举措
  • 体坛联播|双杀阿森纳,巴黎晋级欧冠决赛对阵国际米兰