前言:本人小白一个,自学初入C#(可能连初入也不算,哈哈哈),目前从事机器视觉方面的工作,写这篇文章主要是记录自己平时遇到的一些问题,不懂的地方大家多多支持啊!------------持续更新中。
学习C#之前,我从事了2年的视觉评估工作,平时主要就是打光测试啊,写写评估报告,拜访客户等简单的工作,用的视觉软件是海康的VM。没有什么技术含量,但是所谓万事开头难,既然入了这一行,那就得珍惜这个机会。后来利用工作之余,慢慢摸索C#,当然现在也在摸索中。
由于不是专业出生,专业知识非常薄弱,要是以后我问出一些弱智问题,望大家不要取笑。
最近我模仿MVS里的例子BasicDemo,准备自己写一个一样的程序,并添加一点其他功能,把目前遇到的一些问题记录下来。
安装的软件有:VS2015,Halcon18,MVS。
这里我不准备用Halcon来调用相机,而是用MVS的DLL来调用相机,Halcon主要用于图像的处理。
找到MVS的例子文件夹,打开BasicDemo例子,具体位置如下,把自己想要的功能复制到自己的程序中(这里我选择直接全部复制,懒得重新写)。
C:\Program Files (x86)\MVS\Development\Samples\C#\BasicDemo
我添加得第一个功能就是改变窗口大小,里面的控件自适应比例,具体代码如下(来源网络):
class ControlsAutosize
{
/*该类包含两个方法:setTag和setControl
* setTag记录当前窗体控件大小
* setControl当窗体大小发生改变时,控件随之等比例改变
*/
public void setTag(Control cons)
{
foreach (Control con in cons.Controls)
{
con.Tag = con.Width + ";" + con.Height + ";" + con.Left + ";" + con.Top + ";" + con.Font.Size;
if (con.Controls.Count > 0)
{
setTag(con);
}
}
}
public void setControls(float newx, float newy, Control cons)
{
//遍历窗体中的控件,重新设置控件的值
foreach (Control con in cons.Controls)
{
//获取控件的Tag属性值,并分割后存储字符串数组
if (con.Tag != null)
{
string[] mytag = con.Tag.ToString().Split(new char[] { ';' });
//根据窗体缩放比例确定控件的值
con.Width = Convert.ToInt32(System.Convert.ToSingle(mytag[0]) * newx);//宽度
con.Height = Convert.ToInt32(System.Convert.ToSingle(mytag[1]) * newy);//高度
con.Left = Convert.ToInt32(System.Convert.ToSingle(mytag[2]) * newx);//左边距
con.Top = Convert.ToInt32(System.Convert.ToSingle(mytag[3]) * newy);//顶边距
Single currentSize = System.Convert.ToSingle(mytag[4]) * newy;//字体大小
con.Font = new System.Drawing.Font(con.Font.Name, currentSize, con.Font.Style, con.Font.Unit);
if (con.Controls.Count > 0)
{
setControls(newx, newy, con);
}
}
}
}
}
然后再直接调用就行了
//变量定义
private float x;
private float y;
public BasicDemo()
{
InitializeComponent();
x = this.Width;
y = this.Height;
ControlsAutosize controlsAutosize = new ControlsAutosize();
controlsAutosize.setTag(this);
}
在窗体的Resize事件下添加如下代码:
private void BasicDemo_Resize(object sender, EventArgs e)
{
float newx = (this.Width) / x;//宽放大倍数
float newy = (this.Height) / y;//高放大倍数
ControlsAutosize controlsAutosize = new ControlsAutosize();
controlsAutosize.setControls(newx, newy, this);
}
原文链接:https://blog.csdn.net/qq_42002500/article/details/107656851
第二个功能为图像显示窗口显示自己想要的图像,并且能够实现平移缩放功能,效果如下:
要实现这个功能,我们要借助Halcon里面的一个控件HWindowControl,添加步骤为工具箱右键–选择项–浏览–找到halcondotnet–完成,最后就可以在工具箱里找到这个控件,可以看到这里其实还有另外一个控件HSmartWindowControl,这个控件也可以用,而且自带平移功能,网上说这个控件不太稳定,但试了一下没什么问题,为了避免以后出现异常,我还是使用的HWindowControl控件。
添加完后,我们再添加一个button,label和contextMenuStrip控件,分别为加载图片,记录鼠标位置,单击鼠标右键弹出菜单栏功能。
为contextMenuStrip1添加适应屏幕和缩放平移两个选项,当单击适应屏幕时,图片将会填充整个图像显示区域,当单击缩放平移时,图片此时才可以进行缩放平移操作,否则将不能进行此项功能,并且把contextMenuStrip1关联到hWindowControl1_ContextMenuStrip属性中。
在适应屏幕ToolStripMenuItem_Click事件添加如下代码:
private void 适应屏幕ToolStripMenuItem_Click(object sender, EventArgs e)
{
HOperatorSet.SetPart(hWindowControl1.HalconWindow, 0, 0, height - 1, widht - 1);
HOperatorSet.ClearWindow(hWindowControl1.HalconWindow);
HOperatorSet.DispObj(ho_Image, hWindowControl1.HalconWindow);
}
在缩放平移ToolStripMenuItem_Click事件添加如下代码:
private void 缩放平移ToolStripMenuItem_Click(object sender, EventArgs e)
{
IsMove = true;
}
在bnLaodPicture_Click事件添加如下代码:
//变量定义
double RowDown;//记录鼠标左键点击图片时的坐标
double ColDown;//记录鼠标左键点击图片时的坐标
bool IsMove = false;//判断是否需要平移缩放
bool MoveFlag;//是否在移动
HObject ho_Image;//图片变量
HTuple widht, height;//图片的长和宽
string path;//文件路径
private void bnLaodPicture_Click(object sender, EventArgs e)
{
HOperatorSet.GenEmptyObj(out ho_Image);
ho_Image.Dispose();
OpenFileDialog dialog = new OpenFileDialog();
dialog.Multiselect = false; //是否允许多选
dialog.Title = "请选择图片"; //窗口title
dialog.Filter = "*.All|*.*|*.png|*.png*|*.jpg|*.jpg*"; //可选择的文件类型
if (dialog.ShowDialog() == System.Windows.Forms.DialogResult.OK)
{
path = dialog.FileName; //获取文件路径
HOperatorSet.ReadImage(out ho_Image, path);
HOperatorSet.GetImageSize(ho_Image, out widht, out height);
HOperatorSet.SetPart(hWindowControl1.HalconWindow, 0, 0, height - 1, widht - 1);
hWindowControl1.HalconWindow.DispObj(ho_Image);
}
}
在hWindowControl1_HMouseDown事件添加如下代码,这里先判断是否点击菜单栏的缩放平移,再判断是否加载过图片:
private void hWindowControl1_HMouseDown(object sender, HMouseEventArgs e)
{
try
{
if (IsMove)
{
if (ho_Image != null)
{
//记录按键按下的坐标点
RowDown = e.Y;
ColDown = e.X;
MoveFlag = true;
}
else
{
MessageBox.Show("请先加载图片!", "提示");
}
}
}
catch (HalconException HDevExpDefaultException)
{
throw HDevExpDefaultException;
}
}
在hWindowControl1_HMouseMove事件添加如下代码,这里是当鼠标移动到图像显示区域,记录鼠标的当前位置并算出偏移量,实现图片的平移,平移之前判断鼠标左键是否按下以及MoveFlag是否为true,否则不进行平移;
private void hWindowControl1_HMouseMove(object sender, HMouseEventArgs e)
{
HTuple row1, col1, row2, col2;
label4.Text = "R:" + e.Y.ToString("f1") + " C:" + e.X.ToString("f1");
try
{
if (MoveFlag && e.Button == MouseButtons.Left)
{
double RowOffSet = RowDown - e.Y;
double ColumnOffSet = ColDown - e.X;
HOperatorSet.ClearWindow(hWindowControl1.HalconWindow);
HOperatorSet.GetPart(hWindowControl1.HalconWindow, out row1, out col1, out row2, out col2);
HOperatorSet.SetPart(hWindowControl1.HalconWindow, RowOffSet + row1, ColumnOffSet + col1, RowOffSet + row2, ColumnOffSet + col2);
HOperatorSet.SetPart(hWindowControl1.HalconWindow, RowOffSet + row1, ColumnOffSet + col1, RowOffSet + row2, ColumnOffSet + col2);
HOperatorSet.DispObj(ho_Image, hWindowControl1.HalconWindow);
}
}
catch (HalconException HDevExpDefaultException)
{
throw HDevExpDefaultException;
}
}
在hWindowControl1_HMouseUp事件添加如下代码,这里是当鼠标左键松开后,判定移动结束:
private void hWindowControl1_HMouseUp(object sender, HMouseEventArgs e)
{
MoveFlag = false;
}
在hWindowControl1_HMouseWheel事件添加如下代码,这里是监听鼠标滚轮:
private void hWindowControl1_HMouseWheel(object sender, HMouseEventArgs e)
{
if (IsMove)
{
HTuple Zoom, Row, Col, Button;
HTuple Row0, Column0, Row00, Column00, Ht, Wt, r1, c1, r2, c2;
if (e.Delta > 0)
{
Zoom = 1.5;
}
else
{
Zoom = 0.5;
}
HOperatorSet.GetMposition(hWindowControl1.HalconWindow, out Row, out Col, out Button);
HOperatorSet.GetPart(hWindowControl1.HalconWindow, out Row0, out Column0, out Row00, out Column00);
Ht = Row00 - Row0;
Wt = Column00 - Column0;
if (Ht * Wt < 32000 * 32000 || Zoom == 1.5)//普通版halcon能处理的图像最大尺寸是32K*32K。如果无限缩小原图像,导致显示的图像超出限制,则会造成程序崩溃
{
r1 = (Row0 + ((1 - (1.0 / Zoom)) * (Row - Row0)));
c1 = (Column0 + ((1 - (1.0 / Zoom)) * (Col - Column0)));
r2 = r1 + (Ht / Zoom);
c2 = c1 + (Wt / Zoom);
HOperatorSet.SetPart(hWindowControl1.HalconWindow, r1, c1, r2, c2);
HOperatorSet.ClearWindow(hWindowControl1.HalconWindow);
HOperatorSet.DispObj(ho_Image, hWindowControl1.HalconWindow);
}
}
}
至此,图片的平移缩放功能就大功告成了,以上有什么不足之处请谅解,毕竟是小白,如果您有更好的方法,欢迎评论。
最后附上源码:
https://download.csdn.net/download/qq_45072282/85069439