我有以下代码,
import javafx.application.Application;
import javafx.beans.value.ObservableValue;
import javafx.scene.Scene;
import javafx.scene.layout.StackPane;
import javafx.stage.Stage;
public class TextFieldTest extends Application {
public static void main(String[] args) {
launch();
}
@SuppressWarnings("static-access")
public void start(Stage stage) {
stage.setTitle("Hello World!");
TextField field = new TextField("hello world");
field.textProperty().addListener((ObservableValue<? extends String> observable, String oldValue, String newValue) -> {
System.out.println(field.getCaretPosition());
field.positionCaret(5);
});
StackPane root = new StackPane();
root.getChildren().addAll(field);
stage.setScene(new Scene(root, 250, 250));
stage.show();
}
}
当我在TextField
中键入内容时,我希望插入符号移动到位置5,但这没有发生。有什么问题吗?
答案 0 :(得分:-1)
插入号移动到处理程序中的正确位置,但随后在内部重置到文本的末尾。 println
调用显示位置为5
:
field.textProperty().addListener((ObservableValue<? extends String> observable, String oldValue, String newValue) -> {
field.positionCaret(5);
System.out.println("After:" + field.getCaretPosition()); // After:5
});
但是,textProperty
更新后,TextField
在内部放置插入记号,从而覆盖处理程序中设置的值。
相反,TextField
本身定义的事件在插入符的内部定位之后被触发,因此新位置生效。例如:
field.setOnKeyTyped(e -> {
field.positionCaret(5);
});
将插入号显示在位置5。
基于JavaFX 8分析
在执行处理程序之后,执行将最终到达私有方法TextInputControl.replaceText(int, String, int, int)
,将更改发生的插入符号位置的值作为最后一个参数传入(因此,如果在内容的结尾)。这种方法将重置类anchor
的{{1}}和caretPosition
字段的值,从而覆盖先前的值(示例中为5)。