2012-01-18 19 views
9

Por lo tanto, estoy transmitiendo música en un hilo separado. Si salgo de la aplicación (onPause(), onStop() llamándome, etc.), la música continúa sonando, pero al final, después de abrir otras aplicaciones y alternar entre ellas y volver a la pantalla de inicio, mi aplicación muere. Sin fallas, solo un WIN DEATH y process com.myapp.android has died en logcat. Obviamente, es legítimo que el sistema destruya las aplicaciones para recuperar recursos.MediaPlayer en el hilo separado vs ejecutando en el servicio a través de startForeground()

Mi pregunta es: ¿ejecutar cosas en un hilo fuera del hilo principal (UI) significa que ahora tiene menos prioridad en lo que respecta al sistema? Es decir, ¿es más probable que se muera que si ejecuto el reproductor multimedia en un Service e incluso uso startForeground() para hacer que el servicio se ejecute en primer plano?

¡Cualquier idea o aclaración sería muy apreciada!

EDITAR

Además, parte de la documentación relativa a los servicios que me confunde. En su parte pertinente, establece:

Precaución: Un servicio se ejecuta en el hilo principal de su proceso en el servicio alojamiento no crea su propio hilo y no se ejecuta en un proceso independiente (a menos que se especifique lo contrario) Esto significa que, si su servicio va a hacer un trabajo intensivo de CPU o bloquear operaciones (como reproducción de MP3 o redes), debe crear un nuevo subproceso dentro del servicio para hacer ese trabajo.

Siempre he ejecutado la reproducción de MP3 en un servicio en el hilo principal y la interfaz de usuario sigue siendo receptiva. Si se supone que debo ponerlo en un hilo separado como se recomienda en la cita anterior, entonces no volveré al punto donde comencé, es decir, con la reproducción de medios fuera del hilo principal, aumentando así la probabilidad de que la reproducción muere cuando se abren otras aplicaciones, etc.?

Respuesta

2

Creo que la mayoría de su pregunta se responde en el Android documentation on Services.

Desde el enlace:

un servicio de primer plano es un servicio que se considera que es algo el usuario es consciente de manera activa y por lo tanto no es un candidato para el sistema a matar cuando bajo de memoria. Un servicio en primer plano debe proporcionar una notificación para la barra de estado, que se ubica bajo el encabezado "En curso" , lo que significa que la notificación no puede descartarse a menos que el servicio se detenga o elimine del primer plano.

Para responder a su pregunta, sí, la ejecución de un Thread separada fuera de un Activity va a tener la prioridad más baja que un Service se ejecuta en el primer plano, si el Activity que inició la Thread ha sido detenido/pausa.

Personalmente, yo recomiendo hacer esto en un Service, ya que este es exactamente el tipo de cosas la clase Service ha sido creado para.

Editar:

interesante, lo que sugiere parece contrario a lo que he leído (todo es sensible cuando no se utiliza el hilo en Service). De todos modos, probablemente debería iniciarse en un hilo de fondo.

El hilo (un hilo que USTED crea) no morirá a menos que el proceso muera, y eso sucederá cuando el tiempo de ejecución decida que se necesitan recursos. Activity se pueden matar cuando no están en primer plano, por lo que también se pueden destruir sus Thread. Si tiene un Service marcado como primer plano, es menos probable que se destruya y, por lo tanto, no debería tener el mismo problema.

+0

Gracias! ¿Puedes abordar mi edición? – LuxuryMode

+1

He colocado mi reproductor multimedia dentro de un servicio y fuera de uno ejecutándose en su propio hilo. Android matará al reproductor multimedia independientemente de dónde se encuentre si necesita más recursos. Y no es menos probable que se mate en un servicio que tiene prioridad de primer plano que en un hilo separado. El único lugar donde parece que nunca mueren es en una actividad que actualmente está en primer plano. – AndroidDev

-1

No hay necesidad de ejecutar un MediaPlayer desde un hilo. Siempre que use MediaPlayer.prepareAsync, en lugar de MediaPlayer.prepare, no hay métodos en MediaPlayer que se bloqueen lo suficiente como para causar problemas. Ejecútelo en el hilo de primer plano de su Servicio.

Si su proceso es asesinado, los hilos van con él. Los procesos que alojan los Servicios tienen una vida más larga que las Actividades, siempre que llame al método Service.startForeground (y muestre la notificación obligatoria solicitada por startForeground en la barra de estado). Tan pronto como una actividad se detiene, todo el proceso se convierte en un candidato principal para el reciclaje (asumiendo que no hay un servicio en primer plano en el proceso también).

+4

Desafortunadamente, mientras que la documentación parece indicar que prepareAsync() es lo suficientemente bueno, no es suficiente. Otras llamadas además de prepare() pueden colgar la aplicación, por lo que es mejor que una instancia de MediaPlayer esté en su propio hilo. – ajacian81

7

Acabo de publicar parte de esta respuesta en otro lugar, pero sigue siendo relevante.

Desafortunadamente, llamar a prepareAsync() simplemente no es lo suficientemente bueno como para evitar que las solicitudes ANR y la aplicación se cuelguen durante unos segundos, especialmente si está reproduciendo un archivo de la red. Su mejor opción es colocar su instancia de MediaPlayer en su propio hilo, o al menos ejecutar llamadas intensivas en un controlador (como mediaplayer.start()). He estado usando MediaPlayer durante más de un año y puedo decir que definitivamente se cuelga después de varias llamadas, dependiendo de las circunstancias.

Lo ideal es que genere un hilo que controle su MediaPlayer desde un Servicio. De esta manera, se asegura de que sus medios continúen reproduciéndose mientras su aplicación está en segundo plano y cualquier llamada de bloqueo (aparte de prepare()/prepareAsync()) no cuelga su aplicación.

+1

Estoy de acuerdo. Sin embargo, debo agregar que he visto al mediaplayer terminar incluso en un hilo generado por un servicio. Parece que el reproductor de medios tiene su propio enhebrado interno que tiene una prioridad incluso menor que un servicio en primer plano y que Android está más dispuesto a eliminar un hilo engendrado antes de que finalice el servicio. – AndroidDev

+0

Entonces, creo que esto resuelve el problema mejor que el aceptado. De todos modos, lo que quiero saber es, ¿necesito ejecutar un hilo separado incluso en un servicio? Actualmente, estoy usando un proceso completamente diferente pero quiero moverlo al proceso principal. – frostymarvelous

+0

El servicio se ejecuta de forma predeterminada en el subproceso principal de la interfaz de usuario. Podemos crear un Thread/AsyncTask en el Servicio. Eso es más o menos cómo lo haría. – ajacian81

Cuestiones relacionadas