Partage via


Cycle de vie de l’activité

Les activités sont un bloc de construction fondamental d’applications Android et peuvent exister dans un certain nombre d’états différents. Le cycle de vie de l’activité commence par l’instanciation et se termine par la destruction, et inclut de nombreux états entre eux. Lorsqu’une activité change d’état, la méthode d’événement de cycle de vie appropriée est appelée, en informant l’activité du changement d’état imminent et en lui permettant d’exécuter du code pour s’adapter à cette modification. Cet article examine le cycle de vie des activités et explique la responsabilité qu'une activité a lors de chaque changement d'état pour faire partie d'une application fiable et bien conçue.

Vue d’ensemble du cycle de vie des activités

Les activités sont un concept de programmation inhabituel propre à Android. Dans le développement d’applications traditionnel, il existe généralement une méthode principale statique, qui est exécutée pour lancer l’application. Avec Android, cependant, les choses sont différentes ; Les applications Android peuvent être lancées via n’importe quelle activité inscrite au sein d’une application. Dans la pratique, la plupart des applications n’auront qu’une activité spécifique spécifiée comme point d’entrée de l’application. Toutefois, si une application se bloque ou est arrêtée par le système d’exploitation, le système d’exploitation peut essayer de redémarrer l’application à la dernière activité ouverte ou n’importe où dans la pile d’activité précédente. En outre, le système d’exploitation peut suspendre les activités lorsqu’elles ne sont pas actives et les récupérer si elle est faible en mémoire. Une attention particulière doit être prise en compte pour permettre à l’application de restaurer correctement son état en cas de redémarrage d’une activité, en particulier si cette activité dépend des données des activités précédentes.

Le cycle de vie de l’activité est implémenté en tant que collection de méthodes que le système d’exploitation appelle tout au long du cycle de vie d’une activité. Ces méthodes permettent aux développeurs d’implémenter les fonctionnalités nécessaires pour répondre aux exigences d’état et de gestion des ressources de leurs applications.

Il est extrêmement important pour le développeur d’applications d’analyser les exigences de chaque activité afin de déterminer quelles méthodes exposées par le cycle de vie de l’activité doivent être implémentées. L’échec de cette opération peut entraîner une instabilité de l’application, des incidents, un ballonnement des ressources et peut-être même une instabilité du système d’exploitation sous-jacente.

Ce chapitre examine en détail le cycle de vie des activités, notamment :

  • États d’activité
  • Méthodes de cycle de vie
  • Conservation de l’état d’une application

Cette section inclut également une procédure pas à pas qui fournit des exemples pratiques sur la façon de sauvegarder efficacement l’état pendant le cycle de vie de l'Activité. À la fin de ce chapitre, vous devez avoir une compréhension du cycle de vie de l’activité et de la prise en charge dans une application Android.

Cycle de vie de l’activité

Le cycle de vie de l’activité Android comprend une collection de méthodes exposées dans la classe Activity qui fournissent au développeur une infrastructure de gestion des ressources. Cette infrastructure permet aux développeurs de répondre aux exigences de gestion d’état uniques de chaque activité au sein d’une application et de gérer correctement la gestion des ressources.

États d’activité

Le système d'exploitation Android gère les activités en fonction de leur état. Cela permet à Android d’identifier les activités qui ne sont plus utilisées, ce qui permet au système d’exploitation de récupérer de la mémoire et des ressources. Le diagramme suivant illustre les états qu’une activité peut parcourir pendant sa durée de vie :

Diagramme des états d’activité

