Anular el botón Atrás para actuar como botón de inicio

253

Al presionar el botón Atrás, me gustaría que mi aplicación pase al estado detenido, en lugar del estado destruido.

En los documentos de Android dice:

... no todas las actividades tienen el comportamiento de que se destruyen cuando se presiona BACK. Cuando el usuario comienza a reproducir música en la aplicación Música y luego presiona ATRÁS, la aplicación anula el comportamiento normal de la espalda, evita que se destruya la actividad del reproductor y continúa reproduciendo música, aunque su actividad ya no sea visible

¿Cómo replicar esta funcionalidad en mi propia aplicación?

Creo que debe haber tres posibilidades ...

  1. Capture el botón de retroceso presione (como se muestra a continuación) y luego llame a cualquier método que llame el botón de inicio.

    @Override
    public boolean onKeyDown(int keyCode, KeyEvent event) {
        if ((keyCode == KeyEvent.KEYCODE_BACK)) {
            Log.d(this.getClass().getName(), "back button pressed");
        }
        return super.onKeyDown(keyCode, event);
    }
  2. Capture el botón de retroceso y luego falsifique el botón de inicio.

  3. Capture el botón de retroceso, luego inicie una Actividad de la pantalla de inicio, poniendo efectivamente la Actividad de mi aplicación en el estado detenido.

Editar: conozco los servicios y estoy usando uno en la aplicación con la que está relacionado este problema. Esta pregunta es específicamente acerca de poner la Actividad en el estado detenido en lugar del estado destruido al presionar el botón Atrás.

bdls
fuente
vea una respuesta similar stackoverflow.com/questions/5914040/…
Zar E Ahmer

Respuestas:

338

La mayoría de las veces necesita crear un Servicio para realizar algo en segundo plano, y su visible Activitysimplemente lo controla Service. (Estoy seguro de que el reproductor de música funciona de la misma manera, por lo que el ejemplo en los documentos parece un poco engañoso). Si ese es el caso, entonces su Activitylata finishcomo de costumbre y Serviceseguirá funcionando.

Un enfoque más simple es capturar la Backpresión del botón y llamar a moveTaskToBack (verdadero) de la siguiente manera:

// 2.0 and above
@Override
public void onBackPressed() {
    moveTaskToBack(true);
}

// Before 2.0
@Override
public boolean onKeyDown(int keyCode, KeyEvent event) {
    if (keyCode == KeyEvent.KEYCODE_BACK) {
        moveTaskToBack(true);
        return true;
    }
    return super.onKeyDown(keyCode, event);
}

Creo que la opción preferida debería ser que una Actividad finalice normalmente y pueda recrearse, por ejemplo, leer el estado actual de un Servicio si es necesario. Pero moveTaskToBackpuede usarse como una alternativa rápida en ocasiones.

NOTA : como señaló Dave a continuación, Android 2.0 introdujo un nuevo onBackPressedmétodo y estas recomendaciones sobre cómo manejar el botón Atrás.

Mirko N.
fuente
1
moveTaskToBack () parece funcionar según lo deseado. ¿Cuáles podrían ser las desventajas de usar este método? ¿Hay casos en los que esto podría no funcionar como se esperaba?
bdls
1
Después de leer su documento con más cuidado, creo que debería funcionar bien. (Inicialmente pensé que se aplicaba a la actividad, pero de hecho dice "la tarea que contiene esta actividad"). Pero, por supuesto, debe probarlo usted mismo. :)
Mirko N.
Gracias Mirko, el método parece funcionar bien. Sería genial si le das más importancia a tu edición en la parte inferior de tu respuesta para quienes examinen esta pregunta más adelante, ¡ya que eso era lo que estaba buscando!
bdls
44
Lea android-developers.blogspot.com/2009/12/… para conocer la forma recomendada de manejar la tecla de retroceso.
hackbod
1
@bdls en teoría, su actividad en segundo plano podría ser eliminada por el sistema si se queda sin recursos, por lo que para estar seguro, debería poder recrearse de todos modos. Eché un vistazo al código fuente de la aplicación Android Music y no veo ningún manejo especial del botón de retroceso.
Mirko N.
46

Utiliza el siguiente código:

public void onBackPressed() {    
    Intent intent = new Intent();
    intent.setAction(Intent.ACTION_MAIN);
    intent.addCategory(Intent.CATEGORY_HOME);
    startActivity(intent);
}
Aniruddh Ambarkar
fuente
23

Si desea ver el botón Atrás, eche un vistazo a esta publicación en el Blog para desarrolladores de Android . Cubre la forma más fácil de hacer esto en Android 2.0 y la mejor manera de hacerlo para una aplicación que se ejecuta en 1.xy 2.0.

Sin embargo, si su actividad se detiene, aún puede ser eliminada dependiendo de la disponibilidad de memoria en el dispositivo. Si desea que se ejecute un proceso sin interfaz de usuario, debe crear un Service. La documentación dice lo siguiente sobre los Servicios:

