많은 UI 구성 요소가이를 필요로하기 때문에 호출 스레드는 STA이어야합니다.


174

http://www.codeproject.com/KB/IP/Facebook_API.aspx를 사용하고 있습니다 .

WPF를 사용하여 만든 XAML 을 호출하려고합니다 . 그러나 그것은 나에게 오류를 준다 :

많은 UI 구성 요소에 필요하기 때문에 호출 스레드는 STA이어야합니다.

어떻게해야할지 모르겠습니다. 나는 이것을하려고합니다 :

FacebookApplication.FacebookFriendsList ffl = new FacebookFriendsList();

그러나 그것은 저에게 그 오류를주고 있습니다.

백그라운드 작업자를 추가했습니다.

static BackgroundWorker bw = new BackgroundWorker();

static void Main(string[] args)
{
    bw.DoWork += bw_DoWork;
    bw.RunWorkerAsync("Message to worker");
    Console.ReadLine();
}

static void bw_DoWork(object sender, DoWorkEventArgs e)
{
    // This is called on the worker thread
    FacebookApplication.FacebookFriendsList ffl = new FacebookFriendsList();

    Console.WriteLine(e.Argument);        // Writes "Message to worker"

    // Perform time-consuming task...
}

답변:


222

디스패처 에서 코드를 호출하십시오 .

Application.Current.Dispatcher.Invoke((Action)delegate{
      // your code
});

그래, 너희들은 내 목숨을 구했어 !!
Alex McManns

11
이것이 실제 답변입니다. 이것으로 WPF의 창 어리 석음을 해킹 할 수 있습니다.
Andrew

7
이와 유사하게 MVVMLight를 사용하는 경우 다음을 사용할 수 있습니다.DispatcherHelper.CheckBeginInvokeOnUI(Action action)
TimothyP

이 문제는 복잡하고 좌절 해 보였지만이 장면은 정말 멋집니다! 정말 고맙습니다 !
Kay Lee

4
@Andrew 어리석은 것이 아니라 단순히 백그라운드 스레드에서 UI 스레드에 액세스하려고합니다.
Krusty

139

메인 스레드에서 호출하는 경우 이전 답변에서 설명한대로 STAThread 속성을 Main 메서드에 추가해야합니다.

별도의 스레드를 사용하는 경우 STA (단일 스레드 아파트)에 있어야하며 백그라운드 작업자 스레드의 경우에는 해당되지 않습니다. 다음과 같이 스레드를 직접 작성해야합니다.

Thread t = new Thread(ThreadProc);
t.SetApartmentState(ApartmentState.STA);

t.Start();

ThreadProc는 ThreadStart 유형의 대리자입니다.


2
이 (STA를 사용하여) 가능한 부작용이 있습니까?
Louis Rhys

10
STA의 주요 부작용은 동시 COM 콜백이 직렬화된다는 것입니다. COM 콜백을 사용하지 않는 경우에는 문제가되지 않습니다.
Timores

내 목숨을 구했다! 서로 다른 두 앱 간의 통합을 위해 로컬 API를 호스팅 한 WPF 앱에서이 기능을 사용할 수있었습니다!
schizoid04

18

당신은 또한 이것을 시도 할 수 있습니다

// create a thread  
Thread newWindowThread = new Thread(new ThreadStart(() =>  
{  
    // create and show the window
    FaxImageLoad obj = new FaxImageLoad(destination);  
    obj.Show();  

    // start the Dispatcher processing  
    System.Windows.Threading.Dispatcher.Run();  
}));  

// set the apartment state  
newWindowThread.SetApartmentState(ApartmentState.STA);  

// make the thread a background thread  
newWindowThread.IsBackground = true;  

// start the thread  
newWindowThread.Start();  

감사. 이것은 Form 대신 Applicationcontext 클래스를 사용할 때 도움이됩니다.
SaddamBinSyed

다른 여러 곳에서와 같이 버튼을 클릭하면 새 양식이 열립니다. 왜 그 장소들 중 하나만 이이 오류를 던지고 있습니까?
Paul McCarthy

17

백그라운드 스레드에서 UI 구성 요소에 콜백을 받고 있다고 의심됩니다. UI 스레드를 인식하므로 BackgroundWorker를 사용하여 호출하는 것이 좋습니다.

BackgroundWorker의 경우 기본 프로그램은 [STAThread]로 표시되어야합니다.


1
위와 같이 추가를 시도했지만 여전히 오류가 발생합니다 : /
C ..

나는 코드에 친숙하지 않다. 이 문제를 일으키는 코드 줄을 정확하게 디버깅하고 찾을 수 있습니까?
Preet Sangha

3

프로그램에 [STAThread]속성을 표시하면 오류가 사라집니다! 그것은 마술이다 :)


1

나 에게이 오류는 null 매개 변수가 전달되어 발생했습니다. 변수 값을 확인하면 코드를 변경하지 않고도 문제가 해결되었습니다. BackgroundWorker를 사용했습니다.


-3

기존 스레드에서 새 창 UI 문을 호출하면 오류가 발생합니다. 그 대신 기본 스레드 내에 새 스레드를 만들고 새 자식 스레드에 창 UI 문을 작성하십시오.


pls를 작성하는 방법 설명?
Tushar Gupta-curioustushar
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.