我有一个无边框表单,其中包含以下代码:
public partial class Splash : Form
{
bool painted = false;
public Splash()
{
InitializeComponent();
Opacity = 0;
}
protected override void OnPaint(PaintEventArgs e)
{
//
}
protected override void OnPaintBackground(PaintEventArgs e)
{
if (painted)
return;
Graphics gfx = e.Graphics;
gfx.CopyFromScreen(new Point(Bounds.Left, Bounds.Top),
Point.Empty, Bounds.Size);
gfx.DrawImage(Properties.Resources.Splash, e.ClipRectangle);
Opacity = 100;
painted = true;
}
}
这在我的Windows 7机器上运行得很好,但是在Windows XP中它显示垃圾(可能是帧缓冲中没有错位的东西)而不是启动图像。我有时可以在垃圾里找出高度扭曲的旧探险家窗户遗留物等。
奇怪的是,我在不同的程序中运行相同的代码,该程序具有相同类型的24位PNG,并且在XP机器上运行良好。
知道为什么会这样吗?
解决方案:
在Bitmap b;
行后添加bool painted = false;
,并将OnPaintBackground
更改为:
protected override void OnPaintBackground(PaintEventArgs e)
{
if (!painted)
{
b = new Bitmap(Width, Height);
Graphics g = Graphics.FromImage(b);
g.CopyFromScreen(new Point(Bounds.Left, Bounds.Top),
Point.Empty, Bounds.Size);
g.DrawImage(Properties.Resources.Splash, e.ClipRectangle);
Opacity = 100;
painted = true;
g.Dispose();
}
Graphics gfx = e.Graphics;
gfx.DrawImage(b, new Point(0, 0));
gfx.Dispose();
}
答案 0 :(得分:2)
我认为这是因为你画了一次后没有刷新表格。 Win XP不存储任何窗口的图形内容,他只是通知他们自己画画。您的OnPaint
和OnPaintBackground
函数应始终刷新窗口。
我不明白为什么你不使用BackgroundImage
属性和Opacity
。您可以将图像设置为拉伸,缩放等。是否要显示效果?
答案 1 :(得分:1)
您是否考虑过将.BorderStyle设置为None且使用.TransparencyKey设置的表单?如果没有CopyFromScreen调用的麻烦,它应该模仿你想要获得的效果。
根据评论进行编辑
我找到了一些示例源代码,它可以完成你想要的每像素alpha混合,但它更复杂并涉及pInvoke。作为参考,你可以在这里找到它。 http://www.codeproject.com/KB/GDI-plus/perpxalpha_sharp.aspx
答案 2 :(得分:0)
我认为Win7存储了Windows的图形内容并自动重绘它们。当窗口没有响应时你可以看到差异 - 在WinXP中他不会被刷新,而在Win7中他看起来还不错。当您将鼠标悬停在任务栏上时,窗口预览以及表单出现时的“表单增长”效果。 我在一个单独的答案中写这个,因为我不知道如何在这个网站上添加评论......