使 TextField 只接受字母字符

Make TextField only accept alphabetic characters

我有这段代码应该删除任何非字符值并将其替换为空白 space(它删除非字符值)

public void firstNameOnlyText() {
    txtFirstName.textProperty().addListener(new ChangeListener<String>() {
        public void changed(ObservableValue<? extends String> observable, String oldValue, String newValue) {

            if (!newValue.matches("\D*")) {
                    txtFirstName.setText(newValue.replaceAll("[^\D]", ""));
                }
            }
    });
}

该代码非常适合删除数字,但我不知道要使用什么正则表达式,所以它也替换了标点符号(例如 `、!、]、[ 等)

有人可以帮助我吗?

首先,不要为此功能使用侦听器。这里的问题是,如果您在文本字段的文本 属性 上有另一个侦听器,该侦听器将在恢复到有效状态之前看到无效状态(使用非字符输入)。文本字段上任何类型的过滤器的目的应该是确保只看到有效状态。您应该改用 TextFormatter

Regex 规则在 Pattern documentation 中描述。如果你想允许任何大写或小写字母字符,你可以使用 "[a-zA-Z]";如果你想明确匹配 Character.isLowerCase()Character.isUpperCase() 的规则,你可以使用

"[\p{javaLowerCase}\p{javaUpperCase}]".

这是一个例子:

Pattern pattern = Pattern.compile("[a-zA-Z]*");
UnaryOperator<TextFormatter.Change> filter = c -> {
    if (pattern.matcher(c.getControlNewText()).matches()) {
        return c ;
    } else {
        return null ;
    }
};
TextFormatter<String> formatter = new TextFormatter<>(filter);
txtFirstName.setTextFormatter(formatter);

您可以使用取反的正则表达式集 ^ 只保留 A 到 Z(不区分大小写)。如果过滤后的字符串不同,则设置文本框的值。

final String filtered = newValue.replaceAll("[^a-zA-Z]", "");
if (!newValue.equals(filtered)) {
    // set 
}