Presione el botón Atrás del controlador de fragmentos de Android [duplicado]
Tengo algunos fragmentos en mi actividad.
[1], [2], [3], [4], [5], [6]
Y en el botón Atrás, presione Debo regresar de [2] a [1] si el fragmento activo actual es [2], o no hacer nada en caso contrario.
¿Cuál es la mejor práctica para hacer eso?
EDITAR : La aplicación no debe regresar a [2] desde [3]...[6]
Cuando esté realizando una transición entre Fragmentos, llame addToBackStack()
como parte de su FragmentTransaction
:
FragmentTransaction tx = fragmentManager.beginTransation();
tx.replace( R.id.fragment, new MyFragment() ).addToBackStack( "tag" ).commit();
Si necesita un control más detallado (es decir, cuando algunos Fragmentos son visibles, desea suprimir la tecla Atrás), puede establecer una OnKeyListener
vista principal de su fragmento:
//You need to add the following line for this solution to work; thanks skayred
fragment.getView().setFocusableInTouchMode(true);
fragment.getView().requestFocus();
fragment.getView().setOnKeyListener( new OnKeyListener()
{
@Override
public boolean onKey( View v, int keyCode, KeyEvent event )
{
if( keyCode == KeyEvent.KEYCODE_BACK )
{
return true;
}
return false;
}
} );
Prefiero hacer algo como esto:
private final static String TAG_FRAGMENT = "TAG_FRAGMENT";
private void showFragment() {
final Myfragment fragment = new MyFragment();
final FragmentTransaction transaction = getSupportFragmentManager().beginTransaction();
transaction.replace(R.id.fragment, fragment, TAG_FRAGMENT);
transaction.addToBackStack(null);
transaction.commit();
}
@Override
public void onBackPressed() {
final Myfragment fragment = (Myfragment) getSupportFragmentManager().findFragmentByTag(TAG_FRAGMENT);
if (fragment.allowBackPressed()) { // and then you define a method allowBackPressed with the logic to allow back pressed or not
super.onBackPressed();
}
}
Si anulas el método onKey para la vista de fragmentos, necesitarás:
view.setFocusableInTouchMode(true);
view.requestFocus();
view.setOnKeyListener(new View.OnKeyListener() {
@Override
public boolean onKey(View v, int keyCode, KeyEvent event) {
Log.i(tag, "keyCode: " + keyCode);
if( keyCode == KeyEvent.KEYCODE_BACK && event.getAction() == KeyEvent.ACTION_UP) {
Log.i(tag, "onKey Back listener is working!!!");
getFragmentManager().popBackStack(null, FragmentManager.POP_BACK_STACK_INCLUSIVE);
return true;
}
return false;
}
});
Utilice el método addToBackStack cuando reemplace un fragmento por otro:
getFragmentManager().beginTransaction().replace(R.id.content_frame, fragment).addToBackStack("my_fragment").commit();
Luego en tu actividad usa el siguiente código para retroceder de un fragmento a otro (el anterior).
@Override
public void onBackPressed() {
if (getParentFragmentManager().getBackStackEntryCount() > 0) {
getParentFragmentManager().popBackStack();
} else {
super.onBackPressed();
}
}
Si desea manejar el evento de la tecla Atrás del hardware, debe seguir el siguiente código en su método onActivityCreated() de Fragment.
También debe marcar el evento Action_Down o Action_UP. Si no marca, el método onKey() se llamará 2 veces.
Además, si su rootview (getView()) no contiene el foco, entonces no funcionará. Si ha hecho clic en algún control, nuevamente debe enfocar la vista raíz usando getView().requestFocus(); Después de esto, solo se llamará onKeydown().
getView().setFocusableInTouchMode(true);
getView().requestFocus();
getView().setOnKeyListener(new OnKeyListener() {
@Override
public boolean onKey(View v, int keyCode, KeyEvent event) {
if (event.getAction() == KeyEvent.ACTION_DOWN) {
if (keyCode == KeyEvent.KEYCODE_BACK) {
Toast.makeText(getActivity(), "Back Pressed", Toast.LENGTH_SHORT).show();
return true;
}
}
return false;
}
});
Funciona muy bien para mí.