我正在尝试使用Javafx上的Android手机上的Contacts应用程序编写类似的程序。在FXML文件中,我有一个包含三个Textfields的Vbox,前两个字段用于名字和姓氏,第三个字段是一个数字。
现在,我希望程序要做的是,当数字的文本字段填充到一个字符时,将自动添加到vbox中的另一个textfield。(对于另一个数字(。
我希望下一个领域发生同样的事情。以及随后的任何其他字段,因此具有递归形式。
现在,我知道可以实现这一目标的唯一方法是使用侦听器,但是我不知道如何创建这样的递归听众。而且,一旦完成工作,就必须删除对旧字段的听众,因此在旧字段中键入某些内容时,它不会不断创建新字段。但是当您在内部时无法删除听众。
有没有办法做到这一点?
lambda表达式无法提及自己,但是匿名的内部类可以,因此,如果您将侦听器实现为匿名的内部类,则可以实现您想要做的事情:
import javafx.application.Application;
import javafx.beans.value.ChangeListener;
import javafx.beans.value.ObservableValue;
import javafx.scene.Scene;
import javafx.scene.control.ScrollPane;
import javafx.scene.control.TextField;
import javafx.scene.layout.VBox;
import javafx.stage.Stage;
public class DynamicTextFields extends Application {
private TextField lastTextField ;
@Override
public void start(Stage primaryStage) {
lastTextField = new TextField();
VBox vbox = new VBox(5, lastTextField);
ChangeListener<String> textFieldListener = new ChangeListener<String>() {
@Override
public void changed(ObservableValue<? extends String> obs, String oldValue, String newValue) {
lastTextField.textProperty().removeListener(this);
lastTextField = new TextField();
lastTextField.textProperty().addListener(this);
vbox.getChildren().add(lastTextField);
}
};
lastTextField.textProperty().addListener(textFieldListener);
Scene scene = new Scene(new ScrollPane(vbox), 400, 400);
primaryStage.setScene(scene);
primaryStage.show();
}
public static void main(String[] args) {
launch(args);
}
}
每当文本从空白变为非空置或相反的方向时,添加/删除 TextField
的 TextField
s的 text
属性将 ChangeListener
注册。<<<<<<。/p>
public void addTextField(Pane parent) {
TextField textField = new TextField();
textField.textProperty().addListener((o, oldValue, newValue) -> {
boolean wasEmpty = oldValue.isEmpty();
boolean isEmpty = newValue.isEmpty();
if (wasEmpty != isEmpty) {
if (wasEmpty) {
// append textfield if last becomes non-empty
if (parent.getChildren().get(parent.getChildren().size() - 1) == textField) {
addTextField(parent);
}
} else {
int tfIndex = parent.getChildren().indexOf(textField);
if (tfIndex < parent.getChildren().size() - 1) {
// remove textfield if this is not the last one
parent.getChildren().remove(tfIndex);
parent.getChildren().get(tfIndex).requestFocus();
}
}
}
});
parent.getChildren().add(textField);
}
VBox root = new VBox();
addTextField(root);