web-dev-qa-db-fra.com

Accéder au gestionnaire de thread d'interface utilisateur à partir d'un service

J'essaie quelque chose de nouveau sur Android pour lequel je dois accéder au gestionnaire du fil de l'interface utilisateur.

Je sais ce qui suit:

  1. Le thread d'interface utilisateur a son propre gestionnaire
  2. Tout message sera placé Dans la file de messages du fil de l'interface utilisateur
  3. Le looper prend l'événement .__ et le transmet au gestionnaire 
  4. Le gestionnaire gère le message et Envoie l'événement specfic à l'interface utilisateur

Je veux avoir mon service qui doit obtenir le gestionnaire de thread d'interface utilisateur et mettre un message dans ce gestionnaire . Ainsi, ce message sera traité et sera envoyé à l'interface utilisateur . service qui sera lancé par une application.

Je voudrais savoir si cela est possible… .. Si c'est le cas, merci de suggérer des extraits de code afin que je puisse l'essayer.

Cordialement Girish

85
iLikeAndroid

Cet extrait de code construit un gestionnaire associé au thread principal (UI):

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

Vous pouvez ensuite poster des éléments à exécuter dans le fil principal (UI) comme suit:

handler.post(runnable_to_call_from_main_thread);

Si le gestionnaire lui-même est créé à partir du thread principal (UI), l'argument peut être omis par souci de concision:

Handler handler = new Handler();

Le Guide de développement Android sur les processus et les threads contient plus d'informations.

170
volley

Créez un objet Messenger attaché à votre Handler et transmettez ce Messenger à Service (par exemple, dans un Intent extra pour startService()). La Service peut alors envoyer une Message à la Handler via la Messenger. Voici un exemple d'application en démontrant ceci.

28
CommonsWare

Pour le moment, je préfère utiliser une bibliothèque de bus d’événements telle que Otto pour ce type de problème. Il suffit de souscrire les composants souhaités (activité):

protected void onResume() {
    super.onResume();
    bus.register(this);
}

Ensuite, fournissez une méthode de rappel:

public void onTimeLeftEvent(TimeLeftEvent ev) {
    // process event..
}

et ensuite, lorsque votre service exécute une instruction comme celle-ci:

bus.post(new TimeLeftEvent(340));

Ce POJO sera transmis à votre activité ci-dessus et à tous les autres composants abonnés. Simple et élégant.

4
pram

Vous pouvez obtenir des valeurs via le récepteur de diffusion ...... comme suit, créez d’abord votre propre IntentFilter en tant que,

Intent intentFilter=new IntentFilter();
intentFilter.addAction("YOUR_INTENT_FILTER");

Puis créez la classe intérieure BroadcastReceiver en tant que,

    private BroadcastReceiver broadcastReceiver = new BroadcastReceiver() {
    /** Receives the broadcast that has been fired */
    @Override
    public void onReceive(Context context, Intent intent) {
        if(intent.getAction()=="YOUR_INTENT_FILTER"){
           //HERE YOU WILL GET VALUES FROM BROADCAST THROUGH INTENT EDIT YOUR TEXTVIEW///////////
           String receivedValue=intent.getStringExtra("KEY");
        }
    }
};

Enregistrez maintenant votre récepteur de diffusion dans onResume () en tant que,

registerReceiver(broadcastReceiver, intentFilter);

Et enfin, annulez l'enregistrement de BroadcastReceiver dans onDestroy () en tant que,

unregisterReceiver(broadcastReceiver);

Maintenant, la partie la plus importante ... Vous devez lancer la diffusion de partout où vous avez besoin d'envoyer des valeurs ..... alors faites comme,

Intent i=new Intent();
i.setAction("YOUR_INTENT_FILTER");
i.putExtra("KEY", "YOUR_VALUE");
sendBroadcast(i);

....à votre santé :)

2
Melbourne Lopes

Je suggère d'essayer le code suivant:

    new Handler(Looper.getMainLooper()).post(() -> {

        //UI THREAD CODE HERE



    });
0
user2983041

Dans kotlin c'est comment vous pouvez le faire

Laisser dire si vous voulez montrer le message Toast du service

val handler = Handler(Looper.getMainLooper())
handler.post {
   Toast.makeText(context, "This is my message",Toast.LENGTH_LONG).show()
}
0
Zohab Ali

Solution:

  1. Créez un Handler avec Looper à partir du thread principal: requestHandler
  2. Créer une Handler avec Looper à partir du thread principal: responseHandler et remplacer la méthode handleMessage
  3. publie une tâche Runnable sur requestHandler
  4. Dans la tâche Runnable, appelez sendMessage sur responseHandler
  5. Cet invocation de résultat sendMessage de handleMessage dans responseHandler.
  6. Obtenir les attributs de la Message et le traiter, mettre à jour l'interface utilisateur

Exemple de code:

    /* Handler from UI Thread to send request */

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

     /* Handler from UI Thread to process messages */

    final Handler responseHandler = new Handler(Looper.getMainLooper()) {
        @Override
        public void handleMessage(Message msg) {

            /* Processing handleMessage */

            Toast.makeText(MainActivity.this,
                    "Runnable completed with result:"+(String)msg.obj,
                    Toast.LENGTH_LONG)
                    .show();
        }
    };

    for ( int i=0; i<10; i++) {
        Runnable myRunnable = new Runnable() {
            @Override
            public void run() {
                try {
                   /* Send an Event to UI Thread through message. 
                      Add business logic and prepare message by 
                      replacing example code */

                    String text = "" + (++rId);
                    Message msg = new Message();

                    msg.obj = text.toString();
                    responseHandler.sendMessage(msg);
                    System.out.println(text.toString());

                } catch (Exception err) {
                    err.printStackTrace();
                }
            }
        };
        requestHandler.post(myRunnable);
    }
0
Ravindra babu