Multi-CV

Sous Android 9 (et versions antérieures), les applications passaient à l'état PAUSED lorsque :

  • Une nouvelle activité translucide lancée au-dessus de l'application, alors que l'application était encore visible (et, par conséquent, n'a pas été arrêtée).
  • L'activité a perdu le focus, mais n'a pas été masquée et l'utilisateur a pu interagir avec lui. Par exemple, en mode multi-fenêtres, un certain nombre d'activités peuvent être visibles et recevoir une entrée tactile simultanément.

Ces situations diffèrent dans la quantité de pause qu'une application doit effectuer, mais ne peuvent pas être distinguées au niveau de l'application.

Dans Android 10, toutes les activités les plus focalisables dans les piles visibles résident dans l'état RESUMED . Cela améliore la compatibilité avec les modes multi-fenêtres et MD pour les applications qui utilisent onPause() au lieu de onStop() pour arrêter d'actualiser l'interface utilisateur et d'interagir avec l'utilisateur. Ça signifie:

  • Les deux activités en écran partagé reprennent.
  • Toutes les activités les plus visibles en mode de fenêtrage de forme libre sont reprises.
  • Les activités sur plusieurs écrans peuvent être reprises en même temps.

Figure 1. Reprise multiple sur un appareil pliable

Figure 2. CV multiple en mode bureau

Les activités peuvent résider dans l'état PAUSED lorsqu'elles ne peuvent pas être concentrées ou sont partiellement occultées, telles que :

  • Dans un écran partagé réduit (avec le lanceur sur le côté), l'activité principale n'est pas reprise car elle n'est pas focalisable.
  • En mode image dans l'image, l'activité n'est pas reprise car elle n'est pas focalisable.
  • Lorsque les activités sont couvertes par d'autres activités transparentes dans la même pile.

Cette approche indique aux applications qu'une activité peut recevoir une entrée d'un utilisateur uniquement dans l'état RESUMED . Avant Android 10, les activités pouvaient également recevoir des entrées à l'état PAUSED (par exemple, essayez de toucher simultanément les deux activités en écran partagé sur un appareil exécutant Android 9).

Pour conserver le signal de reprise des versions précédentes d'Android (et pour communiquer quand les applications doivent obtenir l'accès aux ressources à accès exclusif ou singleton), Android 10 inclut un nouveau rappel :

Activity#onTopResumedActivityChanged(boolean onTop)

Lorsqu'il est invoqué, ce rappel est appelé entre Activity#onResume() et Activity#onPause() . Ce rappel est facultatif et peut être ignoré, de sorte qu'une activité peut passer d'un RESUMED à un état PAUSED sans devenir la plus élevée du système. Par exemple, en mode multi-fenêtres. Étant donné que ce rappel est facultatif, il ne fait pas partie du cycle de vie des activités et doit être rarement utilisé.

L'activité précédente à reprise supérieure reçoit et termine l'exécution de onTopResumedActivity(false) avant que la prochaine activité à reprise supérieure reçoive onTopResumedActivity(true) , sauf si l'activité précédente prend trop de temps pour gérer l'appel de méthode et atteint le délai d'attente de 500 ms.

Compatibilité

Pour maintenir la compatibilité lors de la mise en œuvre de plusieurs CV, envisagez ces solutions.

Plusieurs activités reprises dans un processus d'application

  • Publier. Sous Android 9 et versions antérieures, une seule activité du système est reprise à la fois. Toutes les transitions entre activités impliquent de mettre une activité en pause avant d'en reprendre une autre. Certaines applications et frameworks (tels que Flutter ou LocalActivityManager d'Android) utilisent ce fait et stockent l'état de l'activité reprise dans des singletons.
  • La solution. Dans Android 9 et versions antérieures, si deux activités du même processus sont toutes les deux reprises, le système ne reprend que l'activité la plus élevée dans l'ordre Z. Les applications ciblant Android 10 peuvent prendre en charge la reprise simultanée de plusieurs activités.

