您好,欢迎访问一九零五行业门户网

C#开发实例-订制屏幕截图工具(四)基本截图功能实现代码

实现原理基本截图的功能主要靠响应主窗体的鼠标按下、鼠标移动、鼠标抬起几个事件的功能来实现的。截取的图片区域使用“label”组件来显示,需要重新实现“label”组件的“paint”方法。
左键单击开始截图,右键单击取消截图,双击鼠标左键完成截图,将截取的图片保存到windows剪贴板中。
添加“label”组件工具箱》公共组件》双击“label”组件,修改组件属性:
name=lbl_cutimage,
autosize=false,
backcolor=transparent,
text = “”
“form1_load”事件添加代码:
this.lbl_cutimage.hide();
定义截图功能依赖的基本变量 #region 截图基本变量 /// <summary> /// 用于判断是否已经开始截图,控制信息框是否显示。 /// </summary> private bool iscuting; /// <summary> /// 鼠标按下的点 /// </summary> private point beginpoint; /// <summary> /// 最终确定的绘图基点 /// </summary> private point endpoint; /// <summary> /// 用于记录截图显示区域的大小(包括调整块的区域,调整区域边框宽度2px) /// </summary> private rectangle cutimagerect = new rectangle(0, 0, 5, 5); #endregion
定义枚举类型:更新ui的模式 /// <summary> /// 更新ui的模式,用于标记哪些需要显示,哪些需要隐藏; /// </summary> [flagsattribute] public enum updateuimode : uint { //值得注意的是,如果要使用组合值,那么就不能用连接的数字表示,必须是几何级增长! none = 0, showtextpro = 1, showpenstyle = 2, showtoolbox = 4, showinfobox = 8, showzoombox = 16, showcutimage = 32, hidetextpro = 64, hidepenstyle = 128, hidetoolbox = 256, hideinfobox = 512 }
添加方法:计算并保存截图的区域框的大小 /// <summary> /// 计算并保存截图的区域框的大小 /// </summary> private void savecutimagesize(point beginpoint, point endpoint) { // 保存最终的绘图基点,用于截取选中的区域 this.endpoint = beginpoint; // 计算截取图片的大小 int imgwidth = math.abs(endpoint.x - beginpoint.x) + 1; int imgheight = math.abs(endpoint.y - beginpoint.y) + 1; int lblwidth = imgwidth + 4; int lblheight = imgheight + 4; // 设置截图区域的位置和大小 this.cutimagerect = new rectangle(beginpoint.x - 2, beginpoint.y - 2, lblwidth, lblheight); }
添加方法:执行截图,将选定区域的图片保存到剪贴板 /// <summary> /// 执行截图,将选定区域的图片保存到剪贴板 /// </summary> /// <param name="savetodisk"> /// 是否将图片保存到磁盘 /// </param> private void execcutimage(bool savetodisk, bool uploadimage) //bool savetodisk = false, bool uploadimage = false { // 如果图片获取区域不可见,则退出保存图片过程 if (!this.lbl_cutimage.visible) { return; } rectangle srcrect = new rectangle(); srcrect.x = this.lbl_cutimage.location.x + 2; srcrect.y = this.lbl_cutimage.location.y + 2; srcrect.width = this.lbl_cutimage.width - 4; srcrect.height = this.lbl_cutimage.height - 4; rectangle destrect = new rectangle(0, 0, srcrect.width, srcrect.height); bitmap bmp = new bitmap(srcrect.width, srcrect.height); graphics g = graphics.fromimage(bmp); g.drawimage(this.screenimage, destrect, srcrect, graphicsunit.pixel); clipboard.setimage(bmp); exitcutimage(true); }
添加方法:退出截图过程 /// <summary> /// 退出截图过程 /// </summary> private void exitcutimage(bool hidewindow) // = true { this.lbl_cutimage.visible = false; this.iscuting = false; if (hidewindow) { this.screenimage.dispose(); this.hide(); } }
主窗口鼠标按下事件处理程序 /// <summary> /// 截图窗口鼠标按下事件处理程序 /// </summary> /// <param name="sender"></param> /// <param name="e"></param> private void form1_mousedown(object sender, mouseeventargs e) { // 左键单击事件 if (e.button == mousebuttons.left && e.clicks == 1) { if (!this.lbl_cutimage.visible) { this.iscuting = true; this.beginpoint = e.location; this.endpoint = e.location; savecutimagesize(e.location, e.location); updatecutinfolabel(updateuimode.showcutimage | updateuimode.showinfobox); } } // 左键双击事件 if (e.button == mousebuttons.left && e.clicks == 2) { if (this.lbl_cutimage.visible) { execcutimage(false, false); } } // 右键单击事件 if (e.button == mousebuttons.right) { exitcutimage(!this.lbl_cutimage.visible); } }
主窗口鼠标移动事件处理程序 /// <summary> /// 截图窗口鼠标移动事件处理程序 /// </summary> /// <param name="sender"></param> /// <param name="e"></param> private void form1_mousemove(object sender, mouseeventargs e) { // 如果截取区域不可见,则退出处理过程 if (!this.lbl_cutimage.visible) { updatecutinfolabel(updateuimode.none); return; } point pntbgn = this.beginpoint; point pntend = e.location; // 如果是反向拖动,重新设置起始点 if (e.location.x < this.beginpoint.x && e.location.y < this.beginpoint.y) { pntbgn = e.location; pntend = this.beginpoint; } else { if (e.location.x < this.beginpoint.x) { pntbgn = new point(e.location.x, this.beginpoint.y); pntend = new point(this.beginpoint.x, e.location.y); } else { if (e.location.y < this.beginpoint.y) { pntbgn = new point(this.beginpoint.x, e.location.y); pntend = new point(e.location.x, this.beginpoint.y); } } } if (this.iscuting) { savecutimagesize(pntbgn, pntend); } updatecutinfolabel(updateuimode.none); }
主窗口鼠标抬起事件处理程序 /// <summary> /// 截图窗口鼠标抬起事件处理程序 /// </summary> /// <param name="sender"></param> /// <param name="e"></param> private void form1_mouseup(object sender, mouseeventargs e) { if (e.button == mousebuttons.left) { if (this.iscuting) { this.iscuting = false; updatecutinfolabel(updateuimode.none); } } }
截取区域图片绘制 /// <summary> /// 截取区域图片的绘制事件处理程序 /// </summary> /// <param name="sender"></param> /// <param name="e"></param> private void lbl_cutimage_paint(object sender, painteventargs e) { int imgwidth = this.lbl_cutimage.width - 4; int imgheight = this.lbl_cutimage.height - 4; if (imgwidth < 1) { imgwidth = 1; } if (imgheight < 1) { imgheight = 1; } // 创建缓存图像,先将要绘制的内容全部绘制到缓存中,最后再一次性绘制到 label 上, // 这样可以提高性能,并且可以防止屏幕闪烁的问题 bitmap bmp_lbl = new bitmap(this.lbl_cutimage.width, this.lbl_cutimage.height); graphics g = graphics.fromimage(bmp_lbl); // 将要截取的部分绘制到缓存 rectangle destrect = new rectangle(2, 2, imgwidth, imgheight); point srcpoint = this.lbl_cutimage.location; srcpoint.offset(2, 2); rectangle srcrect = new rectangle(srcpoint, new system.drawing.size(imgwidth, imgheight)); g.drawimage(this.screenimage, destrect, srcrect, graphicsunit.pixel); solidbrush brush = new solidbrush(color.fromargb(10, 124, 202)); pen pen = new pen(brush, 1.0f); //以下部分(边框和调整块)的绘制放在(编辑内容)的后面,是解决绘制编辑内容会覆盖(边框和调整块)的问题 // 绘制边框外的区域,解决会被编辑内容覆盖的问题 // 上边 destrect = new rectangle(0, 0, this.lbl_cutimage.width, 2); srcpoint = this.lbl_cutimage.location; //srcpoint.offset(2, 2); srcrect = new rectangle(srcpoint, new system.drawing.size(this.lbl_cutimage.width, 2)); g.drawimage(this.backgroundimage, destrect, srcrect, graphicsunit.pixel); // 下边 destrect = new rectangle(0, this.lbl_cutimage.height - 2, this.lbl_cutimage.width, 2); srcpoint = this.lbl_cutimage.location; srcpoint.offset(0, this.lbl_cutimage.height - 2); srcrect = new rectangle(srcpoint, new system.drawing.size(this.lbl_cutimage.width, 2)); g.drawimage(this.backgroundimage, destrect, srcrect, graphicsunit.pixel); // 左边 destrect = new rectangle(0, 2, 2, this.lbl_cutimage.height - 4); srcpoint = this.lbl_cutimage.location; srcpoint.offset(0, 2); srcrect = new rectangle(srcpoint, new system.drawing.size(2, this.lbl_cutimage.height - 4)); g.drawimage(this.backgroundimage, destrect, srcrect, graphicsunit.pixel); // 右边 destrect = new rectangle(this.lbl_cutimage.width - 2, 2, 2, this.lbl_cutimage.height - 4); srcpoint = this.lbl_cutimage.location; srcpoint.offset(this.lbl_cutimage.width - 2, 2); srcrect = new rectangle(srcpoint, new system.drawing.size(2, this.lbl_cutimage.height - 4)); g.drawimage(this.backgroundimage, destrect, srcrect, graphicsunit.pixel); // 绘制边框 g.drawline(pen, 2, 2, this.lbl_cutimage.width - 3, 2); g.drawline(pen, 2, 2, 2, this.lbl_cutimage.height - 3); g.drawline(pen, this.lbl_cutimage.width - 3, 2, this.lbl_cutimage.width - 3, this.lbl_cutimage.height - 3); g.drawline(pen, 2, this.lbl_cutimage.height - 3, this.lbl_cutimage.width - 3, this.lbl_cutimage.height - 3); // 绘制四个角的调整块 g.fillrectangle(brush, 0, 0, 4, 5); g.fillrectangle(brush, this.lbl_cutimage.width - 4, 0, 4, 5); g.fillrectangle(brush, 0, this.lbl_cutimage.height - 5, 4, 5); g.fillrectangle(brush, this.lbl_cutimage.width - 4, this.lbl_cutimage.height - 5, 4, 5); // 绘制中间的四个调整块 int blockx = this.lbl_cutimage.width / 2 - 2; int blocky = this.lbl_cutimage.height / 2 - 2; g.fillrectangle(brush, blockx, 0, 4, 5); g.fillrectangle(brush, 0, blocky, 4, 5); g.fillrectangle(brush, blockx, this.lbl_cutimage.height - 5, 4, 5); g.fillrectangle(brush, this.lbl_cutimage.width - 4, blocky, 4, 5); // 绘制到 label 上 e.graphics.drawimage(bmp_lbl, 0, 0); bmp_lbl.dispose(); }
双击鼠标左键完成截图功能 /// <summary> /// 截取区域图片的鼠标按下事件处理程序 /// </summary> /// <param name="sender"></param> /// <param name="e"></param> private void lbl_cutimage_mousedown(object sender, mouseeventargs e) { // 左键双击事件 if (e.button == mousebuttons.left && e.clicks == 2) { if (this.lbl_cutimage.visible) { execcutimage(false, false); } } }
注意:代码都贴完了,别忘了为窗体或组件绑定事件处理程序;
例如:截取区域图片的鼠标按下事件处理程序“lbl_cutimage_mousedown”,就是“lbl_cutimage”组件的“mousedown”事件的处理程序,绑定方法参考下图:
到此,基本截图的功能实现已经实现,赶快去截取一张图片,粘贴到qq的聊天窗口看看吧。
以上就是c#开发实例-订制屏幕截图工具(四)基本截图功能实现代码的详细内容。
其它类似信息

推荐信息