【问题标题】:How can I create WPF Window in BackgroundWorker?如何在 BackgroundWorker 中创建 WPF 窗口?
【发布时间】:2010-09-02 02:54:11
【问题描述】:

谁能解释一下,我怎样才能在 BackgroundWorker 线程中创建 WPF 窗口而不会出错?

我有一些课程(WPF 窗口):

public partial class Captcha : Window
    {
        public Captcha()
        {
            InitializeComponent();
        }

        private void SendCaptchaBtn_Click(object sender, RoutedEventArgs e)
        {
            DialogResult = true;
            this.Close();
        }
    }

在后台工作人员的 DoWork 函数中,我尝试使用此窗口创建一个对象:

BackgroundWorker bgWorker = new BackgroundWorker();
bgWorker.DoWork += new DoWorkEventHandler(bgWorker_DoWork);
bgWorker.RunWorkerAsync();

void bgWorker_DoWork(object sender, DoWorkEventArgs e)
        {
                parser = new Parser();
                parser.ParseFunc(tempKeywords);
        }

Parser 对象有一个“Captcha”窗口:

Captcha captcha_dlg = new Captcha();

当我运行程序时,Captcha-class点的构造函数出现运行时错误:调用线程必须是STA,因为许多UI组件都需要这个。 怎么了?谢谢你的帮助,对不起我的英语不好:(。

【问题讨论】:

    标签: wpf backgroundworker


    【解决方案1】:

    简短的回答是,你不能。

    BackgroundWorker 使用的任何线程都是 MTA 线程,因为它们来自线程池。启动后无法将线程从 MTA 更改为 STA。

    如果您想在另一个线程上创建 UI,最好的办法是使用 Thread 类,并在启动前通过调用 SetApartmentState() 将其设置为 STA。

    【讨论】:

    • 谢谢,现在它工作了:)。这是最佳解决方案 - 对于每个异步。在我的程序中创建另一个线程的函数/进程?那么调度员呢?它类似于 Windows 窗体应用程序中的 MethodInvoker 和委托,例如,可能需要访问主窗口中的某些控件? :)
    • @Dmitriy 如果您问为程序正在执行的每个异步操作创建一个新线程是否最佳,如果您想在该线程上显示 UI,我看不到另一种方式,因为WPF 必须在 STA 线程上运行。
    • 在同一个线程上有两个窗口并不是什么大问题,因为繁重的工作通常是异步完成的(在另一个线程上)
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2016-06-19
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-10-11
    • 2012-02-20
    相关资源
    最近更新 更多