Erstellen eines Threads im .NET MAUI-UI-Thread
In diesem Artikel wird beschrieben, wie Sie die .NET Multi-Platform App UI (.NET MAUI) MainThread-Klasse verwenden können, um Code im Haupt-UI-Thread auszuführen. Die meisten Betriebssysteme verwenden ein Einzelthreadingmodell für Code, der die Benutzeroberfläche umfasst. Dieses Modell ist notwendig, um Ereignisse der Benutzeroberfläche, einschließlich Tastaturanschläge und Toucheingabe, ordnungsgemäß zu serialisieren. Dieser Thread wird oft als Hauptthread, Benutzeroberflächenthread oder UI-Thread bezeichnet. Der Nachteil dieses Modells ist, dass Code, der auf Elemente der Benutzeroberfläche zugreift, im Hauptthread der Anwendung ausgeführt werden muss.
Die MainThread
-Klasse befindet sich im Microsoft.Maui.ApplicationModel
-Namespace.
Wann ist dies erforderlich?
Anwendungen müssen manchmal Ereignisse verwenden, die den Ereignishandler in einem sekundären Ausführungsthread aufrufen, wie beispielsweise die Sensoren Accelerometer
oder Compass
. Alle Sensoren können bei Verwendung mit höheren Erkennungsgeschwindigkeiten Informationen in einem sekundären Thread zurückgeben. Wenn der Ereignishandler auf Elemente der Benutzeroberfläche zugreifen muss, muss er diesen Code im Hauptthread aufrufen.
Ausführen von Code im UI-Thread
Um Code im Hauptthread auszuführen, rufen Sie die statische MainThread.BeginInvokeOnMainThread-Methode auf. Das Argument ist ein Action-Objekt, das einfach eine Methode ohne Argumente und ohne Rückgabewert ist:
MainThread.BeginInvokeOnMainThread(() =>
{
// Code to run on the main thread
});
Es ist auch möglich, eine separate Methode für den Code zu definieren und dann diesen Code mit der BeginInvokeOnMainThread
-Methode aufzurufen:
void MyMainThreadCode()
{
// Code to run on the main thread
}
MainThread.BeginInvokeOnMainThread(MyMainThreadCode);
Ermitteln, ob ein Aufruf erforderlich ist
Mit der MainThread-Klasse können Sie ermitteln, ob der aktuelle Code im Hauptthread ausgeführt wird. Die MainThread.IsMainThread-Eigenschaft gibt true
zurück, wenn der Code, der die Eigenschaft aufruft, im Hauptthread ausgeführt wird, und false
, wenn dies nicht der Fall ist. Es ist logisch, davon auszugehen, dass Sie ermitteln müssen, ob der Code auf dem Hauptthread ausgeführt wird, bevor Sie MainThread.BeginInvokeOnMainThread aufrufen. Beispielsweise verwendet der folgende Code den IsMainThread
, um zu ermitteln, ob die MyMainThreadCode
-Methode direkt aufgerufen werden soll, wenn der Code im Hauptthread ausgeführt wird. Wenn er nicht im Hauptthread ausgeführt wird, wird die Methode an BeginInvokeOnMainThread
übergeben:
if (MainThread.IsMainThread)
MyMainThreadCode();
else
MainThread.BeginInvokeOnMainThread(MyMainThreadCode);
Diese Überprüfung ist nicht erforderlich. BeginInvokeOnMainThread
selbst testet, ob der aktuelle Code im Hauptthread ausgeführt wird oder nicht. Wenn der Code im Hauptthread ausgeführt wird, ruft BeginInvokeOnMainThread
die bereitgestellte Methode einfach direkt auf. Wenn der Code in einem sekundären Thread ausgeführt wird, ruft BeginInvokeOnMainThread
die bereitgestellte Methode im Hauptthread auf. Wenn der von Ihnen ausgeführte Code unabhängig vom Hauptthread oder sekundären Thread identisch ist, rufen Sie einfach BeginInvokeOnMainThread
auf, ohne zu überprüfen, ob dies erforderlich ist. Dies ist vernachlässigbarer Aufwand.
Der einzige Grund, warum Sie die IsMainThread
-Eigenschaft überprüfen müssen, besteht darin, dass Sie über Verzweigungslogik verfügen, die basierend auf dem Thread etwas anderes ausführt.
Weitere Methoden
Die MainThread-Klasse umfasst die folgenden zusätzlichen static
-Methoden, die für die Interaktion mit Elementen der Benutzeroberfläche aus Hintergrundthreads verwendet werden können:
Methode | Argumente | Rückgabe | Zweck |
---|---|---|---|
InvokeOnMainThreadAsync<T> |
Func<T> |
Task<T> |
Ruft Func<T> auf dem Hauptthread auf, und wartet auf den Abschluss. |
InvokeOnMainThreadAsync |
Action |
Task |
Ruft Action auf dem Hauptthread auf, und wartet auf den Abschluss. |
InvokeOnMainThreadAsync<T> |
Func<Task<T>> |
Task<T> |
Ruft Func<Task<T>> auf dem Hauptthread auf, und wartet auf den Abschluss. |
InvokeOnMainThreadAsync |
Func<Task> |
Task |
Ruft Func<Task> auf dem Hauptthread auf, und wartet auf den Abschluss. |
GetMainThreadSynchronizationContextAsync |
Task<SynchronizationContext> |
Gibt SynchronizationContext für den Hauptthread zurück |