Ces états peuvent être divisés en 4 groupes principaux comme suit :

  1. Actif ou en cours d’exécution : les activités sont considérées comme actives ou en cours d’exécution si elles se trouvent au premier plan, également appelées haut de la pile d’activités. Cela est considéré comme l’activité de priorité la plus élevée dans Android, et, par conséquent, sera uniquement tué par le système d’exploitation dans des situations extrêmes, par exemple si l’activité tente d’utiliser plus de mémoire que disponible sur l’appareil, car cela pourrait entraîner l’absence de réponse de l’interface utilisateur.

  2. Suspendu : lorsque l’appareil est en veille ou qu’une activité est toujours visible mais partiellement masquée par une nouvelle activité non complète ou transparente, l’activité est considérée comme suspendue. Les activités suspendues sont toujours actives, c’est-à-dire qu’elles conservent toutes les informations d’état et de membre, et restent attachées au gestionnaire de fenêtres. Il s’agit de la deuxième activité de priorité la plus élevée dans Android et, par conséquent, sera tuée par le système d’exploitation uniquement si l’arrêt de cette activité répond aux exigences de ressources nécessaires pour maintenir l’activité active/en cours d’exécution stable et réactive.

  3. Arrêté/en arrière-plan : les activités complètement masquées par une autre activité sont considérées comme arrêtées ou en arrière-plan. Les activités arrêtées tentent toujours de conserver leurs informations d’état et de membre tant que possible, mais les activités arrêtées sont considérées comme étant la priorité la plus basse des trois états et, par conséquent, le système d’exploitation tuera d’abord les activités dans cet état pour répondre aux besoins en ressources des activités de priorité plus élevée.

  4. Redémarré : il est possible qu’une activité, en pause ou arrêtée dans le cycle de vie, soit supprimée de la mémoire par Android. Si l’utilisateur revient à l’activité, il doit être redémarré, restauré à son état précédemment enregistré, puis affiché à l’utilisateur.

Activité Re-Creation en réponse aux modifications de configuration

