Java 在Libgdx文本字段中输入密钥处理

Java 在Libgdx文本字段中输入密钥处理,java,android,input,libgdx,Java,Android,Input,Libgdx,我在libgdx应用程序中设置了一个包含三个文本字段的stage,在桌面模式和安卓模式下,我得到了不同的行为。在Android上,键入enter键将光标移动到下一个文本字段。在桌面上,键入enter键不起任何作用 如何使光标在两个平台上一致移动?我希望能够在用户输入时将焦点设置为另一个字段。在Android上,无论我将焦点设置为什么,默认的回车键行为都会将焦点跳到后面的字段 以下是我当前用于移动光标和清除下一个字段的代码: stage.addListener(new InputListe

我在libgdx应用程序中设置了一个包含三个文本字段的stage,在桌面模式和安卓模式下,我得到了不同的行为。在Android上,键入enter键将光标移动到下一个文本字段。在桌面上,键入enter键不起任何作用

如何使光标在两个平台上一致移动?我希望能够在用户输入时将焦点设置为另一个字段。在Android上,无论我将焦点设置为什么,默认的回车键行为都会将焦点跳到后面的字段

以下是我当前用于移动光标和清除下一个字段的代码:

    stage.addListener(new InputListener() {
        @Override
        public boolean keyUp(InputEvent event, int keycode) {
            if (keycode == Input.Keys.ENTER) {
                nextField();
            }
            return false;
        }
    });
    Gdx.input.setInputProcessor(stage);
}

private void nextField() {
    TextField nextField = 
            stage.getKeyboardFocus() == text1
            ? text2
            : stage.getKeyboardFocus() == text2
            ? text3
            : text1;
    nextField.setText("");
    stage.setKeyboardFocus(nextField);
}
我已尝试取消事件或从处理程序方法返回true,但在代码完成后焦点仍在移动


我的完整示例代码是。

我找到了一个解决方案,但我仍然希望有一个更干净的解决方案,使两个平台的行为方式相同

我添加了一个标志来指示默认情况下焦点是否会移动,并且我仅在焦点自身不移动时更改焦点。然后,我从Android的
MainActivity
类或桌面的
Main
类设置该标志。我已经发布了完整的示例代码


TextField使用私有的内部InputListener,该函数在构造函数中初始化,不能轻易覆盖。更改焦点的相关代码在此侦听器的keyTyped方法期间:

public boolean keyTyped (InputEvent event, char character) {
     [...]
     if ((character == TAB || character == ENTER_ANDROID) && focusTraversal)
         next(Gdx.input.isKeyPressed(Keys.SHIFT_LEFT) || Gdx.input.isKeyPressed(Keys.SHIFT_RIGHT));
     [...]
}
一个简单的解决方案是同时禁用焦点遍历,并设置一个com.badlogic.gdx.scenes.scene2d.ui.TextFieldListener来自动执行遍历:

TextField textField
textField.setFocusTraversal(false);
textField.setTextFieldListener(new TextFieldListener() {
    @Override
    public void keyTyped(TextField textField, char key) {
        if ((key == '\r' || key == '\n')){
            textField.next(Gdx.input.isKeyPressed(Keys.SHIFT_LEFT) || Gdx.input.isKeyPressed(Keys.SHIFT_RIGHT));
        }
    }
});
如果您需要能够使用TextFields setFocusTraversal方法启用和禁用焦点遍历,那么在将内部InputListener添加到TextField时,还可以将其包装到您自己的侦听器中,这是一个相当棘手的解决方案(但我不建议这样做):

编辑:
再想一想,您也可以使用第一种解决方案来实现这一点,只需覆盖TextField的setFocusTraversal,并在调用此方法时启用/禁用您自己的侦听器。

gdx-1.9.4中,我可以执行以下操作:

final TextField newMessageTextField = new TextField("", uiSkin){
    @Override
    protected InputListener createInputListener () {
        return new TextFieldClickListener(){
            @Override
            public boolean keyUp(com.badlogic.gdx.scenes.scene2d.InputEvent event, int keycode) {
                System.out.println("event="+event+" key="+keycode);
                return super.keyUp(event, keycode);
            };
        };
    }
};
按下箭头后,将焦点放在我得到的文本字段上

event=keyUp key=19
event=keyUp key=20
event=keyUp key=22
event=keyUp key=21

我认为禁用焦点遍历将完全满足我的需要。谢谢。它起作用了,我已经更新了我的文档以包含它。赏金是你的。
final TextField newMessageTextField = new TextField("", uiSkin){
    @Override
    protected InputListener createInputListener () {
        return new TextFieldClickListener(){
            @Override
            public boolean keyUp(com.badlogic.gdx.scenes.scene2d.InputEvent event, int keycode) {
                System.out.println("event="+event+" key="+keycode);
                return super.keyUp(event, keycode);
            };
        };
    }
};
event=keyUp key=19
event=keyUp key=20
event=keyUp key=22
event=keyUp key=21