WPF CrossThreadException in App.Xaml with BackgroundWorker

本文关键字:with BackgroundWorker Xaml App CrossThreadException in WPF | 更新日期: 2023-09-27 17:51:04

我在我的App.Xaml:

public App()
{
    _backgroundWorker = new BackgroundWorker();
    _backgroundWorker.DoWork += new DoWorkEventHandler(DoBackgroundWork);
    _backgroundWorker.RunWorkerCompleted += new RunWorkerCompletedEventHandler(BackgroundCompleted);
    _backgroundWorker.RunWorkerAsync();
    _splashView = new SplashView();
    _splashView.Show();
}

DoBackgroundWork方法执行一些数据库设置,然后BackgroundCompleted事件关闭_splashView并显示_mainView

然而,从BackgroundCompleted修改_splashView中的任何东西都会导致交叉线程异常,这就是我认为后台工作人员被设计用来修复的。我猜这与App.Xaml中背景工作者的工作方式有关。也许这是一个糟糕的启动画面?

WPF CrossThreadException in App.Xaml with BackgroundWorker

后台worker使用SynchronizationContext。这是从内存,但我不认为它已经在应用程序的构造函数中初始化。

在构造BW之前,请检查SynchronizationContext。Current不为空。还要检查SynchronizationContext。电流值与施工前电流值相同

如果不是,您需要在稍后的过程中移动代码…App.OnStartUp应该没问题

也许这是一个糟糕的方式做启动屏幕?

除非我误解了你的问题,否则我认为没有必要这样做来显示启动画面。只需选择图像,并在属性窗口中单击BuildAction下拉菜单,然后选择SplashScreen。此外,我认为你可以通过消除BackgroundWorker来简化你的过程,除非你的数据函数需要很长时间。我相信你添加它是为了适应闪屏的显示/隐藏

无法保证OnWorkCompleted的事件处理程序将使用哪个线程执行。

参见类似问题BackgroundWorker OnWorkCompleted抛出跨线程异常

你必须使用InvokeBeginInvoke方法从后台线程修改视觉元素。你可以直接在你要修改属性的对象上调用它,或者使用Dispatcher

编辑:As per conversation with Adam

SynchronizationContext具有OnWorkCompleted事件处理程序在初始线程(而不是BackgroundWorker的)上运行的预期效果。http://msdn.microsoft.com/en-us/magazine/gg598924.aspx。(见图2)

如果BackgroundWorker在SynchronizationContext初始化之前被创建并运行,那么OnWorkCompleted将可能在与BackgroundWorker相同的线程上执行。

谢谢亚当。