374 votes

Comment masquer un élément de menu dans la barre d'action ?

J'ai une barre d'action avec un élément de menu. Comment puis-je masquer/afficher cet élément de menu ?

C'est ce que j'essaie de faire :

MenuItem item = (MenuItem) findViewById(R.id.addAction);
item.setVisible(false);
this.invalidateOptionsMenu();

527voto

K-ballo Points 44794

Obtenir un MenuItem pointant vers cet élément, appelez setVisible pour ajuster sa visibilité et ensuite appeler invalidateOptionsMenu() sur votre activité afin que le menu de la barre d'action soit ajusté en conséquence.

Mise à jour : A MenuItem n'est pas une vue ordinaire qui fait partie de votre mise en page. C'est quelque chose de spécial, complètement différent. Votre code renvoie null para item et c'est ce qui cause le crash. Ce dont vous avez besoin à la place, c'est de faire :

MenuItem item = menu.findItem(R.id.addAction);

Voici l'ordre dans lequel vous devez appeler : premier appel invalidateOptionsMenu() et ensuite à l'intérieur onCreateOptionsMenu(Menu) obtenir une référence au MenuItem (en appelant menu.findItem() ) et appeler setVisible() sur elle

1 votes

C'est ce à quoi j'ai pensé au départ, mais cela fait planter l'application.

3 votes

@Stir Zoltán : Eh bien c'est comme ça qu'il faut faire, il se peut que vous le fassiez mal si cela fait planter l'application. Par exemple, votre MenuItem peut être null parce que vous utilisez getItem au lieu de findItem . Nous ne pourrons jamais le savoir, sans voir à la fois votre code et votre journal de bord.

0 votes

OK mais comment obtenir une référence au menu en dehors de la méthode onCreateOptionsMenu ?

183voto

P1r4nh4 Points 482

J'ai trouvé un addendum à cette question :

Si vous souhaitez modifier la visibilité de vos éléments de menu en cours de route, il vous suffit de définir une variable membre dans votre activité pour vous rappeler que vous souhaitez masquer le menu et d'appeler invalidateOptionsMenu() et de cacher les éléments dans votre surcharge onCreateOptionsMenu(...) méthode.

//anywhere in your code
...
mState = HIDE_MENU; // setting state
invalidateOptionsMenu(); // now onCreateOptionsMenu(...) is called again
...

@Override
public boolean onCreateOptionsMenu(Menu menu)
{
    // inflate menu from xml
    MenuInflater inflater = getSupportMenuInflater();
    inflater.inflate(R.menu.settings, menu);

    if (mState == HIDE_MENU)
    {
        for (int i = 0; i < menu.size(); i++)
            menu.getItem(i).setVisible(false);
    }
}

Dans mon exemple, j'ai caché tous les éléments.

2 votes

C'est exactement ce que je cherchais. Maintenir le MenuItem et appeler setVisible() ne semblait pas faire ce que j'attendais (peut-être parce que j'appelais invalidateOptionsMenu() après, reconstruisant ainsi le menu), mais quoi qu'il en soit -- cela fonctionne exactement comme je l'espérais, merci !

4 votes

Si vous voulez cacher chaque élément, il existe un moyen plus simple. Au lieu de passer en boucle par chaque élément ici, vous pourriez simplement faire : if (HIDE_MENU) { return false; } else { getSupportMenuInflater().inflate(R.menu.menu_settings, menu); return true; } La documentation indique : "Vous devez retourner true pour que le menu soit affiché ; si vous retournez false, il ne sera pas affiché".

0 votes

J'aimerais également mentionner que cette approche est beaucoup plus propre que la réponse acceptée. Merci de votre participation !

95voto

suhas_sm Points 401

Oui.

  1. Vous pouvez définir un indicateur/condition.
  2. Appelez invalidateOptionsMenu() lorsque vous souhaitez masquer l'option. Ceci appellera onCreateOptionsMenu() .
  3. Sur onCreateOptionsMenu() l'indicateur/condition et l'afficher ou le masquer de la manière suivante le cacher de la manière suivante :
MenuItem item = menu.findItem(R.id.menu_Done);

if (flag/condition)) {
  item.setVisible(false); 
} else { }

2 votes

Cela ne devrait-il pas être invalidateOptionsMenu au lieu de invalidateOptions ?

3 votes

Si vous faites de votre drapeau un booléen, vous pouvez simplement définir la visibilité de l'élément sur le drapeau (ou !drapeau) si nécessaire. Ainsi, item.setVisbility(!flag) ; fait de cette opération une ligne unique sans condition if.

0 votes

Où est définie la variable "menu" ?

40voto

Elias Points 2409

Vous pouvez appeler ça comme ça :

MenuItem item = menu.findItem(R.id.my_item);
item.setVisible(false);

Mise à jour :

Assurez-vous que votre code ne renvoie pas null para item ou cela peut faire planter l'application.

0 votes

Si vous utilisez cette méthode, l'élément continuera de consommer de l'espace et vous risquez de vous retrouver avec un "vide" dans votre interface utilisateur à l'endroit où le bouton devrait se trouver. L'utilisation de removeItem dans onPrepareOptionsMenu() fera l'affaire.

24voto

hotzen Points 828

N'a pas fonctionné pour moi. J'ai dû utiliser explicitement onPrepareOptionsMenu pour rendre un élément invisible.

Alors utilisez onCreateOptionsMenu pour créer le menu et onPrepareOptionsMenu pour modifier la visibilité, etc.

1 votes

Pour moi, ça a marché dans les deux sens, mais en se basant sur La documentation d'Android onPrepareOptionsMenu semble être le bon endroit pour faire ce type d'opération : "Préparer le menu d'options standard de l'écran à être affiché. Cette opération est appelée juste avant l'affichage du menu, et chaque fois qu'il est affiché. Vous pouvez utiliser cette méthode pour activer/désactiver efficacement des éléments ou pour modifier dynamiquement son contenu."

0 votes

Oui, c'est l'idéal. Pour la logique d'affichage et de masquage, il faut utiliser onPrepareOptionsMenu() plutôt que onCreateOptionsMenu(), car il n'est appelé qu'une seule fois et n'est donc pas utile si vous voulez modifier les éléments du menu après son initialisation. Donc, gonfler dans onCreate, mais afficher/masquer dans onPrepare, puis utiliser invalidateOptionsMenu() pour rafraîchir le menu.

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X