整理的C#螢幕截圖,控制元件截圖程式
阿新 • • 發佈:2018-11-11
程式碼基本從網上搜集而來,整理成以下檔案:
包括螢幕截圖(和螢幕上看到的一致);
以及控制元件截圖(只要該控制元件在本視窗內顯示完全且不被其他控制元件遮擋就可正確截圖)
- using System;
- using System.Collections.Generic;
- using System.Drawing;
- using System.Linq;
- using System.Runtime.InteropServices;
- using System.Text;
- using System.Threading.Tasks;
- using System.Windows.Forms;
- namespace LC
- {
- class ScreenCapture
- {
- #region 抓取螢幕
- /// <summary>
- /// 抓取螢幕(層疊的視窗)
- /// </summary>
- /// <param name="x">左上角的橫座標</param>
- /// <param name="y">左上角的縱座標</param>
- /// <param name="width">抓取寬度</param>
- /// <param name="height">抓取高度</param>
- /// <returns></returns>
- public static Bitmap captureScreen(int x, int y, int width, int height)
- {
- Bitmap bmp = new Bitmap(width, height);
- using (Graphics g = Graphics.FromImage(bmp))
- {
- g.CopyFromScreen(new Point(x, y), new Point(0, 0), bmp.Size);
- g.Dispose();
- }
- //bit.Save(@"capture2.png");
- return bmp;
- }
- /// <summary>
- /// 抓取整個螢幕
- /// </summary>
- /// <returns></returns>
- public static Bitmap captureScreen()
- {
- Size screenSize = Screen.PrimaryScreen.Bounds.Size;
- return captureScreen(0,0,screenSize.Width,screenSize.Height);
- }
- #endregion
- #region 使用BitBlt方法抓取控制元件,無論控制元件是否被遮擋
- /// <summary>
- /// 控制元件(視窗)的截圖,控制元件被其他視窗(而非本視窗內控制元件)遮擋時也可以正確截圖,使用BitBlt方法
- /// </summary>
- /// <param name="control">需要被截圖的控制元件</param>
- /// <returns>該控制元件的截圖,控制元件被遮擋時也可以正確截圖</returns>
- public static Bitmap captureControl(Control control)
- {
- //呼叫API截圖
- IntPtr hSrce = GetWindowDC(control.Handle);
- IntPtr hDest = CreateCompatibleDC(hSrce);
- IntPtr hBmp = CreateCompatibleBitmap(hSrce, control.Width, control.Height);
- IntPtr hOldBmp = SelectObject(hDest, hBmp);
- if (BitBlt(hDest, 0, 0, control.Width, control.Height, hSrce, 0, 0, CopyPixelOperation.SourceCopy | CopyPixelOperation.CaptureBlt))
- {
- Bitmap bmp = Image.FromHbitmap(hBmp);
- SelectObject(hDest, hOldBmp);
- DeleteObject(hBmp);
- DeleteDC(hDest);
- ReleaseDC(control.Handle, hSrce);
- // bmp.Save(@"a.png");
- // bmp.Dispose();
- return bmp;
- }
- return null;
- }
- // /// <summary>
- // /// 有問題!!!!!使用者區域座標不對啊
- // /// 控制元件(視窗)的使用者區域截圖,控制元件被其他視窗(而非本視窗內控制元件)遮擋時也可以正確截圖,使用BitBlt方法
- // /// </summary>
- // /// <param name="control">需要被截圖的控制元件</param>
- // /// <returns>控制元件(視窗)的使用者區域截圖</returns>
- // public static Bitmap captureClientArea(Control control)
- // {
- //
- // Size sz = control.Size;
- // Rectangle rect = control.ClientRectangle;
- //
- //
- // //呼叫API截圖
- // IntPtr hSrce = GetWindowDC(control.Handle);
- // IntPtr hDest = CreateCompatibleDC(hSrce);
- // IntPtr hBmp = CreateCompatibleBitmap(hSrce, rect.Width, rect.Height);
- // IntPtr hOldBmp = SelectObject(hDest, hBmp);
- // if (BitBlt(hDest, 0, 0, rect.Width, rect.Height, hSrce, rect.X, rect.Y, CopyPixelOperation.SourceCopy | CopyPixelOperation.CaptureBlt))
- // {
- // Bitmap bmp = Image.FromHbitmap(hBmp);
- // SelectObject(hDest, hOldBmp);
- // DeleteObject(hBmp);
- // DeleteDC(hDest);
- // ReleaseDC(control.Handle, hSrce);
- // // bmp.Save(@"a.png");
- // // bmp.Dispose();
- // return bmp;
- // }
- // return null;
- //
- // }
- #endregion
- #region 使用PrintWindow方法抓取視窗,無論控制元件是否被遮擋
- /// <summary>
- /// 視窗的截圖,視窗被遮擋時也可以正確截圖,使用PrintWindow方法
- /// </summary>
- /// <param name="control">需要被截圖的視窗</param>
- /// <returns>視窗的截圖,控制元件被遮擋時也可以正確截圖</returns>
- public static Bitmap captureWindowUsingPrintWindow(Form form)
- {
- return GetWindow(form.Handle);
- }
- private static Bitmap GetWindow(IntPtr hWnd)
- {
- IntPtr hscrdc = GetWindowDC(hWnd);
- Control control = Control.FromHandle(hWnd);
- IntPtr hbitmap = CreateCompatibleBitmap(hscrdc, control.Width, control.Height);
- IntPtr hmemdc = CreateCompatibleDC(hscrdc);
- SelectObject(hmemdc, hbitmap);
- PrintWindow(hWnd, hmemdc, 0);
- Bitmap bmp = Bitmap.FromHbitmap(hbitmap);
- DeleteDC(hscrdc);//刪除用過的物件
- DeleteDC(hmemdc);//刪除用過的物件
- return bmp;
- }
- #endregion
- #region DLL calls
- [DllImport("gdi32.dll")]
- static extern bool BitBlt(IntPtr hdcDest, int xDest, int yDest, int
- wDest, int hDest, IntPtr hdcSource, int xSrc, int ySrc, CopyPixelOperation rop);
- [DllImport("gdi32.dll")]
- static extern IntPtr DeleteDC(IntPtr hDc);
- [DllImport("gdi32.dll")]
- static extern IntPtr DeleteObject(IntPtr hDc);
- [DllImport("gdi32.dll")]
- static extern IntPtr CreateCompatibleBitmap(IntPtr hdc, int nWidth, int nHeight);
- [DllImport("gdi32.dll")]
- static extern IntPtr CreateCompatibleDC(IntPtr hdc);
- [DllImport("gdi32.dll")]
- static extern IntPtr SelectObject(IntPtr hdc, IntPtr bmp);
- [DllImport("user32.dll")]
- public static extern IntPtr GetDesktopWindow();
- [DllImport("user32.dll")]
- public static extern IntPtr GetWindowDC(IntPtr ptr);
- [DllImport("user32.dll")]
- public static extern bool PrintWindow(IntPtr hwnd, IntPtr hdcBlt, UInt32 nFlags);
- [DllImport("user32.dll")]
- static extern bool ReleaseDC(IntPtr hWnd, IntPtr hDc);
- #endregion
- }
- }