Android: Quand onCreateOptionsMenu est-il appelé pendant le cycle de vie de l'activité?

149

J'ai mis quelques points d'arrêt onCreate(un au début et un à la fin de la méthode), et j'en ai également mis un au début de onCreateOptionsMenu. La onCreateméthode est appelée en premier et avant qu'elle ne se termine onCreateOptionsMenu.

J'essaie de séparer le Fragmentcode de navigation dans mon application, j'ai donc quelques objets auxquels je délègue onCreateOptionsMenuen fonction de si l'application s'exécute sur un téléphone / une tablette (j'utilise la taille de l'écran pour déterminer cela, mon fichier de mise en page pour les grands écrans ont une vue que je vérifie une fois la mise en page gonflée). Le problème que je rencontre est que je crée ces objets dans onCreate et que je reçois une exception de pointeur nul lorsque je référence l'objet dans onCreateOptionsMenu.

Christopher Perry
la source

Réponses:

112

La méthode onCreate est appelée en premier, et avant la fin, onCreateOptionsMenu est appelé.

Ce sera vrai sur les appareils et les applications dotés d'une barre d'action officielle de style Honeycomb. S'il n'y a pas de barre d'action, onCreateOptionsMenu()ne doit pas être appelé jusqu'à ce que l'utilisateur appelle le menu, généralement en appuyant sur le bouton MENU.

(J'utilise la taille de l'écran pour le déterminer, mon fichier de mise en page pour les grands écrans a une vue que je vérifie une fois la mise en page gonflée)

Ce test s'interrompra très prochainement, une fois que Ice Cream Sandwich sera expédié. D'après ce que je peux dire, les téléphones ICS auront des barres d'action (mais peut-être pas des barres système).

CommonsWare
la source
J'ai oublié de mentionner que j'utilise la bibliothèque ActionbarSherlock. Votre réponse m'a rappelé. C'est probablement la raison de ce comportement, puisque c'est un wrapper sur la bibliothèque de compatibilité, qui place les éléments de menu dans la "ActionBar".
Christopher Perry
@commonsware - Cela signifie sur les appareils et les applications qui n'ont pas de barre d'action. Le menu apparaîtra même si onCreateOptionsMenu n'a pas d'élément visible?
NinjaCoder
12
dans mon cas onCreateMenu appel après onResume
Kostya Khuta
1
Oui j'ai le même problème ... Mais mon code est lié à un Fragment.
Yoann Hercouet
J'ai commencé à avoir NPEen vérifiant si le nav drawer fragmentétait ouvert onCreateOptionsMenu. J'ai dû mettre des vérifications nulles dans le onCreateOptionsMenu de l'activité, ainsi que dans le rappel que le fragment utilisait dans son onCreateOptionsMenu. Vraiment bizarre parce que cela ne se produisait que sur quelques écrans, mais systématiquement sur ceux-ci.
theblang
54

Dans mon cas sur Android 2.3 et avec la FragmentActivitybibliothèque de support v4, l'ordre des méthodes de cycle de vie invoquées est le suivant:

07-18 18:29:21.629  20183-20183/? I/onCreate:
07-18 18:29:21.719  20183-20183/? I/onStart: 
07-18 18:29:21.719  20183-20183/? I/onResume: 
07-18 18:29:21.739  20183-20183/? I/onCreateOptionsMenu:
Roman Nazarevych
la source
27

J'ai trouvé si dans onResume () j'appelle

invalidateOptionsMenu();

puis onCreateOptionsMenu (menu menu) est appelé par la suite - selon le cycle de vie de l' activité (je pense que c'est le terme correct ici) , comme indiqué par @ tir38

@Override
public void onResume() {
    super.onResume();
    invalidateOptionsMenu();
}
Gene Bo
la source
4
Si vous utilisez actionbarsherlock, appelez cette méthodesupportInvalidateOptionsMenu();
Shan Xeeshi
3
Soyez prudent lorsque vous dites «immédiatement». Cela n'arrivera pas vraiment immédiatement. Lorsque vous invalidateOptionsMenu, un travail pour (re) créer le menu d'options sera ajouté à la file d'attente des messages de l'interface utilisateur. Tout ce qui est dans la file d'attente sera exécuté en premier.
tir38
21

Ajout dans la réponse ci-dessus, Dans le cas d'ICS et Honeycomb onCreateOptionsMenu est appelé après onCreate et onPostCreate alors que dans Gingerbread et les versions antérieures, il est appelé après onCreate mais avant onPostCreate. C'est la seule différence que j'ai trouvée.

Pawan Maheshwari
la source
3

D'après mon expérience ActionBarActivitydu support v7, la méthode onCreateOptionsMenu()appelée au setContentView()milieu onCreate()apparaît sur 4.1.1.

Mais sur 4.4, une autre histoire est onCreateOptionMenu()appelée après onCreate(). Aussi, je ne sais pas que ce sera peut-être immédiatement après, peut-être pas. Mais c'est fait après. Je n'ai pas testé sur d'autres versions mais la 4.1.1 est la première où j'ai eu un problème avec l'ordre d'initialisation.

Yevgen Kulik
la source
Peut-être avez-vous besoin d'utiliser supportInvalidateOptionsMenu()?
David d C e Freitas
2

Je suggère de créer une fonction de rappel dans votre fragment pour éviter les problèmes de synchronisation avec onResume () et onCreateOptionsMenu ().

faire les travaux suivants sans faute pour moi:

  1. créez et ajoutez votre fragment à votre activité
  2. laissez une référence de ce fragment dans votre activité
  3. créer une méthode publique doSomethingWithTheMenu () dans votre fragment
  4. appelez cette méthode depuis votre activité lorsque onCreateOptionsMenu (menu Menu) est appelé.

exemple:

@Override
public boolean onCreateOptionsMenu(Menu menu) {
    if (this.myFragment != null) {
        this.myFragment.doSomethingWithTheMenu(menu);
    }
    return true;
}
datayeah
la source