C#关于HWindowControl实现一些便捷功能——(缩放与拖动图像)

一、关于Hwindow窗体显示的part二、以鼠标为中心的缩放三、以鼠标拖动移动图片

一、关于Hwindow窗体显示的part

首先 HWindowControl 控件的尺寸是固定的,当我们在这个固定的尺寸中,相对原来显示的一幅完整的图像,现在只显示图像的一部分,即可达到放大效果。 即想放大时,我们便缩小 ImagePart ;想缩小时,我们便放大 ImagePart 。 例如:一幅 800600 的图像, 一开始我们将 ImagePart 设置为:左上角 (0, 0) ,右下角(800600) ; 现在我们将其设置为 :左上角(0, 0) ,右下角(400, 300) , 之前用整幅图像去填充 HWindowControl 控件,现在用半幅图像去填充它,显然这部分图像就会被放大。放大的倍数是 2 。 再有 现在我们将其设置为 :左上角(100, 100) ,右下角(500, 400) , 则就相当于拖动图片向左上角移动。 而我们需要设置part需要的参数就是矩形的左上角与右下角的坐标值,或者左上角以及长宽值。

二、以鼠标为中心的缩放

现在可以缩放了,再看看如何实现以鼠标的当前位置作为中心,进行缩放? 要保证鼠标中心位置,即保证鼠标所指的图像相对位置不变即可。 如图,黑色框为原本图像,当 我们要放大图像时(将原图像变小再按比例填充至HWindowControl 窗口内),所以应该是变换为红色的; 我们要缩小图像时(将原图像变大再按比例压缩至HWindowControl 窗口内),所以应该是变换为蓝色的。 红色点为鼠标在HWindowControl 窗体控件中的坐标。

我们可获取原始图像显示时的part为LUPointX,LUPointY; 获取的鼠标的坐标为MouseX,MouseY; 放大比例Zoom为0.5; 则有红色矩形的左上角坐标为:

LUPointY2 = (MouseY - (Zoom * (MouseY - LUPointY)));

LUPointX2 = (MouseX - (Zoom * (MouseX - LUPointX)));

此处注意图像坐标是从上向下,从左至右递增的。 又有右下角坐标:

//Ht,Wt为原图像的右下角与左上角计算出来的长宽。

RBPointY2 = LUPointY2 + (Ht * Zoom);

RBPointX2 = LUPointX2 + (Wt * Zoom);

到此就可以通过part属性来设置显示区域啦。 全代码如下:

需要把下面的事件绑定到HWindowControl 的HMouseWheel上

public void Scale(object sender, HMouseEventArgs e)

{

double Zoom = 0.5;//缩放比例

HTuple MouseX, MouseY;//鼠标位于图片窗体的坐标

//左上角与右下角坐标

HTuple LUPointY, LUPointX, RBPointY, RBPointX;

HTuple LUPointY2, LUPointX2, RBPointY2, RBPointX2;

//当前显示的界面大小

HTuple Ht, Wt;

HTuple WindowID = hWindowControl1.HalconWindow;

MouseX = e.X;

MouseY = e.Y;

Zoom = e.Delta > 0 ? Zoom : (1 + Zoom);

HOperatorSet.GetPart(WindowID, out LUPointY, out LUPointX, out RBPointY, out RBPointX);

Ht = RBPointY - LUPointY;

Wt = RBPointX - LUPointX;

if ((Ht * Wt) < 32000 * 32000)

{

LUPointY2 = (MouseY - (Zoom * (MouseY - LUPointY)));

LUPointX2 = (MouseX - (Zoom * (MouseX - LUPointX)));

RBPointY2 = LUPointY2 + (Ht * Zoom);

RBPointX2 = LUPointX2 + (Wt * Zoom);

HOperatorSet.SetPart(WindowID, LUPointY2, LUPointX2, RBPointY2, RBPointX2);

hWindowControl.HalconWindow.ClearWindow();

hWindowControl.HalconWindow.DispObj(hImage);

}

}

三、以鼠标拖动移动图片

移动比较简单, 首先我们记录下左键按下时的鼠标坐标位置(startPointX,startPointY), 当鼠标左键释放时的坐标位置(endPointX,endPointY) 可以获得x方向与y方向的插值move_c,move_r; 则可得到: 移动后左上角坐标为:(originalImageUL_c + move_c , originalImageUL_r + move_r) 移动后右下角坐标为:(originalImageDR_c + move_c , originalImageDR_r + move_r)

全代码如下:

Point StartPoint = new Point();

Point EndPoint = new Point();

private void HMouseDown(object sender, HMouseEventArgs e)

{

if (e.Button == MouseButtons.Left)

{

StartPoint.X = Convert.ToInt32(e.X);

StartPoint.Y = Convert.ToInt32(e.Y);

hWindowControl1.HMouseMove += HMouseMove;

}

}

private void HMouseUp(object sender, HMouseEventArgs e)

{

hWindowControl1.HMouseMove -= HMouseMove;

}

private void HMouseMove(object sender, HMouseEventArgs e)

{

EndPoint.X = Convert.ToInt32(e.X);

EndPoint.Y = Convert.ToInt32(e.Y);

HWindow_MoveImage(StartPoint, EndPoint, hWindowControl1, hImage);

}

public void HWindow_MoveImage(Point startPoint, Point endPoint, HWindowControl hWindow, HImage hImage)

{

int originalImageUL_r;

int originalImageUL_c;

int originalImageDR_r;

int originalImageDR_c;

hWindow.HalconWindow.GetPart(out originalImageUL_r, out originalImageUL_c, out originalImageDR_r, out originalImageDR_c);

int move_r = startPoint.Y - endPoint.Y;

int move_c = startPoint.X - endPoint.X;

hWindow.HalconWindow.SetPart(originalImageUL_r + move_r, originalImageUL_c + move_c, originalImageDR_r + move_r, originalImageDR_c + move_c);

hWindow.HalconWindow.ClearWindow();

hWindow.HalconWindow.DispObj(hImage);

}

源代码在快速移动的过程中,由于高刷新会造成图像闪烁的问题。将HWindow_MoveImage函数中的hWindow.HalconWindow.ClearWindow();函数前后做如下更改,则可以有效的解决闪烁问题。

HOperatorSet.SetSystem("flush_graphic", "false");

hWindow.HalconWindow.ClearWindow();

HOperatorSet.SetSystem("flush_graphic", "true");

好文链接

评论可见,请评论后查看内容,谢谢!!!
 您阅读本篇文章共花了: