MaskedDateField
MaskedDateField是一个文本输入框,允许用户输入数字格式的日期,并在字段失去焦点时根据定义的掩码自动格式化输入。掩码指定了预期的日期格式,以指导输入和显示。该组件支持灵活的解析、验证、地区本地化和数值还原,以实现一致的、区域特定的日期处理。
MaskedDateField仅专注于日期值。如果您需要一个类似的组件来输入和格式化时间,请查看MaskedTimeField。
MaskedDateField可以在有或没有参数的情况下实例化。您可以定义初始值、标签、占位符,以及用于值变化的事件监听器。
显示代码
- MaskedDateFieldView.java
掩码规则
MaskedDateField支持世界各地使用的多种日期格式,这些格式因日、月、年的顺序而异。常见的模式包括:
- 日/月/年(大多数欧洲国家使用)
- 月/日/年(美国使用)
- 年/月/日(中国、日本和韩国使用;也是ISO标准:
YYYY-MM-DD)
在这些格式中,本地变体包括分隔符的选择(例如,-、/或.)、年份是两位数还是四位数,以及单个数字月份或日期是否用前导零填充。
为处理这种多样性,MaskedDateField使用格式指示符,每个指示符以%开头,后跟一个表示日期特定部分的字母。这些指示符定义了如何解析输入以及如何显示日期。
要在字段外使用相同的掩码语法格式化或解析日期,请使用MaskDecorator工具类。
日期格式指示符
| 格式 | 描述 |
|---|---|
%Y | 年 |
%M | 月 |
%D | 日 |
修饰符
修饰符允许更细致地控制日期组成部分的格式:
| 修饰符 | 描述 |
|---|---|
z | 零填充 |
s | 短文本表示 |
l | 长文本表示 |
p | 紧凑数字 |
d | 十进制(默认格式) |
这些可以组合以构建多种日期掩码。
日期格式本地化
MaskedDateField通过设置适当的地区来适应区域日期格式。这确保日期以符合用户预期的方式显示和解析。
| 区域 | 格式 | 示例 |
|---|---|---|
| 美国 | MM/DD/YYYY | 07/04/2023 |
| 欧洲 | DD/MM/YYYY | 04/07/2023 |
| ISO标准 | YYYY-MM-DD | 2023-07-04 |
要应用本地化,请使用setLocale()方法。它接受java.util.Locale,并自动调整格式和解析:
dateField.setLocale(Locale.FRANCE);
解析逻辑
MaskedDateField根据定义的日期掩码解析用户输入。它接受带有或不带有分隔符的完整和简写数字输入,允许灵活输入,同时确保有效日期。
解析行为取决于掩码定义的格式顺序(例如,%Mz/%Dz/%Yz表示月/日/年)。该格式决定了如何解释数字序列。
例如,假设今天是2012年9月15日,以下是各种输入的解释方式:
示例解析场景
| 输入 | YMD(ISO) | MDY(美国) | DMY(欧洲) |
|---|---|---|---|
1 | 单个数字始终被解释为当前月份的日期编号,因此这将是2012年9月1日。 | 同YMD | 同YMD |
12 | 两个数字始终被解释为当前月份的日期编号,因此这将是2012年9月12日。 | 同YMD | 同YMD |
112 | 三个数字被解释为1位数字的月份编号后跟2位数字的日期编号,因此这将是2012年1月12日。 | 同YMD | 三个数字被解释为1位数字的日期编号后跟2位数字的月份编号,因此这将是2012年12月1日。 |
1004 | 四个数字被解释为MMDD,因此这将是2012年10月4日。 | 同YMD | 四个数字被解释为DDMM,因此这将是2012年4月10日。 |
020304 | 六个数字被解释为YYMMDD,因此这将是2002年3月4日。 | 六个数字被解释为MMDDYY,因此这将是2004年2月3日。 | 六个数字被解释为DDMMYY,因此这将是2004年3月2日。 |
8 digits | 八个数字被解释为YYYYMMDD。例如,20040612是2004年6月12日。 | 八个数字被解释为MMDDYYYY。例如,06122004是2004年6月12日。 | 八个数字被解释为DDMMYYYY。例如,06122004是2004年12月6日。 |
12/6 | 用任何有效分隔符分隔的两个数字被解释为MM/DD,因此这将是2012年12月6日。 注意:除字母和数字之外的所有字符均被视为有效分隔符。 | 同YMD | 用任何分隔符分隔的两个数字被解释为DD/MM,因此这将是2012年6月12日。 |
3/4/5 | 2012年4月5日 | 2005年3月4日 | 2005年4月3日 |
文本日期解析 25.11
默认情况下,MaskedDateField仅接受数字输入日期。然而,您可以启用文本日期解析以允许用户在输入中输入月份和日期名称。此功能在创建更自然的日期输入时特别有用。
要启用文本解析,请使用setTextualDateParsing()方法:
dateField.setTextualDateParsing(true);
月份名称替代
启用文本解析后,您可以在掩码中使用特殊修饰符以接受月份名称而不是数字值:
%Ms- 接受短月份名称(Jan, Feb, Mar等)%Ml- 接受长月份名称(January, February, March等)
月份名称可以出现在掩码中的任何位置,字段仍然会接受数字输入作为后备。
示例
| 掩码 | 输入 | 结果 |
|---|---|---|
%Ms/%Dz/%Yz | Sep/01/25 | 有效 - 解析为2025年9月1日 |
%Ml/%Dz/%Yz | September/01/25 | 有效 - 解析为2025年9月1日 |
%Dz/%Ml/%Yz | 01/September/25 | 有效 - 解析为2025年9月1日 |
%Mz/%Dz/%Yz | 09/01/25 | 有效 - 数字后备仍然有效 |
所有12个月都支持,包括短形式(Jan, Feb, Mar, Apr, May, Jun, Jul, Aug, Sep, Oct, Nov, Dec)和长形式(January, February等)。
日期名称装饰
输入中可以包含星期几的名称以提高可读性,但它们是装饰性的,在解析过程中会被去掉。它们不影响实际的日期值。
%Ds- 接受短星期名称(Mon, Tue, Wed等)%Dl- 接受长星期名称(Monday, Tuesday, Wednesday等)
使用星期几名称(%Ds或%Dl)时,您的掩码必须还包括%Dz或%Dd以指定实际的日期编号。如果没有数字日期成分,输入将无效。
示例
| 掩码 | 输入 | 结果 |
|---|---|---|
%Ds %Mz/%Dz/%Yz | Mon 09/01/25 | 有效 - 星期名称是装饰性的 |
%Dl %Mz/%Dz/%Yz | Monday 09/01/25 | 有效 - 星期名称是装饰性的 |
%Mz/%Dz/%Yz %Ds | 09/01/25 Tue | 有效 - 星期名称在末尾 |
%Dl/%Mz/%Yz | Monday/09/25 | 无效 - 缺少%Dz |
%Mz/%Dl/%Yz | 09/Monday/25 | 无效 - 缺少%Dz |
所有7个星期天都支持,包括短形式(Mon, Tue, Wed, Thu, Fri, Sat, Sun)和长形式(Monday, Tuesday等)。