我如何拍摄应用程序窗口的一部分快照?

时间:2010-10-27 02:14:18

标签: c# winforms

我正在尝试从指定的起始坐标(这是我的问题所在的位置)拍摄应用程序窗口的指定部分的快照。

Rectangle bounds = new Rectangle((this.Width/2)-400,(this.Height/2)-200, 800,400);

using (Bitmap bitmap = new Bitmap(bounds.Width, bounds.Height, PixelFormat.Format32bppArgb))
{   
    using (Graphics graphics = Graphics.FromImage(bitmap))
    {
        IntPtr hdc = graphics.GetHdc();
        PrintWindow(this.axS.Handle, hdc, 0);
        graphics.ReleaseHdc(hdc);
        graphics.Flush();
        string file = "example.png";
        bitmap.Save(file, ImageFormat.Png);
    }
}

我正在尝试使用动态自适应方法来截取窗口中心的屏幕截图,即使在调整大小后也是如此。我不确定如何将xy应用于屏幕截图作为屏幕截图的起点。尺寸始终保持800,400,并始终截取应用程序中心的屏幕截图,无论窗口大小如何。

每次尝试我都挂了,位图从0 (+800), 0 (+400)截取了我需要更改0, 0的屏幕截图。

Bitmap是否有能力做到这一点?如果没有,我可以使用其他什么方法?

2 个答案:

答案 0 :(得分:0)

而不是使用PrintWindow尝试使用Graphics.CopyFromScreen,它允许您同时指定左上角和尺寸。

http://msdn.microsoft.com/en-us/library/6yfzc507.aspx

  

从屏幕到图形的绘图表面执行颜色数据的位块传输,对应于像素矩形。

CopyFromScreen适用于屏幕坐标,因此您必须为通话计算。

答案 1 :(得分:0)

您可以使用SetViewportOrgEx在HDC上设置原点。我发现窗口的标题栏丢掉了中心点的计算,所以我也考虑到了这一点。

int x = (this.Width / 2) - 400;
int y = ((this.Height + SystemInformation.CaptionHeight) / 2) - 200;

Rectangle bounds = new Rectangle(x, y, 800, 400);

using (Bitmap bitmap = new Bitmap(bounds.Width, bounds.Height, PixelFormat.Format32bppArgb))
{
    using (Graphics graphics = Graphics.FromImage(bitmap))
    {
        IntPtr hdc = graphics.GetHdc();
        POINT pt;

        SetViewportOrgEx(hdc, -x, -y, out pt);

        // rest as before
    }
}

SetViewportOrgExPOINT的签名:

[DllImport("gdi32.dll")]
static extern bool SetViewportOrgEx(IntPtr hdc, int X, int Y, out POINT lpPoint);

[StructLayout(LayoutKind.Sequential)]
public struct POINT
{
    public int X;
    public int Y;

    public POINT(int x, int y)
    {
        this.X = x;
        this.Y = y;
    }

    public static implicit operator System.Drawing.Point(POINT p)
    {
        return new System.Drawing.Point(p.X, p.Y);
    }

    public static implicit operator POINT(System.Drawing.Point p)
    {
        return new POINT(p.X, p.Y);
    }
}