2017-09-11 4 views
0

Ich machte eine einfache asynchrone Methode für eine Lade-Animation, während Code ausgeführt wird. Der Code, der ausgeführt wird, fügt dem Stackpanel Steuerelemente hinzu.STA für nicht erstellt Thread/Aufgabe

in PAGE_LOADED Ereignis Ich habe gerade:

Test(); 

In Test() Ich habe

private async void Test() 
{ 
    testbtn.Visibility = Visibility.Visible; 
    await Task.Run(() => LoadAll()); 
    testbtn.Visibility = Visibility.Collapsed; 
} 

und in LoadAll() sind DockPanels usw. für exmaple:

DockPanel headerpanel = new DockPanel(); 
headerpanel.LastChildFill = false; 

Wenn dies ausgeführt wird, erhalte ich einen Fehler, weil der Thread kein STA-Thread ist. Wie kann ich es STA machen, auch wenn ich keinen Thread erstellt habe. (nur await Task.Run(() => LoadAll());)

Muss ich einen großen Thread usw. nur für eine einfache Animationsleiste erstellen, während der Code läuft?

+0

Das Markieren eines Threads als STA ist ein * Versprechen *. Die Art von Versprechen, die eine Aufgabe niemals richtig erfüllen kann. Das Versprechen zu brechen, kann übermäßig unangenehme Nebenwirkungen haben, die zum Beispiel den Finalizer-Thread blockieren. –

Antwort

2

Sie können Ihre Aufgabe in einem Scheduler ausführen, die Sie sicher erlaubt, zu UI-Code ausführen:

private async void Test() 
{ 
    testbtn.Visibility = Visibility.Visible; 
    TaskScheduler scheduler = TaskScheduler.FromCurrentSynchronizationContext(); 
    await Task.Factory.StartNew(() => LoadAll(), 
     CancellationToken.None, TaskCreationOptions.None, scheduler); 
    testbtn.Visibility = Visibility.Collapsed; 
} 
1

Muss ich ein großes Thema erstellen usw. nur für eine einfache Animation Bar, während Code ausgeführt wird?

Nein; mach einfach keine UI-Arbeit an einem Hintergrund-Thread. Verwenden Sie IProgress<T>/Progress<T> statt, z.B .:

private async void Test() 
{ 
    testbtn.Visibility = Visibility.Visible; 
    IProgress<string> progress = new Progress<string>(value => { ... }); 
    await Task.Run(() => LoadAll(progress)); 
    testbtn.Visibility = Visibility.Collapsed; 
} 

und haben LoadAll Anruf progress.Report("update"), wenn es die Benutzeroberfläche aktualisieren will.

Verwandte Themen