401 Stimmen

Ausführen von Code im Hauptthread von einem anderen Thread aus

In einem Android-Dienst habe ich Thread(s) erstellt, um einige Hintergrundaufgaben zu erledigen.

Ich habe eine Situation, in der ein Thread eine bestimmte Aufgabe in die Nachrichtenwarteschlange des Hauptthreads stellen muss, zum Beispiel eine Runnable .

Gibt es eine Möglichkeit, die Handler des Hauptthemas und posten Message / Runnable aus meinem anderen Thread?

702voto

David Wasser Punkte 89884

HINWEIS: Diese Antwort hat so viel Aufmerksamkeit erregt, dass ich sie aktualisieren muss. Seit die ursprüngliche Antwort gepostet wurde, hat der Kommentar von @dzeikei fast so viel Aufmerksamkeit erhalten wie die ursprüngliche Antwort. Hier sind also 2 mögliche Lösungen:

1. Wenn Ihr Hintergrund-Thread einen Verweis auf eine Context Objekt:

Stellen Sie sicher, dass Ihre Hintergrund-Worker-Threads Zugriff auf ein Context-Objekt haben (dies kann der Anwendungs- oder der Service-Kontext sein). Dann tun Sie dies einfach im Hintergrundworker-Thread:

// Get a handler that can be used to post to the main thread
Handler mainHandler = new Handler(context.getMainLooper());

Runnable myRunnable = new Runnable() {
    @Override 
    public void run() {....} // This is your code
};
mainHandler.post(myRunnable);

2. Wenn Ihr Hintergrund-Thread keinen eigenen Thread hat (oder braucht) Context Objekt

(vorgeschlagen von @dzeikei):

// Get a handler that can be used to post to the main thread
Handler mainHandler = new Handler(Looper.getMainLooper());

Runnable myRunnable = new Runnable() {
    @Override 
    public void run() {....} // This is your code
};
mainHandler.post(myRunnable);

164voto

Alexey Vassiliev Punkte 2249

Wie ein Kommentator weiter unten richtig bemerkte, ist dies keine allgemeine Lösung für Dienste, sondern nur für Threads, die von Ihrer Aktivität aus gestartet werden (ein Dienst kann ein solcher Thread sein, aber nicht alle sind es). Zu dem komplizierten Thema der Kommunikation zwischen Dienst und Aktivität lesen Sie bitte den gesamten Abschnitt "Dienste" in der offiziellen Dokumentation - es ist komplex, daher lohnt es sich, die Grundlagen zu verstehen: http://developer.Android.com/guide/components/services.html#Notifications

Die folgende Methode kann in den einfachsten Fällen funktionieren:

Wenn ich Sie richtig verstehe, benötigen Sie Code, der im GUI-Thread der Anwendung ausgeführt wird (ich kann mir keinen anderen Thread vorstellen, der "main" heißt). Hierfür gibt es eine Methode auf Activity :

someActivity.runOnUiThread(new Runnable() {
        @Override
        public void run() {
           //Your code to run in GUI thread here
        }//public void run() {
});

Doc: http://developer.Android.com/reference/Android/app/Activity.html#runOnUiThread%28java.lang.Runnable%29

Ich hoffe, das ist, wonach Sie suchen.

105voto

Sazzad Hissain Khan Punkte 33230

Kotlin-Versionen

Wenn Sie sind auf einer Aktivität verwenden, dann

runOnUiThread {
    //code that runs in main
}

Wenn Sie haben einen Aktivitätskontext , mContext dann verwenden

mContext.runOnUiThread {
    //code that runs in main
}

Wenn Sie an einem Ort sind, an dem kein Kontext verfügbar verwenden, dann

Handler(Looper.getMainLooper()).post {  
    //code that runs in main
}

33voto

tema_man Punkte 443

Es gibt eine weitere einfache Möglichkeit, wenn Sie keinen Zugang zum Kontext haben.

1). Erstellen Sie einen Handler aus dem Hauptlooper:

Handler uiHandler = new Handler(Looper.getMainLooper());

2). Implementieren Sie eine Runnable-Schnittstelle:

Runnable runnable = new Runnable() { // your code here }

3). Senden Sie Ihr Runnable an den uiHandler:

uiHandler.post(runnable);

Das ist alles ;-) Viel Spaß mit den Threads, aber vergessen Sie nicht, sie zu synchronisieren.

32voto

david m lee Punkte 2317

Ein komprimierter Codeblock sieht wie folgt aus:

   new Handler(Looper.getMainLooper()).post(new Runnable() {
       @Override
       public void run() {
           // things to do on the main thread
       }
   });

Dabei wird weder die Aktivitätsreferenz noch die Anwendungsreferenz weitergegeben.

Kotlin-Äquivalent:

    Handler(Looper.getMainLooper()).post(Runnable {
        // things to do on the main thread
    })

CodeJaeger.com

CodeJaeger ist eine Gemeinschaft für Programmierer, die täglich Hilfe erhalten..
Wir haben viele Inhalte, und Sie können auch Ihre eigenen Fragen stellen oder die Fragen anderer Leute lösen.

Powered by:

X