我在winform应用程序中创建位图图像时遇到问题。
情况:
我有UserControl
名为" CanvasControl
"接受OnPaint
方法作为我的Draw Pad应用程序的画布。在这个用户控件中,我有一个功能" PrintCanvas()
"这将在PNG文件中创建UserControl
的屏幕截图。以下是PrintCanvas()
函数:
public void PrintCanvas(string filename = "sample.png")
{
Graphics g = this.CreateGraphics();
//new bitmap object to save the image
Bitmap bmp = new Bitmap(this.Width, this.Height);
//Drawing control to the bitmap
this.DrawToBitmap(bmp, new Rectangle(0, 0, this.Width, this.Height));
bmp.Save(Application.StartupPath +
@"\ExperimentFiles\Experiment1" + filename, ImageFormat.Png);
bmp.Dispose();
}
此用户控件(CanvasControl
)在我的主窗体中被调出,用户将在其中绘制内容并可选择使用保存按钮进行保存。保存按钮会调出" PrintCanvas()
" UserControl
的功能。
我按预期得到输出图像文件,但问题是它是一张空白图像。
到目前为止我尝试过:
为了测试它不是语法问题,我尝试将PrintCanvas()
函数转移到我的主窗体中,令人惊讶的是我得到了整个主窗体的图像,但是UserControl
不是在那里可见。
我是否错过任何其他设置以使winform UserControl
可打印?
更新:(绘图程序)
答案 0 :(得分:2)
问题中的代码给出了第一个提示,但链接中的代码显示了问题的根源:您使用了错误的'绘图的Graphics
对象的实例:
protected override void OnPaint(PaintEventArgs e)
{
// If there is an image and it has a location,
// paint it when the Form is repainted.
Graphics graphics = this.CreateGraphics();
..
这是winforms图形最常见的错误之一! 永远不要使用CreateGraphics!你总是应该在Paint或DrawXXX事件中使用Graphics对象绘制到控制界面上。这些事件有一个参数e.Graphics
,它是唯一可以绘制持久性图形的参数。
持久性表示在必要时始终会刷新,而不仅仅是在您触发它时。这是一个令人讨厌的错误,因为一切似乎都有效,直到您遇到外部事件需要重绘的情况:
DrawToBitmap
..只有在您使用Graphics
参数中的有效且最新的 PaintEventArgs e
对象时,才会有效。
所以,解决方案很简单:
protected override void OnPaint(PaintEventArgs e)
{
// If there is an image and it has a location,
// paint it when the Form is repainted.
Graphics graphics = e.Graphics(); // << === !!
..
但是 CreateGraphics
的优点是什么?引诱新手进入那个错误只会有好处吗?
不完全;以下是它的一些用途:
TextRenderer
或MeasureString
方法Bitmap
Graphics.DpiX/Y
分辨率
可能还有其他一些我现在无法想到的......
因此,对于正常绘制到控件总是,请使用e.Grapahics
对象!您可以将其传递给子例程以使代码更加结构化,但不要尝试缓存它;它需要是最新的!