Question

I want to get Screenshots of a possible hidden Window of another application that is using drawing via direct3d or opengl. I tryed a lot of ways to receive this windows content but only got black or transparent pictures. The closest i got was by using a DWM sample here http://bartdesmet.net/blogs/bart/archive/2006/10/05/4495.aspx this paints the window onto my c# form but i cant get the pixelcolors. If ill do a form.drawtobitmap the pixels drawn by dwm are missing.

So is their any way to use DWM to recive the capture into a image or to get the image drawn onto my form?

Was it helpful?

Solution

To answer your question: You can use GetPixel() Win32 function. But it's overkill in this situation.

Pinvoke GetPixel

MSDN GetPixel

The right way, is to get the device context and bit blit the content.

EDIT:

I've thrown together some code, by using PrintWindow. Seems to work quite well, even with media players. Note that GetWindowRect returns invalid rectangle for minimized Windows. But it's a decent start.

    [StructLayout(LayoutKind.Sequential)]
    public struct Rect
    {
        internal Rect(int left, int top, int right, int bottom)
        {
            Left = left;
            Top = top;
            Right = right;
            Bottom = bottom;
        }

        public int Left;
        public int Top;
        public int Right;
        public int Bottom;
    }

    [DllImport("user32.dll", SetLastError = true)]
    [return: MarshalAs(UnmanagedType.Bool)]
    static extern bool PrintWindow(IntPtr hwnd, IntPtr hDC, uint nFlags);

    [DllImport("user32.dll")]
    [return: MarshalAs(UnmanagedType.Bool)]
    public static extern bool GetWindowRect(IntPtr hwnd, out Rect lpRect);

    public void DumpWindow(IntPtr hwndSource, string filename)
    {
        Rect rc;
        GetWindowRect(hwndSource, out rc);

        var bmp = new Bitmap(rc.Right - rc.Left, rc.Bottom - rc.Top, PixelFormat.Format32bppArgb);
        using (Graphics gBmp = Graphics.FromImage(bmp))
        {
            IntPtr hdcBmp = gBmp.GetHdc();

            PrintWindow(hwndSource, hdcBmp, 0);

            gBmp.ReleaseHdc(hdcBmp);
        }

        bmp.Save(filename);
    }

Edit2: And if you add a second button to DWM demo form, insert this:

private void button1_Click(object sender, EventArgs e)
{
    var w = (Window)lstWindows.SelectedItem;
    DumpWindow(w.Handle, "test.bmp");
    Process.Start("test.bmp");
}

It still shows an empty image?

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top