2012-06-25 6 views
18

Tengo un servicio de Android que inicia y mantiene un hilo de fondo.¿Ejecutas código en el hilo principal en Android sin acceso a una actividad?

De vez en cuando, el hilo de fondo necesita hacer una devolución de llamada en el hilo principal. Estoy perplejo sobre cómo hacer esto.

No puedo llamar this.runOnUiThread porque "this" es una instancia de Servicio, no de Actividad, y un Servicio no tiene el método runOnUiThread.

Tampoco puedo crear o ejecutar una AsyncTask, porque la documentación de AsyncTask dice que tanto el constructor como el método de ejecución deben invocarse desde el subproceso de la interfaz de usuario.

¿Necesito mantener una referencia a la actividad que está utilizando el servicio y llamar a su método runOnUiThread, o hay otra manera de ejecutar algo en el hilo de la interfaz de usuario?

Gracias.

+3

"el hilo de fondo necesita hacer una devolución de llamada en el hilo principal" - ¿por qué? – CommonsWare

+0

El usuario del servicio es una actividad. Necesita devoluciones de llamada en el hilo principal para que pueda actualizar los elementos de la interfaz de usuario. Supongo que podría recuperar el hilo de fondo y hacerlo responsable de programar una devolución de llamada de UI, pero sería más conveniente para el consumidor del servicio si pudiera hacerlo. –

+3

@Cruceo: Oh, cielos no. – CommonsWare

Respuesta

2

Su actividad tiene que puede se unen al servicio.

http://developer.android.com/guide/components/bound-services.html

Específicamente, echar un vistazo a la creación de un mensajero en esa página. La actividad del cliente puede dar un objeto de mensajería que responda a los mensajes del servicio, y una vez recibido, ejecute el código de UI necesario en el subproceso de la interfaz de usuario con un controlador.

DO NOT mantener la referencia de la actividad en el servicio. Esto puede conducir a todo tipo de problemas de memoria.

+0

Si bien 'Messenger' es una buena solución, no tiene que vincularse al servicio para usarlo. 'Messenger' es' Parcelable' y se puede enviar en un 'Intent' extra en un comando enviado a través de' startService() '. – CommonsWare

1

Sure. Ver Handler. Puede darle a su servicio un objeto controlador y cuando el servicio necesita ejecutar alguna tarea Ejecutable en el hilo de la interfaz de usuario solo debe llamar a handler.post (some_runnable_task). Esta llamada. Puede encontrar un ejemplo en este link 4.Tutorial: Handler.

9

Necesita devoluciones de llamada en el hilo principal para que pueda actualizar los elementos de la IU.

Use LocalBroadcastManager y haga que el servicio envíe una transmisión para ser recogido por la actividad, que lo obtendrá en el hilo principal de la aplicación. Here is a sample application demonstrating this.

O use una transmisión "real" con sendBroadcast().

O utilice Messenger, como mencionó you878, vinculado a un Handler, como mencionó Guillermo, aunque no necesariamente necesita usar un enlace para ello.

53

Estoy usando el siguiente código de vez en cuando si no tengo acceso directo a la actividad (por una razón u otra);

new Handler(Looper.getMainLooper()).post(mYourUiThreadRunnable); 
+4

Pensé que podría estar desactualizado, pero a finales de 2015 esta es la forma recomendada: http://developer.android.com/training/multiple-threads/communicate-ui.html – gaborsch

Cuestiones relacionadas