Detectar la pulsación del botón de inicio en android

Esto me ha estado volviendo loco por un tiempo.

¿Hay alguna forma de detectar de forma fiable si el botón de inicio se ha pulsado en una aplicación de Android?

De no ser así, ¿hay una forma sólida de decir qué causó una actividad para entrar en la pausa? Es decir ¿Podemos detectar si fue causado por una nueva actividad de lanzamiento o por presionar back / home.

Una sugerencia que he visto es anular onPause () y llamar isFinishing (), pero esto devolverá false al presionar el botón de inicio tal como lo haría si una nueva actividad está comenzando así que esto falla en distinguir entre los dos.

Cualquier ayuda muy apreciada.

** Actualización **: Gracias a @ android-hungry para este enlace: http://nisha113a5.blogspot.com/

Sobrepasando el siguiente método:

@Override public void onAttachedToWindow() { super.onAttachedToWindow(); this.getWindow().setType(WindowManager.LayoutParams.TYPE_KEYGUARD); } 

A continuación, el siguiente evento será despedido para las pulsaciones de botón de inicio:

 @Override public boolean onKeyDown(int keyCode, KeyEvent event) { if(keyCode == KeyEvent.KEYCODE_HOME) { //The Code Want to Perform. } }); 

No estoy seguro si hay efectos secundarios con esta línea:

 this.getWindow().setType(WindowManager.LayoutParams.TYPE_KEYGUARD); 

Por lo que parece que, contrariamente a la creencia popular, en realidad puede escuchar la clave de inicio. Preocupantemente, puede devolver falso y tener la tecla de inicio no hacer nada.

Actualización : Como era de esperar, hay algunos efectos secundarios con esto – parece que los vídeos incrustados y google maps no son visibles con este modo habilitado.

Actualización : Supuestamente este hack ya no funciona como de Android 4.0 en adelante

El siguiente código funciona para mí 🙂

 HomeWatcher mHomeWatcher = new HomeWatcher(this); mHomeWatcher.setOnHomePressedListener(new OnHomePressedListener() { @Override public void onHomePressed() { // do something here... } @Override public void onHomeLongPressed() { } }); mHomeWatcher.startWatch(); 
 import android.content.BroadcastReceiver; import android.content.Context; import android.content.Intent; import android.content.IntentFilter; import android.util.Log; public class HomeWatcher { static final String TAG = "hg"; private Context mContext; private IntentFilter mFilter; private OnHomePressedListener mListener; private InnerRecevier mRecevier; public HomeWatcher(Context context) { mContext = context; mFilter = new IntentFilter(Intent.ACTION_CLOSE_SYSTEM_DIALOGS); } public void setOnHomePressedListener(OnHomePressedListener listener) { mListener = listener; mRecevier = new InnerRecevier(); } public void startWatch() { if (mRecevier != null) { mContext.registerReceiver(mRecevier, mFilter); } } public void stopWatch() { if (mRecevier != null) { mContext.unregisterReceiver(mRecevier); } } class InnerRecevier extends BroadcastReceiver { final String SYSTEM_DIALOG_REASON_KEY = "reason"; final String SYSTEM_DIALOG_REASON_GLOBAL_ACTIONS = "globalactions"; final String SYSTEM_DIALOG_REASON_RECENT_APPS = "recentapps"; final String SYSTEM_DIALOG_REASON_HOME_KEY = "homekey"; @Override public void onReceive(Context context, Intent intent) { String action = intent.getAction(); if (action.equals(Intent.ACTION_CLOSE_SYSTEM_DIALOGS)) { String reason = intent.getStringExtra(SYSTEM_DIALOG_REASON_KEY); if (reason != null) { Log.e(TAG, "action:" + action + ",reason:" + reason); if (mListener != null) { if (reason.equals(SYSTEM_DIALOG_REASON_HOME_KEY)) { mListener.onHomePressed(); } else if (reason.equals(SYSTEM_DIALOG_REASON_RECENT_APPS)) { mListener.onHomeLongPressed(); } } } } } } } 
 public interface OnHomePressedListener { public void onHomePressed(); public void onHomeLongPressed(); } 

Esta es una vieja pregunta, pero podría ayudar a alguien.

 @Override protected void onUserLeaveHint() { Log.d("onUserLeaveHint","Home button pressed"); super.onUserLeaveHint(); } 

De acuerdo con la documentación, el método onUserLeaveHint () se llama cuando el usuario hace clic en el botón de inicio O cuando algo interrumpe su aplicación (como una llamada telefónica entrante).

Esto funciona para mi

Es imposible detectar y / o interceptar el botón HOME desde una aplicación de Android. Esto está integrado en el sistema para evitar que las aplicaciones malintencionadas no puedan salir.

Necesitaba iniciar / detener música de fondo en mi aplicación cuando la primera actividad se abre y se cierra o cuando cualquier actividad se detiene en el botón de inicio y luego se reanuda desde el administrador de tareas. Pura reproducción detener / reanudar en Activity.onPause() y Activity.onResume() interrumpió la música por un tiempo, así que tuve que escribir el código siguiente:

 @Override public void onResume() { super.onResume(); // start playback here (if not playing already) } @Override public void onPause() { super.onPause(); ActivityManager manager = (ActivityManager) this.getSystemService(Activity.ACTIVITY_SERVICE); List<ActivityManager.RunningTaskInfo> tasks = manager.getRunningTasks(Integer.MAX_VALUE); boolean is_finishing = this.isFinishing(); boolean is_last = false; boolean is_topmost = false; for (ActivityManager.RunningTaskInfo task : tasks) { if (task.topActivity.getPackageName().startsWith("cz.matelier.skolasmyku")) { is_last = task.numRunning == 1; is_topmost = task.topActivity.equals(this.getComponentName()); break; } } if ((is_finishing && is_last) || (!is_finishing && is_topmost && !mIsStarting)) { mIsStarting = false; // stop playback here } } 

Que interrumpe la reproducción sólo cuando la aplicación (todas sus actividades) está cerrada o cuando se pulsa el botón de inicio. Desafortunadamente, no logré cambiar el orden de las llamadas de método onPause() de la actividad de inicio y onResume() de la actividad iniciada cuando se llama Activity.startActivity() (o detecta en onPause() que la actividad está iniciando otra actividad otra Camino) para que este caso tenga que ser manejado especialmente:

 private boolean mIsStarting; @Override public void startActivity(Intent intent) { mIsStarting = true; super.startActivity(intent); } 

Otro inconveniente es que esto requiere el permiso GET_TASKS añadido a AndroidManifest.xml :

 <uses-permission android:name="android.permission.GET_TASKS"/> 

La modificación de este código que sólo reacciona en la pulsación del botón de inicio es recta.

onUserLeaveHint() en la actividad. Nunca habrá ninguna devolución de llamada a la actividad cuando una actividad nueva se sobrepase o el usuario presiona de nuevo.

Intente crear un contador para cada pantalla. Si el usuario toca HOME, el contador será cero.

 public void onStart() { super.onStart(); counter++; } public void onStop() { super.onStop(); counter--; if (counter == 0) { // Do.. } } 

Usted podría considerar una solución de Andreas Shrade en su artículo sobre cómo crear un modo de quiosco de trabajo en Android . Es un poco hacky, pero dadas las razones que la intercepción del botón de inicio se previene tiene que ser;)

Tuve este problema, y ​​ya que anular el método onKeyDown () no logró nada debido a que el sistema subyacente de Android no llamó a este método, lo resolví con la sustitución onBackPressed (), y tuve un valor booleano establecido allí a false , Porque me presioné de nuevo, déjame mostrarte lo que quiero decir en código:

 import android.util.Log; public class HomeButtonActivity extends Activity { boolean homePressed = false; // override onCreate() here. @Override public void onBackPressed() { homePressed = false; // simply set homePressed to false } @Overide public void onResume() { super.onResume(); homePressed = true; // default: other wise onBackPressed will set it to false } @Override public void onPause() { super.onPause(); if(homePressed) { Log.i("homePressed", "yay"); } } 

Así que la razón por la que esto funcionó es porque la única manera de navegar fuera de esta actividad es presionando hacia atrás o casa por lo que si la espalda fue presionado entonces sé que la causa no estaba en casa, pero de lo contrario la causa era el hogar, por lo que estableció el booleano predeterminado Valor para el homePressed para ser verdad. Sin embargo esto sólo funcionará con una sola instancia de actividad en su aplicación porque de lo contrario tiene más posibilidades de hacer que el método onPause () sea llamado.

Una opción para su aplicación sería escribir una pantalla de inicio de reemplazo utilizando el objetivo android.intent.category.HOME. Creo que este tipo de intención se puede ver el botón de inicio.

Más detalles:

http://developer.android.com/guide/topics/intents/intents-filters.html#imatch

La aplicación promedio puede llevarse bien sin necesidad de saber la diferencia entre una prensa de inicio y un evento de pausa. En otras palabras, onPause () suele ser suficiente.

¿Por qué quieres hacer esto? Darnos más información sobre sus intenciones podría conducir a una mejor estrategia general para usted.

Puesto que solo deseas que la actividad de la raíz se vuelva a mostrar cuando se inicia la aplicación, tal vez puedas obtener este comportamiento cambiando los modos de lanzamiento, etc. en el manifiesto.

Por ejemplo, ¿ha intentado aplicar el atributo android: clearTaskOnLaunch = "true" a su actividad de lanzamiento, tal vez en tándem con android: launchMode = "singleInstance" ?

Tasks and Back Stack es un gran recurso para afinar este tipo de comportamiento.

Es una mala idea cambiar el comportamiento de la clave de inicio. Es por eso que Google no le permite anular la clave de inicio. No ensuciaría con la llave casera generalmente hablando. Usted necesita darle al usuario una forma de salir de su aplicación si se apaga en las malas hierbas por cualquier razón.

Me gustaría imagen de cualquier trabajo alrededor tendrá efectos secundarios no deseados.

  • Al hacer clic en el icono de la aplicación no se activa onOptionsItemSelected ()
  • Android - Eliminación del botón de inicio y de navegación
  • ¿Cómo agregar el relleno / margen entre el icono y el botón Arriba de la barra de acción?
  • Ocultar botón Inicio y Atrás en Android
  • SetHomeButtonEnabled en PreferenciaActividad y preferencia anidada
  • ¿Cómo lanzar el lanzador casero del defecto con código mientras que trabaja con el dispositivo verdadero?
  • Cómo configurar los márgenes de Home-Icon cuando se usa setDisplayHomeAsUpEnabled (true)?
  • El botón HOME no funciona, ¿es posible escuchar?
  • Admob en Android - Área de barra de estado no cubierta cuando se reanuda la actividad
  • Mostrar el botón Atrás en la barra de acción
  • FlipAndroid es un fan de Google para Android, Todo sobre Android Phones, Android Wear, Android Dev y Aplicaciones para Android Aplicaciones.