在WindowsFormsHost上使用RenderTargetBitmap

我在WindowsFormsHost有一组控件,我想捕获当前视图并将其保存为图像,但是我只能在图像中看到一些Panel

是否可以将WindowsFormsHost用作“Visual”并捕获包装的控件?

看我的例子:

    

如果我basePanel添加一个Button或其他内容,那么在使用以下代码导出到PNG时,这将不可见:

  RenderTargetBitmap rtb = new RenderTargetBitmap(basePanel.Width, basePanel.Height, 96, 96, PixelFormats.Pbgra32); rtb.Render(windowHost); PngBitmapEncoder pnge = new PngBitmapEncoder(); pnge.Frames.Add(BitmapFrame.Create(rtb)); Stream stream = File.Create("test.jpg"); pnge.Save(stream); stream.Close(); 

关于为什么这可能不起作用的建议,也许是可能的解决办法? 我想这不是真的想用这种方式工作,但人们真的希望!

Windows窗体控件也知道如何渲染自身,您不必跳过屏幕捕获箍。 看起来像这样:

  using (var bmp = new System.Drawing.Bitmap(basePanel.Width, basePanel.Height)) { basePanel.DrawToBitmap(bmp, new System.Drawing.Rectangle(0, 0, bmp.Width, bmp.Height)); bmp.Save(@"c:\temp\test.png"); } 

WindowsFormsHost的内容由GDI +呈现,就像在Windows窗体应用程序中一样,因此您不能使用RenderTargetBitmap,因为它不是由WPF呈现的。 相反,您应该使用GDI + BitBlt函数,它允许您捕获屏幕上的区域。

有关示例,请参阅此文章


更新:这是代码的另一个版本,更新后用于WPF:

 using System.Drawing; ... public static ImageSource Capture(IWin32Window w) { IntPtr hwnd = new WindowInteropHelper(w).Handle; IntPtr hDC = GetDC(hwnd); if (hDC != IntPtr.Zero) { Rectangle rect = GetWindowRectangle(hwnd); Bitmap bmp = new Bitmap(rect.Width, rect.Height); using (Graphics destGraphics = Graphics.FromImage(bmp)) { BitBlt( destGraphics.GetHdc(), 0, 0, rect.Width, rect.Height, hDC, 0, 0, TernaryRasterOperations.SRCCOPY); } ImageSource img = System.Windows.Interop.Imaging.CreateBitmapSourceFromHBitmap( bmp.GetHBitmap(), IntPtr.Zero, Int32Rect.Empty, BitmapSizeOptions.FromEmptyOptions()); return img; } return null; } 

只需将您的WindowsFormsHost控件作为参数传递给Capture方法,并使用生成的ImageSource执行您喜欢的任何操作。 有关BitBltGetDC的定义,请看一下这个网站 (我在家用电脑上写过,我现在无法访问)