2013-12-17 3 views
10

Я новичок на javafx. Я хочу показать всплывающее меню в правой клавише мыши. Я нахожу один учебник Here и Here, но не понимаю. Я хочу создать всплывающее меню, которое отображается на изображении по этой ссылке.Как создать всплывающее меню

Прямо сейчас я создаю сцену, но мне не нужна сцена. Мне нужно показать всплывающее меню, которое отображается по щелчку правой кнопкой мыши и закрывается, когда я нажимаю в любом месте.

Вот мой код, в котором я использую сцену, но мне нужно всплывающее меню ope, как показано выше.

public void MouseClickedOnTree(MouseEvent event) { 
if (event.isSecondaryButtonDown()) { 

     System.out.println("secondary press"); 
     final Stage optionstage = new Stage(); 

     VBox vBox = new VBox(5); 
     vBox.setMinHeight(50); 
     vBox.setMinWidth(50); 
     Button btnNewTestBed = new Button("New Testbed"); 
     btnNewTestBed.setOnAction(new EventHandler<ActionEvent>() { 
      @Override 
      public void handle(ActionEvent event) { 
       try { 
        optionstage.close(); 
        stage.show(); 
       } catch (IOException ex) { 
        Exceptions.printStackTrace(ex); 
       } 
      } 
     }); 
     Button btnOpenTestbed = new Button("Open Testbed"); 
     btnOpenTestbed.setOnAction(new EventHandler<ActionEvent>() { 
      @Override 
      public void handle(ActionEvent event) { 
       optionstage.close(); 

      } 
     }); 
     optionstage.addEventHandler(KeyEvent.KEY_PRESSED, new EventHandler<KeyEvent>() { 
      @Override 
      public void handle(KeyEvent t) { 
       if (t.getCode() == KeyCode.ESCAPE) { 
        System.out.println("click on escape"); 
        //Stage sb = (Stage) label.getScene().getWindow();//use any one object 
        if(optionstage.isShowing()) 
         optionstage.close(); 
       } 
      } 
     }); 

     vBox.getChildren().addAll(btnNewTestBed, btnOpenTestbed); 
     optionstage.setScene(new Scene(vBox, 100, 100)); 
     //stage.setScene(new Scene(new Group(new Text(50,50, "my second window")))); 
     optionstage.setX(event.getSceneX()); 
     optionstage.setY(event.getScreenY()); 
     optionstage.initStyle(StageStyle.UNDECORATED); 
     optionstage.show(); 

    } 

Просьба предоставить мне любую ссылку или ссылку.

ответ

20

Контекст вашего кода не очень ясен: это внутри обработчика событий? Если да, для чего это обработчик событий? Если нет, то что event в начале if заявление?

Две ссылки, которые вы предоставляете, довольно сложны; в JavaFX (в отличие от Swing) вы должны рассматривать только класс подкласса существующих классов Node для довольно продвинутых вариантов использования. Вам не нужен этот уровень сложности, чтобы создать всплывающее меню.

Самый простой способ создать всплывающее меню - для Control (или подкласса); Вам просто нужно создать ContextMenu добавить MenuItem S к нему, и установить его в качестве contextMenu на вашем управления:

TextField textField = new TextField("Type Something"); // we will add a popup menu to this text field 
final ContextMenu contextMenu = new ContextMenu(); 
MenuItem cut = new MenuItem("Cut"); 
MenuItem copy = new MenuItem("Copy"); 
MenuItem paste = new MenuItem("Paste"); 
contextMenu.getItems().addAll(cut, copy, paste); 
cut.setOnAction(new EventHandler<ActionEvent>() { 
    @Override 
    public void handle(ActionEvent event) { 
     System.out.println("Cut..."); 
    } 
}); 
// ... 
textField.setContextMenu(contextMenu); 

Если вы хотите использовать ContextMenu на узле, который не является ControlPane или Shape, например), вы не имеете метод setContextMenu(...), так что вам просто нужно немного больше работы:

final AnchorPane pane = new AnchorPane(); 
// fill pane with nodes, etc 
// create context menu and menu items as above 
pane.setOnMousePressed(new EventHandler<MouseEvent>() { 
    @Override 
    public void handle(MouseEvent event) { 
     if (event.isSecondaryButtonDown()) { 
      contextMenu.show(pane, event.getScreenX(), event.getScreenY()); 
     } 
    } 
}); 

ВИДЕТЬ Javadocs для ContextMenu или tutorial для получения более подробной информации.

+0

, но я хочу показать его на древовидной структуре. Я хочу показать всплывающее окно в Treeview, когда я нажимаю правой кнопкой мыши на treeview –

+0

. Я использую этот код, но popup не показывает 'contextMenu.show (soariteTree, event.getScreenX(), event.getScreenY()); ' –

+0

Извините, теперь он работает ... Я ставлю код объявления за пределами события, тогда он работает ... спасибо .. –

10

James_D уже предоставил рабочий пример, соответствующий учебникам, но у меня возникли проблемы с ним. Джеймс прав, говоря, что для любого Node типа Control правильный способ открыть контекстное меню - использовать Control.setContextMenu(). Однако в отличие от учебника правильного способа зарегистрировать контекстное меню на неуправляющих узлах следующим образом (Java 8):

pane.addEventHandler(ContextMenuEvent.CONTEXT_MENU_REQUESTED, event -> { 
     contextMenu.show(pane, event.getScreenX(), event.getScreenY()); 
     event.consume(); 
    }); 
    pane.addEventHandler(MouseEvent.MOUSE_PRESSED, event -> { 
     contextMenu.hide(); 
    }); 

Это согласуется с, что делает за кулисами setContextMenu. Реализация setContextMenu для элементов управления использует и потребляет ContextMenuEvent, но не потребляет событие мыши. Это означает, что если вы зарегистрируете прослушиватель для MouseEvent на панели и используете setContextMenu в элементе управления на панели, правый щелчок на элементе управления фактически откроет оба контекстных меню: элемент управления будет прослушивать и использовать ContextMenuEvent, пока панель прослушивает и потребляет MouseEvent. Я обнаружил в своем коде с openjdk-8, что регистрация слушателя ContextMenuEvent на панели разрешила эту проблему с дублирующимся контекстным меню.

Я также обнаружил, что меню, зарегистрированное на панели, не отменяется по умолчанию, когда пользователь щелкает в другом месте. Слушатель MOUSE_PRESSED, который не потребляет его событие, гарантирует, что меню будет отклонено, когда это будет.

+0

Что такое панель в контекстеMenu.show (панель ...); –

+0

Это действительно правильное решение. Слишком плохо, что вы не выше. –

+0

также существует метод setOnContextMenuRequested() в узле –

Смежные вопросы