首页 文章

TextField requestFocus丢失第一个按键? (JavaFX2)

提问于
浏览
0

我有一个嵌入在AnchorPane中的TextField以及几个按钮 . TextField默认没有焦点,因为我希望它显示提示文本(请参阅prompttext in textfield of javafx 2 hides on focus after some java 7 update - 这似乎是一个已知问题) . 我希望TextField在用户按下ENTER或ESCAPE以外的任何键时获得焦点 . 我've created an EventHandler that is attached to my AnchorPane.setOnKeyPressed() (and to the buttons' onKeyPressed侦听器)在键盘事件上运行一个开关,默认为:

default:
                    Platform.runLater(new Runnable() {
                        @Override
                        public void run() {
                            myTxt.requestFocus();
                            myTxt.fireEvent(event);
                        }
                    });

这会将焦点发送到TextField;但是,我按下的键实际上并没有显示在TextField中 . 换句话说,如果我输入

test

TextField将获得焦点,但仅限于此

est

出现在现场 . 我已经为我的KeyEvent监听器添加了logpane / buttons和TextField的日志记录,它向我显示:

Oct 29, 2013 2:22:11 PM com.myapp.AppMainController$4 handle
INFO: Got key t at source Button[id=myBtn, styleClass=button]
Oct 29, 2013 2:22:11 PM com.myapp.AppMainController$6 handle
INFO: Got key t at source TextField[id=myTxt, styleClass=text-input text-field]

因此,关键事件是进入TextField,但它永远不会显示在框中 . 如果我继续输入,剩下的文本会显示出来,如果我通过输入像SHIFT-T这样的组合来获得焦点,那么它就会显示出来(看起来shift按键是“丢失”的那个)而不是字母本身) .

有人遇到过这种情况么?这是JavaFX2中的错误还是我做错了什么?我使用Java 7u45及其附带的JavaFX 2.2.45作为参考 .

Edit 1: 我应该澄清,无论焦点是从窗格还是按钮切换,都会在将焦点切换到TextField时发生这种情况 .

Edit 2 (Solution): 实际问题是"Platform.runLater"包装器 . 如果我只是在没有"runLater"的情况下请求焦点,我的关键事件会出现在我的预期中 .

default:
                        myTxt.requestFocus();

1 回答

  • 1

    我不确定你的上下文是怎样的,但我这样解决了

    public class Main extends Application {
        @Override
        public void start(Stage stage) {        
            final VBox vbox = new VBox();
            vbox.setSpacing(5);
            vbox.setPadding(new Insets(10, 0, 0, 10));
    
            final TextField textField = new TextField();
            final Button button = new Button();
    
            vbox.getChildren().addAll(textField, button);
    
    
            vbox.onKeyPressedProperty().set(new EventHandler<KeyEvent>() {
                @Override public void handle(KeyEvent event) {
                    textField.requestFocus();
                }
            });
    
            stage.setScene(new Scene(vbox, 300, 500));
            stage.show();
        }
    
        public static void main(String[] args) {
            launch(args);
        }
    }
    

    重要的是

    vbox.onKeyPressedProperty().set(new EventHandler<KeyEvent>() {
        @Override public void handle(KeyEvent event) {
            textField.requestFocus();
        }
    });
    

    通过使用keyPressedProperty,它将在您输入任何按钮时激活,而不是在您键入/释放它时激活 . 与首都和非首都合作 .

    Edit

    插入按钮是为了能够通过点击它来“测试”TextField的非焦点,你可以给它焦点 .

    Edit 2

    为了匹配实际答案,您可以使用在多种情况下实际需要的Platform.runLater进行一些解决方法 . 这是IntegerField中的代码(扩展TextField),所以我是它自己的方法 .

    this.setOnMouseClicked(new EventHandler<MouseEvent>() {
        @Override
        public void handle(MouseEvent paramT) {
            Platform.runLater(new Runnable() {
                @Override public void run() {
                    if (isFocused() && !getText().isEmpty()) {
                        selectAll();
                    }               
                }
            });
        }
    });
    

相关问题