我试图在WPF应用程序上对我的启动画面产生淡入淡出效果。 图像对象的不透明度最初为0.此代码会将不透明度从0(最小)修改为1(最大),但行img_waves.Opacity不起作用。图像不透明度保持为0。
private void Splash_ContentRendered(object sender, EventArgs e)
{
System.Threading.Thread.Sleep(3000);
for (double x = 0; x<=1; x+=0.01d)
{
System.Threading.Thread.Sleep(15);
//MessageBox.Show(x.ToString());
img_waves.Opacity = x;
}
this.Close();
}
但是,如果我激活'MessageBox.Show(x.ToString());' 正如您在此图片上看到的那样:
代码有效,但我必须一直点击消息框。
我的问题是:为什么?如果没有MessageBox.Show?
,为什么不起作用答案 0 :(得分:3)
因为你正在阻止GUI线程。它永远不会有机会重绘表单。添加消息框时,将抽取消息队列,从而允许绘图。
处理这个问题的最简单方法是:
private async void Splash_ContentRendered(object sender, EventArgs e)
{
await Task.Delay(3000);
for (double x = 0; x<=1; x+=0.01d)
{
await Task.Delay(15);
img_waves.Opacity = x;
}
this.Close();
}
请注意,这意味着在动画期间仍可以与表单进行交互。对于启动画面来说这不应该是一个问题,但它可能会导致您以“真实”形式出现问题。尽管如此,请确保在动画期间无法关闭表单 - 这可能会导致异常:)
还有其他方法可以强制推送消息队列,但通常不赞成。
所有这一切,你正在使用WPF - 为什么你这样手动做动画?难道你不能把它当作WPF中的动画效果处理吗? MSDN上有一个示例。
答案 1 :(得分:1)
虽然我同意@Luaan解释为什么作为循环的替代解决方案,您可以Storyboard
使用DoubleAnimation
Opacity
属性
private void Splash_ContentRendered(object sender, EventArgs e)
{
var sb = new Storyboard();
var da = new DoubleAnimation(0, 1, new Duration(TimeSpan.FromSeconds(1.5)));
da.BeginTime = TimeSpan.FromSeconds(3);
Storyboard.SetTargetProperty(da, new PropertyPath("Opacity"));
Storyboard.SetTarget(da, img_waves);
sb.Children.Add(da);
sb.Completed += (s1, e1) => this.Close();
sb.Begin();
}