Pour compliquer davantage les choses, Android introduit une nouvelle complication appelée Modifications de configuration. Les modifications de configuration sont des cycles rapides de destruction/récréation d'activités qui se produisent lorsque la configuration d'une activité change, par exemple lorsque l'appareil est pivoté (et que l'activité doit être réinitialisée en mode paysage ou portrait), lorsque le clavier est affiché (et que l'activité a la possibilité de se redimensionner), ou lorsque l'appareil est placé dans une station d'accueil, entre autres.

Les modifications de configuration provoquent toujours les mêmes modifications d’état d’activité qui se produisent pendant l’arrêt et le redémarrage d’une activité. Toutefois, pour vous assurer qu’une application est réactive et fonctionne correctement pendant les modifications de configuration, il est important qu’elle soit gérée le plus rapidement possible. Pour cette raison, Android dispose d’une API spécifique qui peut être utilisée pour conserver l’état pendant les modifications de configuration. Nous aborderons cela plus loin dans la section Gestion de l’état tout au long du cycle de vie .

Méthodes de cycle de vie des activités

Le Kit de développement logiciel (SDK) Android et, par extension, le framework Xamarin.Android fournit un modèle puissant pour gérer l’état des activités au sein d’une application. Quand l’état d’une activité change, l’activité est avertie par le système d’exploitation, qui appelle des méthodes spécifiques sur cette activité. Le diagramme suivant illustre ces méthodes par rapport au cycle de vie de l’activité :

Organigramme du cycle de vie des activités

En tant que développeur, vous pouvez gérer les modifications d’état en substituant ces méthodes au sein d’une activité. Toutefois, il est important de noter que toutes les méthodes de cycle de vie sont appelées sur le thread d’interface utilisateur et empêchent le système d’exploitation d’effectuer le prochain travail de l’interface utilisateur, comme masquer l’activité actuelle, afficher une nouvelle activité, etc. Par conséquent, le code de ces méthodes doit être aussi bref que possible pour rendre une application très performante. Toutes les tâches durables doivent être exécutées sur un thread d’arrière-plan.

Examinons chacune de ces méthodes de cycle de vie et leur utilisation :

OnCreate

OnCreate est la première méthode à appeler lorsqu’une activité est créée. OnCreate est toujours substitué pour effectuer toutes les initialisations de démarrage qui peuvent être requises par une activité telle que :

  • Création de vues
  • Initialisation des variables
  • Liaison de données statiques à des listes

OnCreate prend un paramètre Bundle , qui est un dictionnaire pour stocker et transmettre des informations d’état et des objets entre les activités Si le bundle n’est pas null, cela indique que l’activité redémarre et qu’elle doit restaurer son état à partir de l’instance précédente. Le code suivant montre comment récupérer des valeurs à partir de l’offre groupée :

protected override void OnCreate(Bundle bundle)
{
   base.OnCreate(bundle);

   string intentString;
   bool intentBool;

   if (bundle != null)
   {
      intentString = bundle.GetString("myString");
      intentBool = bundle.GetBoolean("myBool");
   }

   // Set our view from the "main" layout resource
   SetContentView(Resource.Layout.Main);
}

Une fois OnCreate terminé, Android appellera OnStart.

OnStart

OnStart est toujours appelé par le système une fois OnCreate terminé. Les activités peuvent substituer cette méthode si elles doivent effectuer des tâches spécifiques juste avant qu’une activité ne devienne visible, comme l’actualisation des valeurs actuelles des vues au sein de l’activité. Android appellera OnResume immédiatement après cette méthode.

OnResume

Le système appelle OnResume lorsque l’activité est prête à commencer à interagir avec l’utilisateur. Les activités doivent remplacer cette méthode pour effectuer des tâches telles que :

  • Augmentation des taux d’images (tâche courante dans le développement de jeux)
  • Démarrage d’animations
  • Écoute des mises à jour GPS
  • Afficher toutes les alertes ou boîtes de dialogue pertinentes
  • Connecter des gestionnaires d’événements externes

Par exemple, l’extrait de code suivant montre comment initialiser l’appareil photo :

protected override void OnResume()
{
    base.OnResume(); // Always call the superclass first.

    if (_camera==null)
    {
        // Do camera initializations here
    }
}

OnResume est important, car toute opération effectuée dans OnPause doit être non effectuée dans OnResume, car il s’agit de la seule méthode de cycle de vie garantie à s’exécuter après OnPause lors de la remise de l’activité à la vie.

OnPause

OnPause est appelé lorsque le système est sur le point de placer l’activité en arrière-plan ou lorsque l’activité devient partiellement masquée. Les activités doivent remplacer cette méthode si elles doivent :

  • Valider les modifications non enregistrées dans des données persistantes

  • Détruire ou nettoyer d’autres objets consommant des ressources

  • Réduire les fréquences d’images et suspendre les animations

  • Désinscrire les gestionnaires d’événements externes ou les gestionnaires de notification (c’est-à-dire ceux liés à un service). Cette opération doit être effectuée pour empêcher les fuites de mémoire d’activité.

  • De même, si l’activité a affiché des dialogues ou des alertes, elles doivent être nettoyées avec la .Dismiss() méthode.

Par exemple, l’extrait de code suivant libère l’appareil photo, car l’activité ne peut pas l’utiliser lors d’une pause :

protected override void OnPause()
{
    base.OnPause(); // Always call the superclass first

    // Release the camera as other activities might need it
    if (_camera != null)
    {
        _camera.Release();
        _camera = null;
    }
}

Il existe deux méthodes de cycle de vie possibles qui seront appelées après OnPause:

  1. OnResume sera appelé si l’activité doit être retournée au premier plan.
  2. OnStop sera appelé si l’activité est placée en arrière-plan.

OnStop

OnStop est appelé lorsque l’activité n’est plus visible par l’utilisateur. Cela se produit lorsque l’une des opérations suivantes se produit :

  • Une nouvelle activité est en cours de démarrage et couvre cette activité.
  • Une activité existante est mise au premier plan.
  • L’activité est détruite.

OnStop peut ne pas toujours être appelé dans des situations de mémoire faible, comme lorsque Android manque de ressources et ne peut pas correctement mettre l'activité en arrière-plan. Pour cette raison, il est préférable de ne pas compter sur l’appel de OnStop lors de la préparation d’une activité pour destruction. Les méthodes de cycle de vie suivantes qui peuvent être appelées après celle-ci seront OnDestroy si l’activité disparaît ou OnRestart si l’activité revient pour interagir avec l’utilisateur.

OnDestroy

OnDestroy est la méthode finale appelée sur une instance d’activité avant qu’elle ne soit détruite et complètement supprimée de la mémoire. Dans des situations extrêmes, Android peut tuer le processus d'application qui héberge l'activité, ce qui peut entraîner que OnDestroy ne soit pas appelé. La plupart des activités n’implémentent pas cette méthode car la plupart des opérations de nettoyage et d’arrêt ont été effectuées dans les méthodes OnPause et OnStop. La méthode OnDestroy est généralement substituée pour nettoyer les tâches durables qui peuvent consommer des ressources. Par exemple, il peut s’agir de threads d’arrière-plan qui ont été démarrés dans OnCreate.

Aucune méthode de cycle de vie ne sera appelée après la destruction de l’activité.

OnRestart

OnRestart est appelé une fois que votre activité a été arrêtée, avant son redémarrage. Voici un bon exemple lorsque l’utilisateur appuie sur le bouton d’accueil lors d’une activité dans l’application. Lorsque cela se produit, les méthodes OnPause et OnStop sont appelées, et l’activité est déplacée vers l’arrière-plan mais n’est pas détruite. Si l’utilisateur devait ensuite restaurer l’application à l’aide du gestionnaire de tâches ou d’une application similaire, Android appelle la OnRestart méthode de l’activité.

Il n’existe aucune directive générale concernant le type de logique à implémenter dans OnRestart. Cela est dû au fait que OnStart est toujours appelé, que l'activité soit créée ou redémarrée, de sorte que toutes les ressources requises par l'activité doivent être initialisées dans OnStart, plutôt que OnRestart.

La méthode de cycle de vie suivante appelée après OnRestart sera OnStart.

Retour et Accueil

De nombreux appareils Android ont deux boutons distincts : un bouton « Précédent » et un bouton « Accueil ». Vous trouverez un exemple de ceci dans la capture d’écran suivante d’Android 4.0.3 :

Boutons Retour et Accueil

Il existe une différence subtile entre les deux boutons, même s’ils semblent avoir le même effet de placer une application en arrière-plan. Lorsqu’un utilisateur clique sur le bouton Précédent, il indique à Android qu’il est terminé avec l’activité. Android détruit l’activité. En revanche, lorsque l’utilisateur clique sur le bouton Accueil, l’activité est simplement placée en arrière-plan : Android ne tue pas l’activité.

Gestion de l'état tout au long du cycle de vie du logiciel

Lorsqu’une activité est arrêtée ou détruite, le système offre la possibilité de sauvegarder l’état de l’activité pour une restauration ultérieure. Cet état enregistré est appelé état d’instance. Android propose trois options pour stocker l’état de l’instance pendant le cycle de vie de l’activité :

  1. Stockage de valeurs primitives dans un Dictionarybundle utilisé par Android pour enregistrer l’état.

  2. Création d’une classe personnalisée qui contiendra des valeurs complexes telles que des bitmaps. Android utilisera cette classe personnalisée pour enregistrer l’état.

  3. Contourner le cycle de vie des modifications de configuration et assumer l’entière responsabilité de la préservation de l’état dans l’activité.

Ce guide couvre les deux premières options.

État du bundle

L’option principale permettant d’enregistrer l’état de l’instance consiste à utiliser un objet de dictionnaire clé/valeur appelé Bundle. Rappelez-vous que lorsqu'une activité est créée, la méthode OnCreate reçoit un bundle en tant que paramètre, lequel peut être utilisé pour restaurer l'état de l'instance. Il n’est pas recommandé d’utiliser un bundle pour des données plus complexes qui ne sérialisent pas rapidement ou facilement vers des paires clé/valeur (telles que des bitmaps) ; il doit plutôt être utilisé pour des valeurs simples telles que des chaînes.

Une activité fournit des méthodes permettant d’enregistrer et de récupérer l’état de l’instance dans le bundle :

  • OnSaveInstanceState : il est appelé par Android lorsque l’activité est détruite. Les activités peuvent implémenter cette méthode s’ils doivent conserver les éléments d’état clé/valeur.

  • OnRestoreInstanceState : cette méthode est appelée après la fin de la méthode OnCreate, et offre une autre occasion à une activité de restaurer son état une fois l'initialisation terminée.

Le diagramme suivant illustre l’utilisation de ces méthodes :

Schéma de flux des états de l'ensemble

OnSaveInstanceState

OnSaveInstanceState sera appelé lorsque l'activité est en train de s'arrêter. Il reçoit un paramètre groupé dans lequel l’activité peut stocker son état. Lorsqu’un appareil subit une modification de configuration, une activité peut utiliser l’objet Bundle passé pour préserver l’état de l’activité en remplaçant OnSaveInstanceState. Considérons par exemple le code suivant :

int c;

protected override void OnCreate (Bundle bundle)
{
  base.OnCreate (bundle);

  this.SetContentView (Resource.Layout.SimpleStateView);

  var output = this.FindViewById<TextView> (Resource.Id.outputText);

  if (bundle != null) {
    c = bundle.GetInt ("counter", -1);
  } else {
    c = -1;
  }

  output.Text = c.ToString ();

  var incrementCounter = this.FindViewById<Button> (Resource.Id.incrementCounter);

  incrementCounter.Click += (s,e) => {
    output.Text = (++c).ToString();
  };
}

Le code ci-dessus incrémente un entier nommé c lorsqu’un bouton nommé incrementCounter est cliqué, affichant le résultat dans un TextView nom output. Lorsqu’une modification de configuration se produit , par exemple, lorsque l’appareil est pivoté, le code ci-dessus perd la valeur c du fait que le bundle résultat est null, comme illustré dans la figure ci-dessous :

L’affichage n’affiche pas la valeur précédente

Pour conserver la valeur de c dans cet exemple, l’activité peut substituer OnSaveInstanceState, en enregistrant la valeur dans le bundle comme illustré ci-dessous :

protected override void OnSaveInstanceState (Bundle outState)
{
  outState.PutInt ("counter", c);
  base.OnSaveInstanceState (outState);
}

Maintenant, lorsque l’appareil est pivoté vers une nouvelle orientation, l’entier est enregistré dans le bundle et est récupéré avec la ligne :

c = bundle.GetInt ("counter", -1);

Remarque

Il est important d’appeler toujours l’implémentation de base de OnSaveInstanceState afin que l’état de la hiérarchie de vues puisse également être enregistré.

Afficher l’état

Substituer OnSaveInstanceState est un moyen approprié pour enregistrer des données temporaires dans une activité lors des changements d’orientation, comme le compteur dans l’exemple ci-dessus. Toutefois, l’implémentation par défaut de OnSaveInstanceState prend en charge l’enregistrement des données temporaires dans l’interface utilisateur pour chaque vue, tant que chaque vue dispose d’un ID attribué. Par exemple, supposons qu’une application a un EditText élément défini en XML comme suit :

<EditText android:id="@+id/myText"
  android:layout_width="fill_parent"
  android:layout_height="wrap_content"/>

Étant donné que le EditText contrôle est id affecté, lorsque l’utilisateur entre certaines données et fait pivoter l’appareil, les données sont toujours affichées, comme indiqué ci-dessous :

Les données sont conservées en mode paysage

OnRestoreInstanceState (Mise à jour de l'état de l'instance)

OnRestoreInstanceState sera appelé après OnStart. Cela permet à une activité de restaurer tout état précédemment enregistré dans un bundle lors du précédent appel à OnSaveInstanceState. Il s’agit de la même offre groupée fournie à OnCreate, cependant.

Le code suivant montre comment l’état peut être restauré dans OnRestoreInstanceState:

protected override void OnRestoreInstanceState(Bundle savedState)
{
    base.OnRestoreInstanceState(savedState);
    var myString = savedState.GetString("myString");
    var myBool = savedState.GetBoolean("myBool");
}

Cette méthode existe pour fournir une certaine flexibilité quant au moment où l’état doit être restauré. Parfois, il est plus approprié d’attendre que toutes les initialisations soient effectuées avant de restaurer l’état de l’instance. En outre, une sous-classe d’une activité existante peut uniquement vouloir restaurer certaines valeurs à partir de l’état de l’instance. Dans de nombreux cas, il n’est pas nécessaire de remplacer OnRestoreInstanceState, car la plupart des activités peuvent restaurer l’état à l’aide du bundle fourni à OnCreate.

Pour obtenir un exemple d’enregistrement de l’état à l’aide d’un Bundle, reportez-vous à la procédure pas à pas : enregistrement de l’état d’activité.

Limitations de l’offre groupée

Bien que OnSaveInstanceState facilite l’enregistrement de données temporaires, il présente certaines limitations :

  • Il n’est pas appelé dans tous les cas. Par exemple, le fait d’appuyer sur Accueil ou Retour pour quitter une activité n’entraîne OnSaveInstanceState pas l’appel.

  • Le bundle passé dans OnSaveInstanceState n’est pas conçu pour des objets volumineux, comme les images. Dans le cas d’objets volumineux, l’enregistrement de l’objet à partir de OnRetainNonConfigurationInstance est préférable, comme indiqué ci-dessous.

  • Les données enregistrées à l'aide du paquet sont sérialisées, ce qui peut entraîner des retards.

L’état du Bundle est utile pour des données simples qui utilisent peu de mémoire, tandis que les données d’instance hors configuration sont utiles pour des données plus complexes ou des données coûteuses à récupérer, comme lors d’un appel à un service web ou d’une requête de base de données complexe. Les données d’instance non de configuration sont enregistrées dans un objet en fonction des besoins. La section suivante présente un moyen de préserver des types de données plus complexes OnRetainNonConfigurationInstance par le biais de modifications de configuration.

Persistance des données complexes

Outre l’enregistrement des données dans le bundle, Android prend également en charge l’enregistrement des données en substituant OnRetainNonConfigurationInstance et en retournant une instance de Java.Lang.Object qui contient les données à conserver. Il existe deux principaux avantages de l’utilisation OnRetainNonConfigurationInstance pour enregistrer l’état :

  • L'objet retourné fonctionne bien avec des types de données plus grands et complexes, parce que la mémoire retient cet objet.

  • La OnRetainNonConfigurationInstance méthode est appelée à la demande, et uniquement si nécessaire. Cela est plus économique que d’utiliser un cache manuel.

L’utilisation OnRetainNonConfigurationInstance convient aux scénarios où il est coûteux de récupérer les données plusieurs fois, comme dans les appels de service web. Par exemple, considérez le code suivant qui recherche Twitter :

public class NonConfigInstanceActivity : ListActivity
{
  protected override void OnCreate (Bundle bundle)
  {
    base.OnCreate (bundle);
    SearchTwitter ("xamarin");
  }

  public void SearchTwitter (string text)
  {
    string searchUrl = String.Format("http://search.twitter.com/search.json?" + "q={0}&rpp=10&include_entities=false&" + "result_type=mixed", text);

    var httpReq = (HttpWebRequest)HttpWebRequest.Create (new Uri (searchUrl));
    httpReq.BeginGetResponse (new AsyncCallback (ResponseCallback), httpReq);
  }

  void ResponseCallback (IAsyncResult ar)
  {
    var httpReq = (HttpWebRequest)ar.AsyncState;

    using (var httpRes = (HttpWebResponse)httpReq.EndGetResponse (ar)) {
      ParseResults (httpRes);
    }
  }

  void ParseResults (HttpWebResponse httpRes)
  {
    var s = httpRes.GetResponseStream ();
    var j = (JsonObject)JsonObject.Load (s);

    var results = (from result in (JsonArray)j ["results"] let jResult = result as JsonObject select jResult ["text"].ToString ()).ToArray ();

    RunOnUiThread (() => {
      PopulateTweetList (results);
    });
  }

  void PopulateTweetList (string[] results)
  {
    ListAdapter = new ArrayAdapter<string> (this, Resource.Layout.ItemView, results);
  }
}

Ce code récupère les résultats du web au format JSON, les analyse, puis présente les résultats dans une liste, comme illustré dans la capture d’écran suivante :

Résultats affichés à l’écran

Lorsqu’une modification de configuration se produit , par exemple, lorsqu’un appareil est pivoté, le code répète le processus. Pour réutiliser les résultats récupérés à l’origine et ne pas provoquer d’appels réseau inutiles et redondants, nous pouvons utiliser OnRetainNonconfigurationInstance pour enregistrer les résultats, comme indiqué ci-dessous :

public class NonConfigInstanceActivity : ListActivity
{
  TweetListWrapper _savedInstance;

  protected override void OnCreate (Bundle bundle)
  {
    base.OnCreate (bundle);

    var tweetsWrapper = LastNonConfigurationInstance as TweetListWrapper;

    if (tweetsWrapper != null) {
      PopulateTweetList (tweetsWrapper.Tweets);
    } else {
      SearchTwitter ("xamarin");
    }

    public override Java.Lang.Object OnRetainNonConfigurationInstance ()
    {
      base.OnRetainNonConfigurationInstance ();
      return _savedInstance;
    }

    ...

    void PopulateTweetList (string[] results)
    {
      ListAdapter = new ArrayAdapter<string> (this, Resource.Layout.ItemView, results);
      _savedInstance = new TweetListWrapper{Tweets=results};
    }
}

À présent, lorsque l’appareil est pivoté, les résultats d’origine sont récupérés à partir de la LastNonConfiguartionInstance propriété. Dans cet exemple, les résultats se composent d’un string[] contenant des tweets. Étant donné que OnRetainNonConfigurationInstance exige qu'un Java.Lang.Object soit retourné, le string[] est encapsulé dans une classe qui sous-classe Java.Lang.Object, comme indiqué ci-dessous :

class TweetListWrapper : Java.Lang.Object
{
  public string[] Tweets { get; set; }
}

Par exemple, tenter d’utiliser un TextView comme objet retourné par OnRetainNonConfigurationInstance provoquera une fuite de l’activité, comme illustré par le code ci-dessous :

TextView _textView;

protected override void OnCreate (Bundle bundle)
{
  base.OnCreate (bundle);

  var tv = LastNonConfigurationInstance as TextViewWrapper;

  if(tv != null) {
    _textView = tv;
    var parent = _textView.Parent as FrameLayout;
    parent.RemoveView(_textView);
  } else {
    _textView = new TextView (this);
    _textView.Text = "This will leak.";
  }

  SetContentView (_textView);
}

public override Java.Lang.Object OnRetainNonConfigurationInstance ()
{
  base.OnRetainNonConfigurationInstance ();
  return _textView;
}

Dans cette section, nous avons appris à préserver des données d'état simples avec Bundle et à faire persister des types de données plus complexes avec OnRetainNonConfigurationInstance.

Résumé

Le cycle de vie de l’activité Android fournit une infrastructure puissante pour la gestion de l’état des activités au sein d’une application, mais il peut être difficile de comprendre et d’implémenter. Ce chapitre a présenté les différents états qu’une activité peut passer pendant sa durée de vie, ainsi que les méthodes de cycle de vie associées à ces états. Ensuite, des conseils ont été fournis quant au type de logique à effectuer dans chacune de ces méthodes.