2012-05-25 156 views
2

我一直在尝试创建通知窗口,但我一直在努力弄清楚为什么在运行它时不会发生这种不透明度偏移。相反,窗口将保持一秒钟,然后关闭而没有任何可见的变化。我通过其他方法所做的其他尝试都失败了,所以它一定是我遗失的一些财产。谢谢你的帮助!更改不透明度时重绘窗口不透明度

public void RunForm(string error, MessageBoxIcon icon, int duration) 
    { 
     lblMessage.Text = error; 
     Icon i = ToSystemIcon(icon); 
     if (i != null) 
     { 
      BitmapSource bs = System.Windows.Interop.Imaging.CreateBitmapSourceFromHIcon(i.Handle, Int32Rect.Empty, BitmapSizeOptions.FromEmptyOptions()); 
      imgIcon.Source = bs; 
     } 
     this.WindowStartupLocation = WindowStartupLocation.Manual; 
     this.Show(); 
     this.Left = System.Windows.Forms.Screen.PrimaryScreen.WorkingArea.Right - this.RestoreBounds.Width - 20; 
     this.Top = System.Windows.Forms.Screen.PrimaryScreen.WorkingArea.Bottom - this.RestoreBounds.Height - 20; 
     while (this.Opacity > 0) 
     { 
      this.Opacity -= 0.05; 
      Thread.Sleep(50); 
     } 
     this.Close(); 
    } 


<Window Width="225" Height="140" VerticalContentAlignment="Center" HorizontalAlignment="Center" ShowActivated="True" ShowInTaskbar="False" 
ResizeMode="NoResize" Grid.IsSharedSizeScope="False" SizeToContent="Height" WindowStyle="None" BorderBrush="Gray" 
BorderThickness="1.5" Background="White" Topmost="True" AllowsTransparency="True" Opacity="1"> 
<Grid Height="Auto" Name="grdNotificationBox" > 
    <Image Margin="12,12,0,0" Name="imgIcon" Stretch="Fill" HorizontalAlignment="Left" Width="32" Height="29" VerticalAlignment="Top" /> 
    <TextBlock Name="lblMessage" TextWrapping="Wrap" Margin="57,11,17,11"></TextBlock> 
</Grid> 

回答

2

这可不行: 完整的WPF处理在一个单独的线程(技术上两个,而是并不重要)来完成。你改变不透明度并直接让UI线程休眠,再次改变它并将它发回睡眠。 UI线程从来没有时间来处理你所做的事情。即使消除睡眠也无济于事,因为比起快要快很多,并且ui线程也无法处理任何请求。理解你的代码和WPF处理是在同一个线程中完成是很重要的,你需要的时间越长,WPF得到的时间就越少,反之亦然。

要解决它,你需要使用animations。他们正是为了这样的事情。结帐这thread

+0

谢谢。我今天遇到了WCF的单线程问题。我已经结束了与ShowDialog()和动画。 – Tim

1

您基本上阻止了UI线程在您的while loop中更新。使用计时器执行此操作,或更合适地使用Background Worker Thread

编辑:作为dowhilefor表示您可以使用WPF动画来达到此目的。 This article这里详细讨论这一点。

DoubleAnimation da = new DoubleAnimation(); 
da.From = 1; 
da.To = 0; 
da.Duration = new Duration(TimeSpan.FromSeconds(2)); 
da.AutoReverse = true; 
da.RepeatBehavior = RepeatBehavior.Forever; 
rectangle1.BeginAnimation(OpacityProperty, da);