web-dev-qa-db-fra.com

FragmentManager popBackStack ne supprime pas le fragment

J'implémente la navigation dans les menus avec des fragments. Je commence donc par Home, puis les utilisateurs peuvent accéder aux différentes sections et aux détails de chaque section.

Lorsqu'un utilisateur change de section, j'appelle pop sur le backstack de fragmentmanager jusqu'à ce que j'atteigne Home, puis charge la nouvelle section.

Tout cela fonctionne comme prévu. Mais je reçois ce problème:

  1. charge une section qui appelle setHasOptionsMenu (true) sur onResume ()
  2. charge une autre section (ancienne section sur laquelle on peut sortir de la pile). Je le vois bien. Aucun menu n'est affiché
  3. quittez l'application (par exemple, accédez à l'activité Android Laucher), puis à mon retour, je vois la bonne section, mais le menu de l'ancien fragment s'affiche.

J'ai réitéré le backstack et imprimé chaque fragment, et là ce n'est pas le fragment avec le menu. 

Je mets une marque de débogage sur la méthode onResume () (où la fonction setHasOptionsMenu(true) est marquée) et elle entre en effet ici, donc le fragment est toujours quelque part.

Je veux savoir si je fais quelque chose de mal et comment puis-je le résoudre, merci

Mettre à jour:

J'utilise ce code pour charger de nouveaux fragments

fm.beginTransaction()
    .add(container, sectionFragment.getFragment())
    .addToBackStack(sectionFragment.getFragmentName())
    .commit();

Et pour enlever:

private void clearStack(){
int count = fm.getBackStackEntryCount();
    while(count > 1){
        fm.popBackStack();
        count--;
    }
}

NOTE 1: J'utilise add à la place de remplacer parce que je ne veux pas perdre l'état de mon fragment lorsque je retourne à la section de détail. Lorsque je charge une autre section différente, j'appelle clearStack pour faire sauter la pile jusqu'à 1, puis charge un nouveau fragment. À la fin, j'appelle executePendingTransactions () pour finir de supprimer les fragments de la transaction.

NOTE 2: Je constate qu'il entre dans la méthode onDestroy () de mon fragment et qu'il est donc supposé être détruit. Mais je ne sais pas pourquoi on l'appelle à nouveau lorsque l'activité principale reprend.

9
edrian

J'ai trouvé que le problème n'était pas dans la logique d'ajouter et de supprimer des fragments de la pile.

Le problème était que certains fragments chargeaient d'autres fragments à l'intérieur (composant ViewPager). Ensuite, j'ai pensé que lorsque le fragment était retiré, ces fragments l'étaient également. 

Ceci est vrai UNIQUEMENT si vous utilisez la méthode getChildFragmentManager(). Cette méthode DOIT être utilisée lors du chargement de fragments dans d’autres fragmets. Sinon, les fragments sont associés à l'activité des fragments.

20
edrian

J'ai trouvé cette question, car après avoir appelé 

fragmentManager.popBackStack(null, FragmentManager.POP_BACK_STACK_INCLUSIVE);

ce code fragmentManager.getFragments().size() renvoie le nombre maximum de fragments me, qui étaient dans la pile. J'ai vérifié chaque fragment sur null. Et j'ai trouvé que certains fragments sont nuls sur mon cas. Peut-être que ça va aider quelqu'un)

6
Malder

popBackStack retournera simplement votre dernière FragmentTransaction.

Si vous utilisez FragmentTransaction.add, popBackStack appellera simplement FragmentTransacetion.remove.

Mais si vous appelez FragmentTransaction.replace, popBackStack appellera FragmentTransaction.remove et FragmentTransaction.add

Pour votre "NOTE 1": FragmentTransaction.replace ne changera pas l'état de votre fragment.

4
Neige

J'ai eu un problème similaire où la popBackStack() n'a pas enlevé mon fragment. Cependant, j'ai remarqué que j'ai appelé la mauvaise FragmentManager, où je devais appeler getSupportFragmentMananger() au lieu de getFragmentManager().

0
Aviv Cohen

Si vous cherchez réellement à supprimer des fragments à la fois, suivez les instructions suivantes: Comment remplacer des fragments de types différents?

Sinon, utilisez la transaction de remplacement pour les fragments afin d’adoucir les approches transitiona et hassel free, voir https://stackoverflow.com/a/23013075/3176433

Comprenez également le cycle de vie des fragments, http://developer.Android.com/guide/components/fragments.html

0
zIronManBox