代码之家  ›  专栏  ›  技术社区  ›  Jan Jongboom

运行多个UI线程

  •  8
  • Jan Jongboom  · 技术社区  · 15 年前

    跳到底部回答这个问题;这只是一些额外的信息

    我正在使用一个组件(geckofx)来呈现一些网站,很好,但是它只能在Windows窗体中使用;因为它必须绑定到可以绘制的winforms对象。因为所有的winforms都在同一线程中运行,所以一次只能使用一个geckofx实例;所以我决定以winform的形式创建一个“worker类”,并在其中添加所有逻辑。表单不需要与主表单通信。

    现在我可以启动10个窗口,它们最终会工作,但是每个新表单都会在其他所有表单处理完所有geckofx事件之前等待,因为您不能在一个线程上使用多个实例。此外,浏览器必须位于uithread上。所以:

    是否可以创建多个UI线程(每个窗体一个)?

    我见过有人这样做([edit:removed'bad'link]),但没有人能让他的代码示例正常工作。让它工作的人最初使用某种形式的定制消息泵送来做这种事情,但是我不知道如何实现这样的事情。

    4 回复  |  直到 6 年前
        1
  •  9
  •   Julien Roncaglia    15 年前

    我不认为你所要求的是你真正想要的,但是为每个线程创建一个消息泵是很容易的,你只需要调用应用程序,每个线程运行一次。

    static class Program
    {
        /// <summary>
        /// The main entry point for the application.
        /// </summary>
        [STAThread]
        static void Main()
        {
            Thread t1 = new Thread(Main_);
            Thread t2 = new Thread(Main_);
    
            t1.Start();
            t2.Start();
    
            t1.Join();
            t2.Join();
        }
    
        static void Main_()
        {
            Application.EnableVisualStyles();
            Application.SetCompatibleTextRenderingDefault(false);
            Application.Run(new Form1());
        }
    }
    
        2
  •  2
  •   Avram    15 年前

    使用application.doEvent()。

    创建多线程形式:

        Thread form2Thread;
        Form2 form2;
    
        private void Form1_Load(object sender, EventArgs e)
        {
            form2Thread = new Thread(RunForm2);
            form2Thread.SetApartmentState(ApartmentState.STA);
            form2Thread.Name = "Form2 Thread";   // looks nice in Output window
            form2Thread.Start();
        }
    
        public void RunForm2()
        {
            form2 = new Form2();
            Application.Run(form2);
        }
    
        3
  •  2
  •   Scott    14 年前

    Geckofx不需要表格。

    GeckoWebBrowser wb = new GeckoWebBrowser();
    wb.CreateControl(); //<-- the magic lays here!
    wb.DocumentCompleted += delegate{ MessageBox.Show(wb.DocumentTitle); };
    wb.Navigate("http://mysite.com");
    
        4
  •  1
  •   rosenfield    15 年前

    似乎是有可能的。

    我采取 backgrounder ,打开了testapp,并在线程/消息泵2上创建了一个新的表单1:

    private void button2_Click(object sender, EventArgs e) {
        helper.Background(() => {
            Form1 form2 = new Form1();
            form2.Show();
        });
    }
    

    第二个窗口响应鼠标单击等。

    还没有验证是否一切正常,我使用的免费Visual Studio速成版缺少“线程”调试窗口,嗯。所以我有点不知所措。不过,这似乎奏效了。让我知道:—)。