如何从另一个线程显示窗体

本文关键字:显示 窗体 线程 另一个 | 更新日期: 2023-09-27 18:00:58

我在C#Winforms应用程序上的一个单独线程中运行此代码(我的表单名称为MainForm(:

DisplayDownload form2 = new DisplayDownload();
form2.TopMost = true;  
form2.Show();

但是当线程启动时,表单永远不会打开。如果我把代码移到应用程序的主线程上,它会很好地打开,但如果我把它作为自己的线程启动,表单就永远不会打开。

我试着使用这篇文章中被接受的答案:从另一个线程(.Net(调用一个windows窗体,但我得到了这个错误:

无法将匿名方法转换为类型"System.Delegate",因为它不是委托类型

以下是我尝试使用的代码:

MainForm.Invoke(delegate {
         DisplayDownload form2 = new DisplayDownload();

         form2.TopMost = true; 
         form2.Show();
});

有人能告诉我我做错了什么以及如何让它发挥作用吗?

如何从另一个线程显示窗体

添加new MethodInvoker(delegate(),因此:

MainForm.Invoke(new MethodInvoker(delegate() 
{
             DisplayDownload form2 = new DisplayDownload();

             form2.TopMost = true; 
             form2.Show();
}));

您需要显式实例化委托类型:

MainForm.Invoke(new Action(delegate { ... }));

C#2及更高版本可以隐式地将方法组转换为委托,但只能转换为特定的委托类型
Invoke方法采用Delegate基类,因此编译器没有要创建的特定委托类型
因此,您需要自己显式地创建一个委托。

您希望哪个线程处理新Form的事件?如果您希望主线程处理事件,那么按照现有示例的建议使用Control.Invoke

如果希望新线程管理自己的UI事件,则需要调用Application.Run。当你这样做时,表单将能够自己绘制,并在屏幕上可见。

    //This is for WPF Application 
     try
       {
        Application.Current.Dispatcher.Invoke(new Action(() => { 
         DisplayDownload form2 = new DisplayDownload();
         form2.TopMost = true; 
         form2.Show();
        }));
        }
        catch(Exception ex) {
         }