C# 使用CreateGraphics打印当前表单,但也会打印消息框
我正在使用CreateGraphics函数打印我的活动表单(formMain),如下代码所示 环境:经典模式下的windows 7 professional,VisuaStudio 2008C# 使用CreateGraphics打印当前表单,但也会打印消息框,c#,winforms,printscreen,C#,Winforms,Printscreen,我正在使用CreateGraphics函数打印我的活动表单(formMain),如下代码所示 环境:经典模式下的windows 7 professional,VisuaStudio 2008 [System.Runtime.InteropServices.DllImport("gdi32.dll")] public static extern long BitBlt (IntPtr hdcDest, int nXDest, int nYDest, int nWidth, int nHeight
[System.Runtime.InteropServices.DllImport("gdi32.dll")]
public static extern long BitBlt (IntPtr hdcDest, int nXDest, int nYDest, int nWidth, int nHeight, IntPtr hdcSrc, int nXSrc, int nYSrc, int dwRop);
private Bitmap memoryImage;
private void CaptureScreen()
{
Graphics mygraphics = this.CreateGraphics();
Size s = this.Size;
memoryImage = new Bitmap(s.Width, s.Height, mygraphics);
Graphics memoryGraphics = Graphics.FromImage(memoryImage);
IntPtr dc1 = mygraphics.GetHdc();
IntPtr dc2 = memoryGraphics.GetHdc();
BitBlt(dc2, 0, 0, this.ClientRectangle.Width, this.ClientRectangle.Height, dc1, 0, 0, 13369376);
mygraphics.ReleaseHdc(dc1);
memoryGraphics.ReleaseHdc(dc2);
}
private void printDocument1_PrintPage(System.Object sender, System.Drawing.Printing.PrintPageEventArgs e)
{
e.Graphics.DrawImage(memoryImage, 0, 0);
}
private void printButton_Click(System.Object sender, System.EventArgs e)
{
if (MessageBox.Show("test", "test", MessageBoxButtons.YesNo) == DialogResult.Yes)
{
CaptureScreen();
printDocument1.Print();
}
}
案例1:
当MessageBox默认位置显示时,formMain可以清晰打印
案例2:
但是,如果使用鼠标将messageBox移出默认位置,则打印结果将变脏。
它现在在mainForm中包含messageBox(图)
不要直接使用WinAPI(BitBlt,…),请尝试使用以下方法:
Bitmap bmp = new Bitmap(this.Width, this.Height);
this.DrawToBitmap(bmp, this.Bounds);
bmp.Save(@"c:\temp\test.png", System.Drawing.Imaging.ImageFormat.Png); // For testing
这应该只绘制表单的内容。我用另一种最顶级的形式成功地测试了这一点 将其放入代码中:
private void CaptureScreen() {
memoryImage = new Bitmap(this.Width, this.Height);
this.DrawToBitmap(memoryImage, this.Bounds);
}
比如XP。一个应对措施是将这个.Update()放在;在CaptureScreen()调用之前
我认为我的系统是windows 7,但使用经典模式->作为windows xp我已经用以下代码尝试了:mygraphics来自此。CreateGraphics();,这是主要形式。但一切都没有改变。您能给我看完整的代码吗?@user1299527:对不起,刚才复制和粘贴的速度太快了。@user1299527:请按问题中所示保留您的代码。然后用我的答案中的方法替换
CaptureScreen()
方法。(提示:如果您从任何地方复制/粘贴代码,不要只是复制它,试着理解该代码的功能以及为什么它是这样实现的)这就是您泄漏GDI句柄时得到的结果。我怀疑这个片段是否真的可以重编,你必须点击这个按钮数千次。你需要描述你真正在做什么,我不需要点击上千次。作为证据。简单使用鼠标将确认框从默认位置取出。然后,执行打印操作。你可以这样做。点击“打印我”按钮,2。出现确认框时,3。使用鼠标将确认框移动到默认位置之外,4。单击“确定”以confirm@user1299527我已经试过了,对我来说效果不错。无法重现您的问题。顺便说一句,你的表格上有TextBox
或RichTextBox
吗?让消息框与文本框完全对齐是一个奇妙的巧合,我并不特别相信这样的巧合。总之,诊断是在截图之前窗口还没有重新粉刷。这可能发生在没有Aero的旧Windows版本上,比如XP。一个应对措施是放置this.Update()代码>在CaptureScreen()调用之前。还有更多的事情不正常,不让按钮上的文本抗锯齿也是很奇怪的。背景色的奇怪抖动也是如此。