Accès simultané à la caméra

  • Problèmes . Ces problèmes sont également présents dans Android 9 et inférieur. Par exemple, une activité en plein écran et reprise peut perdre le focus de la caméra au profit d'une activité en pause en mode image dans l'image, mais devenir plus exposée avec une adoption plus large des modes multi-fenêtres et multi-affichages.
    • En raison des modifications apportées à l'état RESUME , les applications peuvent être déconnectées de l'appareil photo même lors de la reprise . Pour résoudre ce problème, les applications doivent gérer une déconnexion de la caméra sans plantage. Lorsqu'elles sont déconnectées, les applications reçoivent un rappel déconnecté et tous les appels dans l'API commencent à lancer CameraAccessException .
    • resizeableActivity=false n'est pas une garantie d'accès exclusif à la caméra, car d'autres applications utilisant la caméra peuvent être ouvertes sur d'autres écrans.
  • Solutions. Les développeurs doivent inclure une logique lorsqu'une application est déconnectée de la caméra. Si une application est déconnectée de la caméra, elle doit surveiller les rappels de disponibilité de la caméra pour essayer de se reconnecter et continuer à utiliser la caméra. En plus du CameraManager#AvailabilityCallback#onCameraAvailable() existant, Android 10 a ajouté CameraManager#AvailabilityCallback#onCameraAccessPrioritiesChanged() , qui couvre le cas où la mise au point (et la priorité de la caméra) bascule entre plusieurs activités reprises. Les développeurs d'applications doivent utiliser ces deux rappels pour déterminer le bon moment pour essayer d'accéder à la caméra.

Multi-CV

Dans Android 10, l'état du cycle de vie des activités est déterminé par la visibilité et l'ordre Z. Pour vous assurer que l'état correct après la mise à jour de la visibilité sur une activité et évaluer l'état du cycle de vie applicable, appelez la méthode ActivityRecord#makeActiveIfNeeded() à partir de différents emplacements. Dans Android 10, actif signifie RESUMED ou PAUSED et ne fonctionne que dans ces deux cas.

Dans Android 10, la reprise d'une activité est suivie séparément dans chaque pile au lieu d'un emplacement unique dans le système. En effet, plusieurs transitions d'activité peuvent être effectuées simultanément dans des modes multi-fenêtres. Pour plus de détails, voir ActivityStack#mInResumeTopActivity .

Rappel d'activité le plus repris

Après les actions qui peuvent entraîner une modification de l'activité principale (telles que le lancement, la reprise ou la modification de l'ordre Z de l'activité), ActivityStackSupervisor#updateTopResumedActivityIfNeeded() est appelé. Cette méthode vérifie si l'activité reprise la plus élevée a changé et effectue la mise à jour si nécessaire. Si l'activité de reprise supérieure précédente n'a pas libéré l'état de reprise supérieure, un message de perte d'état de reprise supérieure lui est envoyé et un délai d'attente est programmé côté serveur ( ActivityStackSupervisor#scheduleTopResumedStateLossTimeout() ). Un rapport de l'état de reprise supérieure est envoyé à l'activité suivante après que la précédente a libéré l'état, ou lorsqu'un délai d'attente a été atteint (voir les utilisations de :

ActivityStackSupervisor#scheduleTopResumedActivityStateIfNeeded()

Un nouvel élément de transaction TopResumedActivityChangeItem a été ajouté pour signaler les changements d'état les plus repris aux clients et tirer parti de l'architecture ActivityLifecycler d'Android 9.

L'état de reprise supérieure est stocké côté client, et chaque fois que l'activité passe à RESUMED ou PAUSED , il vérifie également si le rappel onTopResumedActivityChanged() doit être invoqué. Cela permet un certain découplage dans la communication des états du cycle de vie et de l'état de reprise par le haut entre les côtés serveur et client.