为了更好地去学习WPF+Halcon,我决定去报个班学一下。原因无非是想换个工作。相关的教学视频来源于下方的Up主的提供的教程。这里只做笔记分享,想要源码或者教学视频可以和他联系一下。
Halcon官方的代码很多都是基于String的类型判断,我们要对Halcon的代码进行一步简单的封装。
让我们的WPF主程序依赖于HalconExtension类库
添加Nuget
原来的方法
// 显示绘制图案
HalconWindow.HalconWindow.AttachDrawingObjectToWindow(rect);
// 去除绘制图案
//HalconWindow.HalconWindow.DetachDrawingObjectFromWindow(rect);
rect.OnDrag(new HDrawingObject.HDrawingObjectCallbackClass((id, window, type) =>
{
var hv_type = id.GetDrawingObjectParams("type");
var row1 = id.GetDrawingObjectParams("row1");
var row2 = id.GetDrawingObjectParams("row2");
var column1 = id.GetDrawingObjectParams("column1");
var column2 = id.GetDrawingObjectParams("column2");
//打印坐标
NLogHelper.Debug($"拖动事件: {hv_type}:{row1} {column1} {row2} {column2} ");
}));
现在的方法:
using HalconDotNet;
using Newtonsoft.Json;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace HalconExtension.Models
{
/// <summary>
/// 矩形封装
/// </summary>
public class HRectangleObj
{
public HTuple HType { get; private set; }
public HTuple Row1 { get; private set; }
public HTuple Row2 { get; private set; }
public HTuple Column1 { get; private set; }
public HTuple Column2 { get; private set; }
public HDrawingObject DrawingObject { get; set; }
/// <summary>
/// HS组件主题
/// </summary>
public HSmartWindowControlWPF WindowControlWPF { get; set; }
public Action<HRectangleObj> RefleshCallBack { get; set; }
/// <summary>
/// 初始化构造函数
/// </summary>
/// <param name="windowControlWPF"></param>
/// <param name="row1"></param>
/// <param name="column1"></param>
/// <param name="row2"></param>
/// <param name="column2"></param>
public HRectangleObj(HSmartWindowControlWPF windowControlWPF,HTuple row1,HTuple column1,HTuple row2,HTuple column2)
{
WindowControlWPF = windowControlWPF;
Row1 = row1;
Column1 = column1;
Row2 = row2;
Column2 = column2;
DrawingObject = HDrawingObject.CreateDrawingObject(HDrawingObject.HDrawingObjectType.RECTANGLE1,Row1,Column1,Row2,Column2);
}
/// <summary>
/// 默认构造函数
/// </summary>
/// <param name="windowControl"></param>
public HRectangleObj(HSmartWindowControlWPF windowControl)
{
WindowControlWPF = windowControl;
Row1 = 0;
Column1 = 0;
Row2 = 100;
Column2 = 100;
DrawingObject = HDrawingObject.CreateDrawingObject(HDrawingObject.HDrawingObjectType.RECTANGLE1, Row1, Column1, Row2, Column2);
//添加更新事件
DrawingObject.OnDrag(Reflash);
DrawingObject.OnResize(Reflash);
}
/// <summary>
/// 显示图像
/// </summary>
public void Show()
{
WindowControlWPF.HalconWindow.AttachDrawingObjectToWindow(DrawingObject);
}
/// <summary>
/// 分离图像
/// </summary>
public void Close()
{
WindowControlWPF.HalconWindow.DetachDrawingObjectFromWindow(DrawingObject);
}
/// <summary>
/// 序列化输出
/// </summary>
/// <returns></returns>
public override string ToString()
{
return JsonConvert.SerializeObject(new
{
type = HType.ToString(),
row1 = TwoDecimalPlaces(Row1),
column1 = TwoDecimalPlaces(Column1),
row2 = TwoDecimalPlaces(Row2),
column2 = TwoDecimalPlaces(Column2)
});
}
public void Reflash(HDrawingObject drawid, HWindow window, string type)
{
HType = drawid.GetDrawingObjectParams("type");
Row1 = drawid.GetDrawingObjectParams("row1");
Row2 = drawid.GetDrawingObjectParams("row2");
Column1 = drawid.GetDrawingObjectParams("column1");
Column2 = drawid.GetDrawingObjectParams("column2");
//将本身回调
RefleshCallBack(this);
}
/// <summary>
/// 保留两位小数
/// </summary>
/// <returns></returns>
private string TwoDecimalPlaces(HTuple value)
{
return decimal.Round(decimal.Parse(value.ToString()), 2).ToString();
}
}
}
运行代码
InitRectangleBtn = new RelayCommand(() =>
{
MsgHelper.Info("生成矩形");
//rect = HDrawingObject.CreateDrawingObject(HDrawingObject.HDrawingObjectType.RECTANGLE1, 100, 200, 300, 400);
显示绘制图案
//HalconWindow.HalconWindow.AttachDrawingObjectToWindow(rect);
去除绘制图案
HalconWindow.HalconWindow.DetachDrawingObjectFromWindow(rect);
//rect.OnDrag(new HDrawingObject.HDrawingObjectCallbackClass((id, window, type) =>
//{
// var hv_type = id.GetDrawingObjectParams("type");
// var row1 = id.GetDrawingObjectParams("row1");
// var row2 = id.GetDrawingObjectParams("row2");
// var column1 = id.GetDrawingObjectParams("column1");
// var column2 = id.GetDrawingObjectParams("column2");
// //打印坐标
// NLogHelper.Debug($"拖动事件: {hv_type}:{row1} {column1} {row2} {column2} ");
//}));
//初始化对象
RectangleObj = new HRectangleObj(HalconWindow);
//刷新回调里面进行打印
RectangleObj.RefleshCallBack = (obj) =>
{
NLogHelper.Debug(obj.ToString());
};
//显示对象
RectangleObj.Show();
});
抽象就是abstract,简单来说就是认为所有的基类都有相同的函数,比如ToString,Show,Close等。抽象更利于我们的代码的规划。
其实很多语法是程序自己给自己加限制,就是强迫自己按照某个逻辑进行代码开发。典型的例子就是JS转TS。这里不展开说明
using HalconDotNet;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace HalconExtension.Models
{
public abstract class HObjBase
{
/// <summary>
/// HS组件主题
/// </summary>
public HSmartWindowControlWPF WindowControlWPF { get; set; }
public HDrawingObject DrawingObject { get; set; }
public HTuple HType { get; private set; }
public HObjBase(HSmartWindowControlWPF windowControlWPF)
{
WindowControlWPF = windowControlWPF;
}
/// <summary>
/// 显示图像
/// </summary>
public void Show()
{
WindowControlWPF.HalconWindow.AttachDrawingObjectToWindow(DrawingObject);
}
/// <summary>
/// 分离图像
/// </summary>
public void Close()
{
WindowControlWPF.HalconWindow.DetachDrawingObjectFromWindow(DrawingObject);
}
/// <summary>
/// 保留两位小数
/// </summary>
/// <returns></returns>
public string TwoDecimalPlaces(HTuple value)
{
return decimal.Round(decimal.Parse(value.ToString()), 2).ToString();
}
/// <summary>
/// 序列化
/// </summary>
/// <returns></returns>
public abstract override string ToString();
/// <summary>
/// 刷新事件
/// </summary>
public abstract void Reflash(HDrawingObject drawid, HWindow window, string type);
}
}
using HalconDotNet;
using Newtonsoft.Json;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace HalconExtension.Models
{
/// <summary>
/// 矩形封装
/// </summary>
public class HRectangleObj : HObjBase
{
public HTuple HType { get; private set; }
public HTuple Row1 { get; private set; }
public HTuple Row2 { get; private set; }
public HTuple Column1 { get; private set; }
public HTuple Column2 { get; private set; }
/// <summary>
/// 刷新回调
/// </summary>
public Action<HRectangleObj> RefleshCallBack { get; set; }
/// <summary>
/// 初始化构造函数
/// </summary>
/// <param name="windowControlWPF"></param>
/// <param name="row1"></param>
/// <param name="column1"></param>
/// <param name="row2"></param>
/// <param name="column2"></param>
public HRectangleObj(HSmartWindowControlWPF windowControlWPF, HTuple row1, HTuple column1, HTuple row2, HTuple column2) : base(windowControlWPF)
{
//WindowControlWPF = windowControlWPF;
Row1 = row1;
Column1 = column1;
Row2 = row2;
Column2 = column2;
DrawingObject = HDrawingObject.CreateDrawingObject(HDrawingObject.HDrawingObjectType.RECTANGLE1, Row1, Column1, Row2, Column2);
//添加更新事件
DrawingObject.OnDrag(Reflash);
DrawingObject.OnResize(Reflash);
}
/// <summary>
/// 默认构造函数
/// </summary>
/// <param name="windowControl"></param>
public HRectangleObj(HSmartWindowControlWPF windowControl) : base(windowControl)
{
Row1 = 0;
Column1 = 0;
Row2 = 100;
Column2 = 100;
DrawingObject = HDrawingObject.CreateDrawingObject(HDrawingObject.HDrawingObjectType.RECTANGLE1, Row1, Column1, Row2, Column2);
//添加更新事件
DrawingObject.OnDrag(Reflash);
DrawingObject.OnResize(Reflash);
}
/// <summary>
/// 序列化输出
/// </summary>
/// <returns></returns>
public override string ToString()
{
return JsonConvert.SerializeObject(new
{
type = HType.ToString(),
row1 = TwoDecimalPlaces(Row1),
column1 = TwoDecimalPlaces(Column1),
row2 = TwoDecimalPlaces(Row2),
column2 = TwoDecimalPlaces(Column2)
});
}
public override void Reflash(HDrawingObject drawid, HWindow window, string type)
{
HType = drawid.GetDrawingObjectParams("type");
Row1 = drawid.GetDrawingObjectParams("row1");
Row2 = drawid.GetDrawingObjectParams("row2");
Column1 = drawid.GetDrawingObjectParams("column1");
Column2 = drawid.GetDrawingObjectParams("column2");
//将本身回调
RefleshCallBack(this);
}
}
}
如果集成抽象的对象只有一个,那么抽象就没有意义了。抽象一定是多个类继承才有使用的实际意义。
using HalconDotNet;
using Newtonsoft.Json;
using System;
using System.Collections.Generic;
using System.Data.Common;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace HalconExtension.Models
{
public class HCircleObj : HObjBase
{
public HTuple Row { get; set; }
public HTuple Column { get; set; }
public HTuple Radius { get; set; }
public HTuple HType { get; private set; }
/// <summary>
/// 刷新回调
/// </summary>
public Action<HCircleObj> RefleshCallBack { get; set; }
public HCircleObj(HSmartWindowControlWPF windowControlWPF, HTuple row, HTuple col, HTuple radius):base(windowControlWPF)
{
Row = row;
Column = col;
Radius = radius;
DrawingObject = HDrawingObject.CreateDrawingObject(HDrawingObject.HDrawingObjectType.CIRCLE, Row, Column, Radius);
//添加更新事件
DrawingObject.OnDrag(Reflash);
DrawingObject.OnResize(Reflash);
}
public HCircleObj(HSmartWindowControlWPF windowControlWPF) : this(windowControlWPF,64,64,64)
{
}
public override void Reflash(HDrawingObject drawid, HWindow window, string type)
{
HType = drawid.GetDrawingObjectParams("type");
Row = drawid.GetDrawingObjectParams("row");
Column = drawid.GetDrawingObjectParams("column");
Radius = drawid.GetDrawingObjectParams("radius");
//将本身回调
RefleshCallBack(this);
}
public override string ToString()
{
return JsonConvert.SerializeObject(new
{
type = HType.ToString(),
row = TwoDecimalPlaces(Row),
column = TwoDecimalPlaces(Column),
radius = TwoDecimalPlaces(Radius),
});
}
}
}