分享一个截图组件

由于最近项目里要有一个截图功能,花了几天时间写了个小程序,封装了3个不同截屏方式,希望能给有类似需求的园友提供一点点参考

功能概述:

  • 全屏截取
  • 区域截取
  • 窗体截取

效果入下图示:

 

实现方法概述

全屏截图

        /// <summary>
        /// 获取全屏截图
        /// </summary>
        /// <returns>截图</returns>
        publicImage GetFullScreenImage()
        {
            Imageimage = new Bitmap(Screen.PrimaryScreen.Bounds.Width, Screen.PrimaryScreen.Bounds.Height);
            Graphicsg = Graphics.FromImage(image);
            g.CopyFromScreen(new Point(0, 0), new Point(0, 0), Screen.PrimaryScreen.Bounds.Size);
            returnimage;
        }

区域截图

将Form设置为半透明状态,用户移动、拖拽窗体,选择区域后双击截图,Esc或鼠标右键退出。主要代码如下:

        //双击获取截图
        privatevoid GetScreenImage()
        {
            _image = new Bitmap(this.Width, this.Height);
            Graphicsg = Graphics.FromImage(_image);
            g.CopyFromScreen(this.Location, new Point(0, 0), new Size(this.Width, this.Height));
            this.DialogResult= DialogResult.OK;
        }

窗体截取

1,根据鼠标位置获取目标窗体句柄

[DllImport("user32.dll")]
public static extern IntPtr WindowFromPoint(Pointpoint);

2,绘制窗体外边框,使用户知道现在要截取的窗体

调用gdi32.dll里面的方法绘制边框,代码较多,请参见源码

3,截图

根据得到窗体的句柄通过如下方法获得窗体的位置和大小

 

[DllImport("user32.dll")]
 public static extern bool GetWindowRect(IntPtrhWnd, ref RECTlpRect);

被选择的窗体可能不是最前端的窗体,为了完整截取窗体,在截取之前,先把窗体通过以下方法设置为最前端窗体

   [DllImport("user32.dll")]
    public static extern bool SetForegroundWindow(IntPtr hWnd);

截图方法与其他两种截图方法一样,都是用Graphics类的CopyFromScreen方法完成的

组件使用方法

ScreenShot类中封装了3个方法分别用于全屏截取、区域截取和窗体截取,使用方法如下:

1,全屏截取

_image= _screenShot.GetFullScreenImage();

2,区域截取

_image= _screenShot.GetRangeImage();

3,窗体截取

需要添加一个事件:AfterCapture,然后再调用OpenWindowImageCaptureForm方法。在事件参数里得到Image对象

if (_screenShot.AfterCapture == null)
{
       _screenShot.AfterCapture += new EventHandler<WindowScreenCaptureEventArgs>(ScreenShot_AfterWindowCapture);
}
  _screenShot.OpenWindowImageCaptureForm();

 privatevoid ScreenShot_AfterWindowCapture(object o, WindowScreenCaptureEventArgse)
{
         _image = e.Image;
         this.Save(_image);
}

待改进地方

1,窗体截取时操作比较别扭,需要一个辅助窗体

      用鼠标拖拽那个园形图标到目标窗体,然后松开鼠标时,在MouseUp事件里得到目标窗体的句柄。如果没有这个MouseUp事件,我不知道在什么时候,通过什么方式来得到目标窗体的句柄。

2,用方法SetForegroundWindow将选窗体设为最前端时不能马上奇效,权宜之计是调用完这个方法先Sleep 300ms。不然目标窗体的前的窗体也被截屏了,不知道该怎么解决。

      对Windows编程熟悉的朋友可以提些建议,谢谢。

参考

编写过程中,借鉴和使用了以下博客或网站的思路或代码,表示感谢。

http://www.cnblogs.com/tuyile006/archive/2007/07/16/815843.html(全屏、区域)

http://www.codeproject.com/KB/dialog/FindWindow.aspx(窗体截取)

http://www.pinvoke.net/(一个很好的wiki)

 

下载源码(这是csdn的地址,本来想上传到google文档的,可是google文档被和谐了,还需FQ,可惜我放在里面的文档了,哎)

最新版本

posted @ 2010-09-04 18:05  会长  阅读(1593)  评论(2编辑  收藏  举报