C#WinForms:如何设置主函数STAThreadAttribute

jac*_*nad 24 c# winforms

saveFileDialog.ShowDialog()在后台线程中调用时,我得到以下异常:

在进行OLE调用之前,必须将当前线程设置为单线程单元(STA)模式.确保您的Main函数标记了STAThreadAttribute.

根据这个:

要解决此问题,请插入以下语句:

Threading.Thread.CurrentThread.ApartmentState = Threading.ApartmentState.STA;
Run Code Online (Sandbox Code Playgroud)

在Application.Run语句之前的Main中.

但是Application.Run语句在Program.cs中,它似乎是生成的代码,因此任何更改都可能意外丢失.此外,我找不到在项目或主窗体属性中将当前线程设置为STA的方法,但也许我在错误的地方查找.saveFileDialog.ShowDialog()在后台线程中调用的正确方法是什么?

小智 47

解决方案很容易; 只需在Main方法的顶部添加它 [STAThread]

所以你的主要方法应该是这样的

 [STAThread]
 static void Main(string[] args)
 {
     ....
 }
Run Code Online (Sandbox Code Playgroud)

这个对我有用.


Nat*_*han 25

不应该从后台线程调用ShowDialog() - 使用Invoke(..).

Invoke((Action)(() => { saveFileDialog.ShowDialog() }));
Run Code Online (Sandbox Code Playgroud)


Mg.*_*Mg. 12

如果您正在创建调用showDialog的线程,这应该有效:

var thread = new Thread(new ParameterizedThreadStart(param => { saveFileDialog.ShowDialog(); }));
 thread.SetApartmentState(ApartmentState.STA);
thread.Start();
Run Code Online (Sandbox Code Playgroud)


小智 7

添加以下代码 FormLoad

private void Form1_Load(object sender, EventArgs e)
{
    Thread myth;
    myth = new Thread(new System.Threading.ThreadStart(CallSaveDialog)); 
    myth.ApartmentState = ApartmentState.STA;
    myth.Start();
}
Run Code Online (Sandbox Code Playgroud)

CallSaveDialog是一个帖子,在这里你可以ShowDialog像这样打电话

void CallSaveDialog(){saveFileDialog.ShowDialog();}
Run Code Online (Sandbox Code Playgroud)