本文目录导读:

JFormattedTextField 是 Swing 中用于格式化输入的文本组件,它的格式化行为是由 JFormattedTextField.AbstractFormatter(通常简称为 Formatter)控制的。
Swing 提供了几个内置的 Formatter 实现,分别对应不同的格式化需求。
以下是主要的 JFormattedTextField Formatter 格式器 及其详解:
DefaultFormatter
这是所有格式器的基类,它通过反向转换(将字符串转回对象)来验证输入,如果转换失败则拒绝输入。
- 适用场景:当你想使用自定义的
Format对象,或者需要控制通用的编辑行为时。 - 关键属性:
setOverwriteMode(boolean):是否覆盖模式(默认 true)。setAllowsInvalid(boolean):是否允许在编辑过程中暂时输入无效字符(建议设为 false 以严格校验)。setCommitsOnValidEdit(boolean):每次有效编辑后是否立即提交值。
DateFormatter
用于格式化日期和时间,它内部使用 java.text.DateFormat(如 SimpleDateFormat)。
-
构造方法:可以传入一个
DateFormat对象。 -
关键点:通常配合
SimpleDateFormat使用。 -
示例:
JFormattedTextField dateField = new JFormattedTextField( new DateFormatter(new SimpleDateFormat("yyyy-MM-dd")) ); // 设置初始值 dateField.setValue(new Date());
NumberFormatter
用于格式化数字(整数、浮点数、百分比等),它内部使用 java.text.NumberFormat。
-
构造方法:可以传入一个
NumberFormat对象。 -
关键点:
- 必须指定数字格式,否则默认会显示整数(可能带千分位)。
- 可以设置
setMinimum()和setMaximum()来限制输入范围。
-
示例:
// 格式化货币 NumberFormat currencyFormat = NumberFormat.getCurrencyInstance(); JFormattedTextField currencyField = new JFormattedTextField(new NumberFormatter(currencyFormat)); currencyField.setValue(99.99); // 格式化百分比 NumberFormat percentFormat = NumberFormat.getPercentInstance(); percentFormat.setMinimumFractionDigits(2); JFormattedTextField percentField = new JFormattedTextField(new NumberFormatter(percentFormat)); percentField.setValue(0.25); // 显示为 25.00% // 限制整数范围 NumberFormatter intFormatter = new NumberFormatter(NumberFormat.getIntegerInstance()); intFormatter.setMinimum(0); intFormatter.setMaximum(100); JFormattedTextField intField = new JFormattedTextField(intFormatter);
InternationalFormatter
是 DefaultFormatter 和 NumberFormatter 的父类,它提供了更高级的国际化支持和对 Format 对象的更精细控制,通常你直接使用 NumberFormatter 或 DateFormatter 即可,但在需要自定义 Format 时可以继承这个类。
MaskFormatter
不同于上述基于 Format 的格式器,MaskFormatter 基于一个固定的掩码模板,它非常适合格式化固定格式的字符串,如电话号码、邮政编码、社保号等。
-
掩码字符:
- 任何有效数字(0-9)。
- 转义字符(用于插入固定字符)。
U:任何字符(小写 -> 大写)。L:任何字符(大写 -> 小写)。A:任何字母或数字。- 任何字母。
- 任何字符。
H:任何十六进制字符(0-9, a-f, A-F)。
-
示例:
try { MaskFormatter phoneFormatter = new MaskFormatter("(###) ###-####"); phoneFormatter.setPlaceholderCharacter('_'); // 占位符 JFormattedTextField phoneField = new JFormattedTextField(phoneFormatter); phoneField.setValue(""); // 初始显示为 (___) ___-____ } catch (ParseException e) { e.printStackTrace(); }
总结与选择指南
| 格式器 | 适用场景 | 核心原理 | 示例 |
|---|---|---|---|
| DefaultFormatter | 通用文本、自定义 Format 对象 |
调用 Format.parseObject() 和 Format.format() |
自定义的任何格式 |
| DateFormatter | 日期、时间输入 | 内部用 DateFormat |
2023-10-01, 01/10/2023 |
| NumberFormatter | 整数、浮点数、货币、百分比 | 内部用 NumberFormat |
1,234.56, $99.99, 25.00% |
| InternationalFormatter | 高级国际化需求(很少直接使用) | 是 NumberFormatter 的父类 | - |
| MaskFormatter | 固定格式的字符串(如电话、邮编) | 基于字符掩码模板 | (123) 456-7890 |
关键操作技巧
-
设置和获取值:
- 使用
setValue(Object)设置初始值(注意对象类型需匹配,如Date,Number,String)。 - 使用
getValue()获取格式化后的对象(返回类型取决于 Formatter)。 - 使用
getText()获取当前显示的字符串。
- 使用
-
提交行为:
- 默认情况下,当文本框失去焦点或按 Enter 键时,输入会被提交(并转换为对应的对象)。
- 如果输入无法被解析,控件通常会保持红色边框并拒绝提交,且
getValue()返回上一次有效值。
-
创建自定义 Formatter:
- 如果需要非常特殊的格式(如身份证号、车牌号),可以继承
DefaultFormatter并重写stringToValue()和valueToString()方法。
- 如果需要非常特殊的格式(如身份证号、车牌号),可以继承
// 自定义格式化器示例:只允许输入大写字母
JFormattedTextField.AbstractFormatter upperCaseFormatter = new JFormattedTextField.AbstractFormatter() {
@Override
public Object stringToValue(String text) throws ParseException {
// 可以在这里做转换或校验,简单起见直接返回大写字符串
if (text == null) return null;
return text.toUpperCase();
}
@Override
public String valueToString(Object value) throws ParseException {
if (value == null) return "";
return value.toString().toUpperCase();
}
};
JFormattedTextField field = new JFormattedTextField(upperCaseFormatter);
field.setValue("hello"); // 显示为 "HELLO"
合理使用这些格式器可以大幅提升 Swing 应用的输入准确性和用户体验。