Contextmenu-Item deaktivieren

jerevat

Mitglied
Hallo,

ich habe hier Contextmenu-Items, die unter bestimmten Bedingungen disabled gesetzt werden sollen.
Und genau hier ist der Knackpunkt. Es tut sich nichts.
Die Suchergebnisse sind sich einig, dass die Deaktivierung im onPrepareOptionsMenu() erfolgen soll.

Java:
@Override
public boolean onContextItemSelected(@NonNull MenuItem item) {
    if (item.getItemId() == R.id.menuItem1) {
        Toast.makeText(this, "Item1", Toast.LENGTH_SHORT).show();
    } else if (item.getItemId() == R.id.menuItem2) {
        Toast.makeText(this, "Item2", Toast.LENGTH_SHORT).show();
    } else
        return super.onContextItemSelected(item);
}

@Override
public boolean onPrepareOptionsMenu(Menu menu) {
    menu.findItem(R.id.menuItem2).setEnabled(false);
    //menu.findItem(R.id.menuItem2).setOnMenuItemClickListener(null);
    return true;
}

Das führt dazu, dass das Menü weiterhin aufploppt, jedes Item anklickbar ist und das Klick-Ereignis ausgeführt wird.
Wie handhabt ihr das so?
 

Oneixee5

Top Contributor
Das Konzept der "Deaktivierung" eines Elements der Benutzeroberfläche scheint eine gute Idee zu sein, um den Benutzern mitzuteilen, dass eine bestimmte Aktion nicht verfügbar ist. Das Problem ist, dass die meisten Implementierungen ein deaktiviertes Element völlig tot und reaktionsunfähig machen. Dies ist ein Problem für jeden Benutzer, der sich mit dem Programm vertraut macht. Das deaktivierte Element gibt keinen Hinweis darauf, warum es deaktiviert ist. Es gibt keine Möglichkeit für den Benutzer, dies herauszufinden! Der Benutzer muss "einfach wissen", warum es tot ist. Der wichtigste Aspekt einer guten Benutzeroberfläche ist, dass sie den Menschen hilft, die Benutzung zu erlernen, und das bedeutet, dass Dinge, die der Benutzer "einfach wissen" muss, von vornherein eliminiert werden. Solche Elemente sollten nie völlig tot sein, sondern eine Meldung ausgeben, die erklärt, warum die Funktion zu diesem Zeitpunkt nicht verwendet werden kann.

Die visuelle Anzeige ist eindeutig gut. Aber warum müssen die Menüs deaktiviert werden und es völlig unempfänglich machen? Deaktivierte Menüpunkte können Ihnen nicht sagen, warum diese Option nicht benötigt wird. Deaktivierte Menüpunkte sagen nichts darüber aus, warum sie deaktiviert sind. Es kann Minuten oder Stunden dauern, bis man herausfindet, warum eine Option deaktiviert ist. In manchen Fällen kann es sogar ewig dauern.
 

jerevat

Mitglied
Du kannst doch auch ein Menue Icon sichtbar und nicht sichtbar seten zb mit setVisible().

onPrepareOptionsMenu ist ja ein Callback was von System aufgerufen wird , nicht von dir.
Dort kannst du das Menue auch verändern . Eine Änderung könntest du mit
invalidateOptionsMenu() anstosen.



Java:
@Override
public boolean onPrepareOptionsMenu(Menu menu) {
    menu.getItem(0).setTitle("dasdasdasd");
    invalidateOptionsMenu();
    invalidateMenu();
    return super.onPrepareOptionsMenu(menu);
}
In dem Callback tut sich nichts. Nicht einmal den Text des Menüs kann ich überschreiben.

Die visuelle Anzeige ist eindeutig gut. Aber warum müssen die Menüs deaktiviert werden und es völlig unempfänglich machen?
Ein Texteditor z.B. hat auch ein Popupmenu mit Optionen wie Kopieren oder Einfügen.
Es macht Sinn solche Optionen zu deaktivieren, wenn kein Text selektiert oder kein Text in der Zwischenablage ist.
 

Jw456

Top Contributor
Ich habe doch gesagt das das eine callback Methode ist. Die vom Andtoid System aufgrufen wird.
Und das musst du veranlassen. Aber. Natürlich nicht in der Methode selber.
Sondern in einem anderen Listerner.
 

Jw456

Top Contributor
Dort wo du das ändern des menue veranlassen willst.
Also dort wo du der meinung bist das dwr user es nicht mehr bentzen darf. Das musst du schon selber wissen. Das ist deine Programm Logik.
 

jerevat

Mitglied
Dort wo du das ändern des menue veranlassen willst.
Also dort wo du der meinung bist das dwr user es nicht mehr bentzen darf. Das musst du schon selber wissen. Das ist deine Programm Logik.
Sollte in einem LongClickListener der Listview passieren, und wenig überraschend war das Enable-Setzen oder irgendwas im Contextmenu setzen nicht erfolgreich.
Also bin ich auf das Popupmenu umgestiegen und da funktionierte alles auf Anhieb.

Java:
import android.widget.PopupMenu;

public class MainActivity extends AppCompatActivity implements android.widget.PopupMenu.OnMenuItemClickListener {
   
    ListView _listView;
    PopupMenu _menu;
    int _menuIndex = 0;

    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        _listView = (ListView) findViewById(R.id.listView);

        _lvHolidays.setOnItemLongClickListener(new AdapterView.OnItemLongClickListener() {
            @Override
            public boolean onItemLongClick(AdapterView<?> adapterView, View view, int i, long l) {
                _menuIndex = i;
                doPopup(view);
                return true;
            }
        });
    }
    
    private void doPopup(View v) {
        _menu = new PopupMenu(this, v);
        _menu.setOnMenuItemClickListener(this);
        _menu.inflate(R.menu.main_menu);
        // if ( .... )
            _menu.getMenu().findItem(R.id.menuItem2).setEnabled(false);
        _menu.show();
    }
}
Nein macht es nicht. Eine Meldung über das Problem würde Sinn machen. Wenn du mir nicht glaubst, dan informiere dich auf einschlägigen Webseiten.
Jedes Mal auf eine Meldung reagieren zu müssen, ist ein Vorgang zuviel. Besser, man lässt es gar nicht dazu kommen, indem man solche Elemente deaktiviert, wenn sie vorerst keinen Nutzen haben.
 

Neue Themen


Oben