Chaque instance Fragment
a son propre cycle de vie. Lorsqu'un utilisateur parcourt votre application et interagit avec elle, vos fragments passent par différents états de leur cycle de vie : ajout, suppression, entrée dans l'écran et sortie de l'écran.
Pour gérer le cycle de vie, l'instance Fragment
implémente LifecycleOwner
, exposant un objet Lifecycle
auquel vous pouvez accéder via la méthode getLifecycle()
.
Chaque état Lifecycle
possible est représenté dans l'énumération Lifecycle.State
.
En développant l'instance Fragment
sur Lifecycle
, vous pouvez utiliser les techniques et les classes disponibles pour la gestion des cycles de vie avec des composants tenant compte des cycles de vie.
Par exemple, vous pouvez afficher la position de l'appareil à l'écran à l'aide d'un composant tenant compte des cycles de vie. Ce composant peut commencer automatiquement à écouter lorsque le fragment devient actif et s'arrêter lorsque celui-ci passe à un état inactif.
Au lieu d'utiliser un élément LifecycleObserver
, la classe Fragment
inclut des méthodes de rappel correspondant à chacune des modifications du cycle de vie d'un fragment, parmi lesquelles : onCreate()
, onStart()
, onResume()
, onPause()
, onStop()
et onDestroy()
.
La vue d'un fragment comporte un élément Lifecycle
distinct géré indépendamment de l'élément Lifecycle
du fragment. Les fragments conservent une classe LifecycleOwner
pour leur vue, auquel vous pouvez accéder à l'aide des méthodes getViewLifecycleOwner()
ou getViewLifecycleOwnerLiveData()
.
Il est utile d'accéder à la vue de l'élément Lifecycle
dans les cas où un composant du cycle de vie ne doit effectuer des tâches qu'à condition que la vue d'un fragment existe, tels que l'observation d'une classe LiveData
dont le seul rôle est de s'afficher à l'écran.
Cette rubrique décrit en détail le cycle de vie des éléments Fragment
. Elle explique certaines des règles qui déterminent l'état du cycle de vie d'un fragment et montre la relation entre les états Lifecycle
et les rappels de cycle de vie des fragments.
Fragments et gestionnaire de fragments
Lorsqu'un fragment est instancié, son premier état est INITIALIZED
. Pour qu'un fragment puisse passer aux étapes suivantes de son cycle de vie, il doit être ajouté à un gestionnaire FragmentManager
. Le gestionnaire FragmentManager
a pour rôle de déterminer l'état dans lequel doit se trouver le fragment, puis d'activer l'état en question pour le fragment.
Au-delà du cycle de vie du fragment, le gestionnaire FragmentManager
a aussi pour fonction d'associer les fragments à leur activité hôte et de les dissocier lorsqu'ils ne sont plus utilisés. La classe Fragment
comporte deux méthodes de rappel, onAttach()
et onDetach()
, que vous pouvez remplacer pour effectuer des tâches lorsque l'un de ces événements se produit.
Le rappel onAttach()
est activé lorsque le fragment a été ajouté à un gestionnaire FragmentManager
et associé à son activité hôte. À ce stade, le fragment est actif et FragmentManager
gère son état de cycle de vie. Les méthodes FragmentManager
telles que findFragmentById()
renvoient alors ce fragment.
La méthode onAttach()
est appelée systématiquement avant tout changement d'état du cycle de vie.
Le rappel onDetach()
est activé lorsque le fragment a été supprimé d'un gestionnaire FragmentManager
et dissocié de son activité hôte. Le fragment n'est plus actif et ne peut plus être récupéré à l'aide de findFragmentById()
.
La méthode onDetach()
est appelée systématiquement après tout changement d'état du cycle de vie.
Notez que ces rappels ne sont pas liés aux méthodes FragmentTransaction
attach()
et detach()
.
Pour en savoir plus sur ces méthodes, consultez la page Transactions de fragments.
États et rappels du cycle de vie des fragments
Pour déterminer l'état du cycle de vie d'un fragment, le gestionnaire FragmentManager
prend en compte les éléments suivants :
- L'état maximal d'un fragment est déterminé par son gestionnaire
FragmentManager
. Un fragment ne peut pas dépasser l'état de son gestionnaireFragmentManager
. - Dans le cadre d'une opération
FragmentTransaction
, vous pouvez définir un état de cycle de vie maximal sur un fragment à l'aide de la méthodesetMaxLifecycle()
. - L'état du cycle de vie d'un fragment ne peut jamais être supérieur à celui de son parent. Par exemple, un fragment parent ou une activité de même niveau doivent être démarrés avant les fragments enfants correspondants. De même, les fragments enfants doivent être arrêtés avant leur fragment parent ou l'activité de même niveau.
La figure 1 présente chacun des états Lifecycle
d'un fragment et la manière dont ils sont associés aux rappels de cycle de vie du fragment et à la vue Lifecycle
de ce fragment.
Le fragment progresse dans son cycle de vie en passant d'un état à un autre. Par exemple, un fragment ajouté en haut de la pile "Retour" remonte de CREATED
à STARTED
, puis à RESUMED
. À l'inverse, lorsqu'un fragment se détache de la pile "Retour", il descend d'un état au suivant, passant de RESUMED
à STARTED
, puis à CREATED
, puis à DESTROYED
.
Remontées d'un état à l'autre
Lors d'une remontée des états d'un cycle de vie, un fragment appelle d'abord le rappel de cycle de vie associé à son nouvel état. Une fois ce rappel terminé, l'élément Lifecycle.Event
approprié est émis pour les observateurs par le l'élément Lifecycle
du fragment, suivi de la vue du fragment Lifecycle
, si celle-ci a été instanciée.
Fragment CRÉÉ
Lorsque votre fragment atteint l'état CREATED
, il a été ajouté à un gestionnaire FragmentManager
et la méthode onAttach()
a déjà été appelée.
C'est le moment approprié pour restaurer tout état enregistré associé au fragment lui-même via la propriété SavedStateRegistry
de ce fragment.
Notez que la vue du fragment n'a pas été créée et que tout état associé à la vue du fragment ne doit être restauré qu'après la création de cette vue.
Cette transition appelle le rappel onCreate()
. Le rappel reçoit également un argument Bundle
savedInstanceState
contenant tout état précédemment enregistré par onSaveInstanceState()
.
Notez que savedInstanceState
a une valeur null
la première fois que le fragment est créé, mais qu'il est toujours défini sur une valeur non nulle pour les recréations ultérieures, même si vous n'ignorez pas la méthode onSaveInstanceState()
. Pour en savoir plus, consultez la section Enregistrer l'état avec des fragments.
Fragment CRÉÉ et vue INITIALISÉE
La vue Lifecycle
du fragment n'est créée que lorsque votre Fragment
fournit une instance View
valide. Dans la plupart des cas, vous pouvez utiliser les constructeurs de fragments utilisant un identifiant @LayoutId
, ce qui gonfle automatiquement la vue au moment souhaité. Vous pouvez également forcer la méthode onCreateView()
à gonfler la vue ou à créer la vue de votre fragment de façon programmatique.
Si et seulement si la vue de votre fragment est instanciée avec un élément View
non nul, cet élément View
est défini sur le fragment et peut être récupéré à l'aide de getView()
. La méthode getViewLifecycleOwnerLiveData()
est ensuite actualisée avec le nouvel état LifecycleOwner
INITIALIZED
correspondant à la vue du fragment. Le rappel de cycle de vie onViewCreated()
est alors également appelé.
C'est ici que vous devez configurer l'état initial de votre vue, commencer à observer les instances LiveData
dont les rappels actualisent la vue du fragment et configurer des adaptateurs sur toutes les instances RecyclerView
ou ViewPager2
de la vue de votre fragment.
Fragment et vue CRÉÉS
Une fois la vue du fragment créée, l'état de la vue précédent, le cas échéant, est restauré, et l'élément Lifecycle
de la vue passe à l'état CREATED
. Le propriétaire du cycle de vie de la vue envoie également l'événement ON_CREATE
à ses observateurs. Vous devez alors restaurer tout état supplémentaire associé à la vue du fragment.
Cette transition appelle également le rappel onViewStateRestored()
.
Fragment et vue DÉMARRÉS
Nous vous recommandons vivement de lier les composants tenant compte des cycles de vie à l'état STARTED
d'un fragment, car cet état garantit que la vue du fragment est disponible, le cas échéant, a été créée, et que vous pouvez effectuer une opération FragmentTransaction
sur le gestionnaire FragmentManager
enfant du fragment. Si la vue du fragment n'est pas nulle, l'état STARTED
est appliqué à la vue Lifecycle
du fragment immédiatement après l'attribution de l'état STARTED
à l'élément Lifecycle
du fragment.
Lorsque le fragment acquiert l'état STARTED
, le rappel onStart()
est appelé.
Fragment et vue REPRIS
Lorsque le fragment est visible, tous les effets Animator
et Transition
sont terminés, et le fragment peut faire l'objet d'interactions avec l'utilisateur. Le cycle de vie (Lifecycle
) du fragment passe à l'état RESUMED
, et le rappel onResume()
est appelé.
La transition vers l'état RESUMED
est le signal approprié pour indiquer que l'utilisateur peut désormais interagir avec votre fragment. Les fragments ne se trouvant pas dans l'état RESUMED
ne devraient pas faire ressortir leurs vues manuellement ni tenter de gérer la visibilité du mode de saisie.
Transitions d'état descendantes
Lorsqu'un fragment passe à un état inférieur du cycle de vie, l'événement Lifecycle.Event
approprié est envoyé aux observateurs par le cycle de vie (Lifecycle
) de la vue du fragment, si celui-ci est instancié, puis par l'élément Lifecycle
du fragment. Une fois qu'un événement de cycle de vie a été envoyé, le fragment appelle le rappel de cycle de vie associé.
Fragment et vue DÉMARRÉS
Lorsque l'utilisateur commence à quitter le fragment, mais que celui-ci est toujours visible, les cycles de vie (Lifecycle
) du fragment et de sa vue sont restaurés à l'état STARTED
et envoient l'événement ON_PAUSE
à leurs observateurs. Le fragment appelle ensuite son rappel onPause()
.
Fragment et vue CRÉÉS
Une fois que le fragment n'est plus visible, l'état CREATED
est appliqué aux cycles de vie (Lifecycle
) du fragment et de sa vue, qui envoient l'événement ON_STOP
à leurs observateurs. Cette transition d'état est déclenchée non seulement par l'activité ou le fragment parent, mais aussi par l'enregistrement de l'état par l'activité parente ou le fragment. Ce comportement garantit que l'événement ON_STOP
est appelé avant l'enregistrement de l'état du fragment. L'événement ON_STOP
devient ainsi le dernier point où il est possible d'exécuter une opération FragmentTransaction
sur le gestionnaire FragmentManager
enfant.
Comme le montre la figure 2, l'ordre dans lequel ont lieu le rappel onStop()
et l'enregistrement de l'état avec onSaveInstanceState()
dépend du niveau d'API. Pour tous les niveaux d'API antérieurs à l'API 28, la méthode onSaveInstanceState()
est appelée avant onStop()
.
Pour les niveaux d'API 28 et supérieurs, l'ordre d'appel est inversé.
Fragment CRÉÉ et vue DÉTRUITE
Une fois toutes les animations et transitions de sortie terminées et la vue du fragment dissociée de la fenêtre, l'état DESTROYED
est attribué au cycle de vie (Lifecycle
) de la vue du fragment, qui envoie l'événement ON_DESTROY
à ses observateurs. Le fragment appelle ensuite son rappel onDestroyView()
. À ce stade, la vue du fragment a atteint la fin de son cycle de vie et getViewLifecycleOwnerLiveData()
renvoie une valeur null
.
Toutes les références à la vue du fragment doivent alors être supprimées, afin que la mémoire occupée par vue du fragment puisse être récupérée.
Fragment DÉTRUIT
Si le fragment est supprimé ou si le gestionnaire FragmentManager
est détruit, l'état DESTROYED
est attribué au cycle de vie (Lifecycle
) du fragment, qui envoie l'événement ON_DESTROY
à ses observateurs. Le fragment appelle ensuite son rappel onDestroy()
. Le fragment a alors atteint la fin de son cycle de vie.
Ressources supplémentaires
Pour en savoir plus sur le cycle de vie des fragments, consultez les ressources supplémentaires suivantes.