C# Winforms: How to Set Main Function Stathreadattribute

C# WinForms: How to set Main function STAThreadAttribute

ShowDialog() shouldn't be called from a background thread - use Invoke(..).

Invoke((Action)(() => { saveFileDialog.ShowDialog() }));

Current thread must be set to single thread apartment (STA) error in copy string to clipboard

Make sure thread that runs the code is marked with [STAThread] attribute. For WinForm and console based apps it is generally Main method

Put [STAThread] above your main method:

[STAThread]
static void Main()
{
}

For WinForms it is usually in generated Main.cs file that you can edit if necessary (it will not be re-generated on changes). For console it's were you define the Main.

If you can't control the thread (i.e. you are writing a library or main app is locked by some reason) you can instead run code that accesses clipboard on specially configured thread (.SetApartmentState(ApartmentState.STA)) as shown in another answer.

How to handle {STAThread] in C# 9 Using Top-Level Program.cs

using System.Threading;
using System.Windows.Forms;
using MapLines;

var thread = new Thread(() =>
{
Application.SetHighDpiMode(HighDpiMode.SystemAware);
Application.EnableVisualStyles();
Application.SetCompatibleTextRenderingDefault(false);
Application.Run(new MainForm());
});
thread.SetApartmentState(ApartmentState.STA);
thread.Start();

C# Thread - STAThreadAttribute exception

nb. This is pretty dodgy - Windows Forms is designed to run all Forms and Controls through a single thread, but that doesn't mean you won't get it to work. You do need to make sure that you create things in the same thread which they run in though, so try changing it so that you are creating the form inside the thread too...

  static void HotKeyManager_HotKeyPressed(object sender, HotKeyEventArgs e)
{
switch (e.Key)
{
case Keys.D1:

var thread1 = new Thread(new ParameterizedThreadStart(param => { CaptureAreaOfScreenForm caos2 = new CaptureAreaOfScreenForm();caos2.Show(); }));
thread1.SetApartmentState(ApartmentState.STA);
thread1.Start();
break;
case Keys.D2:
CaptureWorkingArea cwa2 = new CaptureWorkingArea();
var thread2 = new Thread(new ParameterizedThreadStart(param => { cwa2.CaptureTheWorkingArea(); }));
thread2.SetApartmentState(ApartmentState.STA);
thread2.Start();
break;
case Keys.D3:
CaptureFullScreen cfs2 = new CaptureFullScreen();
var thread3 = new Thread(new ParameterizedThreadStart(param => { cfs2.CaptureDesktop(); }));
thread3.SetApartmentState(ApartmentState.STA);
thread3.Start();
break;
case Keys.D4:
CaptureAllScreens cas2 = new CaptureAllScreens();
var thread4 = new Thread(new ParameterizedThreadStart(param => { cas2.CaptureScreens(); }));
thread4.SetApartmentState(ApartmentState.STA);
thread4.Start();
break;
case Keys.D5:
UploadFromFile uff2 = new UploadFromFile();
var thread5 = new Thread(new ParameterizedThreadStart(param => { uff2.UploadFile(); }));
thread5.SetApartmentState(ApartmentState.STA);
thread5.Start();
break;
}
//collect the garbage
GC.Collect();
}

Why are WinForms applications STAThread by default?

1. Why is this attribute added?

Because it is required by the ActiveX object model. And you can drop ActiveX controls on a WinForm (so it is there for compatibility) OR some .NET classes use native controls which require that attribute.

2. What does it mean?

It means the thread runs in the single-threaded apartment model.

3. What happens if you remove this attribute?

If the attribute is removed, the behavior is undefined. The program may fail at random, with sometimes sensible error messages. For example, things may work now, then break with a service pack.



Related Topics



Leave a reply



Submit