WPF启动画面UI不更新

时间:2015-02-16 23:37:04

标签: c# wpf splash-screen

我的WPF应用程序上有一个启动画面。启动窗口在我的App类中定义为一个字段,在Startup事件中,我执行各种初始化功能,可能需要一些时间,显示提示/窗口等。我的启动事件看起来像什么像这样:

Startup += (_,__) =>
{
    mySplashScreen.UpdateMessage("Initializing Component A...");

    InitializeComponentA();

    mySplashScreen.UpdateMessage("Initializing Component B...");

    InitializeComponentB();

    mySplashScreen.UpdateMessage("Initializing Component C...");

    InitializeComponentC();

    mySplashScreen.UpdateMessage("Opening application...");
};

对于启动画面更新方法,我尝试了以下方法:

  • 使用实现INotifyPropertyChanged的ViewModel类,绑定到它,并更新视图模型的Message属性。
  • 在代码隐藏中创建一个名为DependencyProperty的{​​{1}},然后绑定/更新它。
  • 直接设置属性(例如Message
  • 将启动画面放在单独的线程中,并通过myTextBlock.Text = splashMessage;设置启动消息(使用Dispatcher.Invoke()确保UI立即更新)。

我的问题是没有任何启动画面消息在窗口上更新/显示。当其中一个DispatcherPriority.Send方法显示对话框时,启动UI更新的唯一条件。在这种情况下,启动UI更新。对于上面的所有选项,我甚至尝试同步和异步等待(通过InitializeComponentX())几秒钟来查看UI是否会更新,但它永远不会更新。

为什么我的启动界面仅在我显示另一个对话框/窗口时才更新?

2 个答案:

答案 0 :(得分:2)

  

为什么我的启动界面仅在我显示另一个对话框/窗口时才更新?

您完全阻止了UI线程,这阻止了WPF处理和显示您的更新。

您需要将工作转移到后台线程中。

答案 1 :(得分:0)

您可以使用async和await机制将组件的初始化推送到workerthread。像这样:

mySplashScreen.UpdateMessage("Initializing Component A...");

await InitializeComponentAAsync();

mySplashScreen.UpdateMessage("Initializing Component B...");

await InitializeComponentBAsync();

mySplashScreen.UpdateMessage("Initializing Component C...");

await InitializeComponentCAsync();

mySplashScreen.UpdateMessage("Opening application...");

它需要更改必须变为异步的initialisecomponent方法。但它不应该是一个非常大的更新。 我还更新了方法名称,使它们符合async方法以'Async'结尾的约定。 这释放了GUI线程,并且应该发生更新。

如果您还没有此版本的.NET,则可以使用后台工作程序初始化所有内容,并使用用户报告进度来更新启动屏幕。我觉得并不太难。