There does not seem to be API for programmatically "selecting" ContextMenu items? By selecting I mean the equivalent of tapping up and down keys (or hovering the mouse over an item). I really only need to select the first item, when a ContextMenu is shown. I attempted to fire a down keyevent upon showing the menu, but nothing happened.. perhaps I constructed the event wrongly.
2 Answers
To get this working, we could use some private API. ContextMenu
skin (ContextMenuSkin
) uses a ContextMenuContent
object, as a container with all the items.
We just need to request the focus for the first of these items.
But for this we could just use some lookups to find the first menu-item
CSS selector. This has to be done after the stage has been shown.
This example will show a context menu with focus on the first item:
@Override
public void start(Stage primaryStage) {
MenuItem cmItem1 = new MenuItem("Item 1");
cmItem1.setOnAction(e->System.out.println("Item 1"));
MenuItem cmItem2 = new MenuItem("Item 2");
cmItem2.setOnAction(e->System.out.println("Item 2"));
final ContextMenu cm = new ContextMenu(cmItem1,cmItem2);
Scene scene = new Scene(new StackPane(), 300, 250);
primaryStage.setScene(scene);
primaryStage.show();
scene.setOnMouseClicked(t -> {
if(t.getButton()==MouseButton.SECONDARY){
cm.show(scene.getWindow(),t.getScreenX(),t.getScreenY());
// Request focus on first item
cm.getSkin().getNode().lookup(".menu-item").requestFocus();
}
});
}

- 44,311
- 7
- 104
- 132
-
How i can select the 2 or n-nth item?I used this but not working (contextMenu.getSkin().getNode().lookup(".menu-item:nth-child(4)").requestFocus();) – GOXR3PLUS May 29 '16 at 03:27
-
Use `cm.getSkin().getNode().lookupAll(".menu-item")` to get a set of all the items, then iterate to get the desired one. – José Pereda May 29 '16 at 10:13
-
hmm .. meanwhile (fx18+) the explicit requestFocus doesn't seem to be necessary any longer, the first item is selected and accessible for enter (aka: action triggered after pressing enter) by default – kleopatra Mar 16 '22 at 17:01
-
ookay .. the default focus/selection is on first item for the first showing, subsequent showings don't auto-select .. bug or feature? – kleopatra Mar 16 '22 at 17:14
For me solution provided in accepted answer didn't work correctly as item was only highlighted but not really selected (<Enter> was not accepting a value).
Instead of that constructing a proper KeyEvent did the work except a bug that only after first letter popup was working correctly.
Finally I combined both and got what I'd wanted:
// 'this' is related to parent component of ContextMenu
popup.show(this, x, y);
// Request focus on first item (sort of hack)
popup.getSkin().getNode().lookup(".menu-item").requestFocus();
this.fireEvent(new KeyEvent(
KeyEvent.KEY_PRESSED, "", "",
KeyCode.DOWN, false, false, false, false));

- 179
- 1
- 14
-
hmm .. wondering why the example in Jose's answer doesn't work for you (it does for me: hitting enter after the contextMenu is shown triggers the action of the first menuItem). What's your fx version/OS? – kleopatra Mar 16 '22 at 16:59
-
Windows 10 / Fx 11.0.2.. Couldn't it be related to different show(...) methods used? – BitLord Mar 16 '22 at 17:01
-
hmm .. Jose's example worksforme for fx11 (as well as later), even without the explicit requestFocus. What am I missing? – kleopatra Mar 16 '22 at 17:06
-
It's strange. Tried to use show(...) on Window. It is almost working now except very first popup appearing (in that case item is still unacceptable). – BitLord Mar 16 '22 at 17:14
-
hmm .. my tentative, not formally tested, observations: a) if the item is selected, it reacts to enter b) with explict calling item.requestFocus after showing it is always selected c) without explicit calling requestFocus, the item is only selected on first showing not on subsequent showing. There is no difference between fx11 and fx18+, nor between using the show taking a window/control. – kleopatra Mar 16 '22 at 17:30
-
I get the behavior as in c) in case without explicit requestFocus() but with firing KeyEvent. PS I use ContextMenu for sort of autocompletion in TextArea, maybe it is crucial. – BitLord Mar 16 '22 at 17:46