Un servicio no tiene una interfaz de usuario visual, sino que se ejecuta en segundo plano durante un período de tiempo indefinido. Por ejemplo, un servicio puede reproducir música de fondo mientras el usuario atiende otros asuntos, o puede obtener datos a través de la red o calcular algo y proporcionar el resultado a las actividades que lo necesitan.

Esto parece apropiado para sus requisitos.

Dave Webb
fuente
14

si ayuda a alguien más, tuve una actividad con 2 diseños que activaba y desactivaba para la visibilidad, tratando de emular una especie de estructura página1> página2. si estaban en la página 2 y presionaron el botón de retroceso, quería que volvieran a la página 1, si presionaron el botón de retroceso en la página 1, aún debería funcionar normalmente. Es bastante básico pero funciona

@Override
public void onBackPressed() {
// check if page 2 is open
    RelativeLayout page2layout = (RelativeLayout)findViewById(R.id.page2layout);
    if(page2layout.getVisibility() == View.VISIBLE){
        togglePageLayout(); // my method to toggle the views
        return;
    }else{
        super.onBackPressed(); // allows standard use of backbutton for page 1
    }

}

espero que ayude a alguien, salud

Craigk
fuente
10

Ejemplo de trabajo ..

Asegúrese de no llamar a super.onBackPressed ();

@Override
public void onBackPressed() {
   Log.d("CDA", "onBackPressed Called");
   Intent setIntent = new Intent(Intent.ACTION_MAIN);
   setIntent.addCategory(Intent.CATEGORY_HOME);
   setIntent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
   startActivity(setIntent);
}

De esta manera, el botón Atrás actúa como el botón Inicio. No termina tu actividad, pero llévala a un segundo plano.

La segunda manera es llamar moveTaskToBack(true);en onBackPressedy asegúrese de retirarsuper.onBackPressed

Zar E Ahmer
fuente
0

Aún mejor, ¿qué tal OnPause () :

Se llama como parte del ciclo de vida de la actividad cuando una actividad pasa a un segundo plano, pero (todavía) no se ha eliminado. La contraparte de onResume ().

Cuando se inicia la actividad B frente a la actividad A, esta devolución de llamada se invocará en A. B no se creará hasta que regrese onPause () de A, así que asegúrese de enter code hereno hacer nada largo aquí.

Esta devolución de llamada se usa principalmente para guardar cualquier estado persistente que la actividad esté editando y asegurarse de que no se pierda nada si no hay suficientes recursos para comenzar la nueva actividad sin matar primero esta.

Este también es un buen lugar para hacer cosas como detener las animaciones y otras cosas que consumen una cantidad notable de CPU para hacer el cambio a la siguiente actividad lo más rápido posible, o para cerrar recursos que son de acceso exclusivo como la cámara.

usuario1524315
fuente
0

Anular onBackPressed () después de Android 2.0. Como

@Override
public void onBackPressed() {
    moveTaskToBack(true);
}
SaiLiu
fuente
0

He probado todas las soluciones anteriores, pero ninguna de ellas funcionó para mí. El siguiente código me ayudó cuando traté de volver a MainActivity de una manera que se llama a onCreate:

Intención.FLAG_ACTIVITY_CLEAR_TOP es la clave.

  @Override
  public void onBackPressed() {
      Intent intent = new Intent(this, MainActivity.class);
      intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_CLEAR_TOP);
      startActivity(intent);
  }
ubulon
fuente
-1

He usado @Mirko N. answser usando el nuevo Custom EditText

 public class EditViewCustom extends EditText {

    Button cancelBtn;
    RelativeLayout titleReleLayout;
    public EditViewCustom(Context context, AttributeSet attrs, int defStyle) {
        super(context, attrs, defStyle);
    }

    public EditViewCustom(Context context, AttributeSet attrs) {
        super(context, attrs);
    }

    public EditViewCustom(Context context) {
        super(context);
    }

    public void setViews(Button cancelBtn,RelativeLayout titleReleLayout){
        this.cancelBtn = cancelBtn;
        this.titleReleLayout = titleReleLayout;
    }

    @Override
    public boolean onKeyPreIme(int keyCode, KeyEvent event) {
        if (event.getKeyCode() == KeyEvent.KEYCODE_BACK) {
            Log.d("KEYCODE_BACK","KEYCODE_BACK");
            cancelBtn.setVisibility(View.GONE);
            this.setFocusableInTouchMode(false);
            this.setFocusable(false);
            titleReleLayout.setVisibility(View.VISIBLE);

            return super.onKeyPreIme(keyCode, event);
          }

        return super.onKeyPreIme(keyCode, event);
    }

}

Luego establezca datos de su actividad

 searchEditView.setViews(cancelBtn, titleRelativeLayout);

Gracias.

Sameer Z.
fuente