Handsontable 时间单元格类型(Time Cell Type)完整指南:基于 Intl.DateTimeFormat 的时间格式化、校验与编辑
发布时间:2026/9/21 17:15:28 作者:尧图编辑部 阅读量:1,286
完整指南:基于 Intl.DateTimeFormat 的时间格式化、校验与编辑)
Handsontable 时间单元格类型Time Cell Type完整指南基于 Intl.DateTimeFormat 的时间格式化、校验与编辑【免费下载链接】handsontableJavaScript Data Grid / Data Table with a Spreadsheet Look Feel. Works with React, Angular, and Vue. Supported by the Handsontable team ⚡项目地址: https://gitcode.com/gh_mirrors/ha/handsontable本指南围绕 Handsontable 官方文档 time-cell-type.md 展开结合仓库内handsontable/src/cellTypes/下intlTimeType、timeType的源码实现与示例代码系统讲解如何用intl-time/time单元格类型展示、格式化、校验、编辑、排序与过滤时间值。Handsontable 的intl-time与time单元格类型cell type用于把单元格值当作时间来处理通过可配置的格式字符串控制显示样式并校验用户输入。它基于浏览器原生的Intl.DateTimeFormatAPI适用于排班scheduling、日志logging或任何基于时间的数据场景。阅读本文后你将掌握在整表、单列或单单元格上配置时间单元格类型使用timeFormat对象定制显示格式与 locale理解源码层的数据格式约束与校验逻辑以及时间值在排序、过滤与编辑中的行为。概览Overview时间单元格类型让你将单元格值视作时间格式化其显示方式并校验输入。使用intl-time或time单元格类型配合原生Intl.DateTimeFormatAPI 与 24 小时制时间字符串。从源码结构看这两种类型在handsontable/src/cellTypes/目录中各自独立实现handsontable/src/cellTypes/intlTimeType/intlTimeType.ts定义CELL_TYPE intl-time组合了IntlTimeEditor、intlTimeRenderer、intlTimeValidator、sourceDataValidator与valueFormatterhandsontable/src/cellTypes/timeType/timeType.ts定义CELL_TYPE: time time组合了TimeEditor、timeRenderer、timeValidator等。两者均挂载在handsontable/src/cellTypes/registry.ts的单元格类型注册表中可通过type: intl-time或type: time直接使用。时间单元格类型演示在官方演示见docs/content/guides/cell-types/time-cell-type/javascript/example1.js中Start、Break start与End三列使用时间单元格类型并配以不同格式短样式timeStyle: short、自定义时:分:秒格式hour/minute/second以及带日周期dayPeriod的格式。演示还提供了 locale 选择器切换后会调用hot.updateSettings({ locale: ... })实时重渲染观察同一timeFormat在不同 locale 下的显示差异。示例数据采用 24 小时制字符串例如const data [ { shift: Morning, start: 09:00, breakStart: 12:00, end: 17:00 }, { shift: Afternoon, start: 13:30, breakStart: 16:00, end: 21:00 }, { shift: Night, start: 22:00, breakStart: 01:00, end: 06:00 }, { shift: Split, start: 08:00, breakStart: 12:30, end: 20:00 }, { shift: Short day, start: 10:00, breakStart: 13:00, end: 15:00 }, ];对应的列配置为columns: [ { type: text, data: shift }, { type: intl-time, data: start, timeFormat: { timeStyle: short } }, { type: intl-time, data: breakStart, timeFormat: { hour: 2-digit, minute: 2-digit, second: 2-digit } }, { type: intl-time, data: end, timeFormat: { hour: numeric, hourCycle: h12, dayPeriod: short } }, ], columnSorting: true, filters: true, dropdownMenu: true,该演示同时启用了columnSorting、filters与dropdownMenu直接验证了时间列上的排序与过滤能力。演示完整 HTML 骨架见 example1.htmlReact、Angular、Vue 版本分别位于 example1.jsx、example1.tsx、example1.ts、example1.html 与 example1.vue。使用时间单元格类型使用对象式object-style配置将type选项设为intl-time或time并把timeFormat设为对象。locale 通过locale选项单独控制。为整个表格设置// set the time cell type for the entire grid type: intl-time, locale: en-US, timeFormat: { hour: numeric, minute: 2-digit, second: 2-digit, hour12: true },为单个列设置columns: [ { type: intl-time, locale: en-US, timeFormat: { timeStyle: medium } } ],为单个单元格设置cell: [ { row: 0, col: 2, type: intl-time, locale: en-US, timeFormat: { hour: 2-digit, minute: 2-digit, hour12: true } } ],说明timeFormat的默认值见handsontable/src/renderers/timeRenderer/timeRenderer.ts中的DEFAULT_INTL_FORMAT{ hour: numeric, minute: 2-digit }。即不显式配置时默认显示时:分。对于intl-time与time单元格源数据必须是 24 小时制时间格式HH:mm、HH:mm:ss或HH:mm:ss.SSS时间才能正常工作。timeFormat对象只影响显示排序与过滤依赖底层值。格式化时间要控制时间在单元格渲染器中的显示方式使用timeFormat选项。自 Handsontable 18.0 起timeFormat的对象形式与intl-time、time单元格类型为必选项。它使用原生Intl.DateTimeFormatAPIlocale 通过locale选项单独控制。使用 Intl.DateTimeFormattimeFormat接受Intl.DateTimeFormatoptions 中与时间相关的属性搭配type: intl-time或type: time使用columns: [ { type: intl-time, locale: en-US, timeFormat: { hour: numeric, minute: 2-digit, second: 2-digit, hour12: true } }, { type: intl-time, locale: de-DE, timeFormat: { timeStyle: medium } } ]注意从源码看若把timeFormat传成字符串valueFormatter会在控制台输出警告The timeFormat option as a string is not supported. Use an Intl.DateTimeFormatOptions object instead.并回退到默认格式——因此请始终使用对象形式。时间专属选项样式快捷方式属性可选值说明timeStylefull、long、medium、short时间格式样式时、分、秒、timeZoneName时间分量选项属性可选值说明hournumeric、2-digit小时表示minutenumeric、2-digit分钟表示secondnumeric、2-digit秒表示fractionalSecondDigits1、2、3秒的小数位dayPeriodnarrow、short、long日周期如 amtimeZoneNamelong、short、shortOffset、longOffset、shortGeneric、longGeneric时区显示Locale 与其他选项属性可选值说明localeMatcherbest fit默认、lookupLocale 匹配算法timeZoneIANA 时区如UTC、America/New_York格式化使用的时区hour12true、false12 小时制 vs 24 小时制hourCycleh11、h12、h23、h24小时周期formatMatcherbasic、best fit默认格式匹配算法完整参考见timeFormatAPI 文档 或 MDN: Intl.DateTimeFormat。编辑器行为timeFormat控制时间在单元格中的显示。编辑器可能会以规范化形式显示值对于intl-time与time底层值始终保持 24 小时制HH:mm、HH:mm:ss或HH:mm:ss.SSS。从源码看TimeEditor继承自TextEditor但把输入元素创建为原生typetime的 input并强制dirltr打开编辑器时会调用原生showPicker()弹出系统时间选择器若传入的值不满足 24 小时制格式会输出警告并清空输入。IntlTimeEditor见handsontable/src/editors/intlTimeEditor/intlTimeEditor.ts则直接继承TimeEditor仅替换类型标识。结果Result配置完成后单元格按你的timeFormat配置显示格式化后的时间值。点击intl-time或time单元格会打开原生时间选择器。无论显示格式如何源数据始终以 24 小时制HH:mm、HH:mm:ss或HH:mm:ss.SSS存储。键盘快捷键intl-time与time单元格编辑器打开浏览器原生时间选择器。选择器内部的键盘导航来自浏览器因此在不同浏览器与操作系统间有所差异。选择器之外标准编辑键盘快捷键适用。深入原理底层的数据格式与校验理解源码能帮你避免显示正常但数据异常的坑时间正则与解析handsontable/src/helpers/dateTime.ts中定义了 24 小时制时间正则export const TIME_REGEX /^([01]\d|2[0-3]):([0-5]\d)(?::([0-5]\d)(?:\.(\d{1,3}))?)?$/;isValidTime(value)判断字符串是否匹配上述HH:mm、HH:mm:ss或HH:mm:ss.SSS模式parseToLocalTime(value)把 24 小时制时间字符串解析为本地时区的Date基准日期为1970-01-01再交给Intl.DateTimeFormat做显示格式化。这也解释了为什么timeFormat中的timeZone选项会影响显示格式化发生在解析出的本地Date之上。校验器与源数据校验handsontable/src/validators/timeValidator/timeValidator.ts中timeValidator单元格编辑时的校验器allowEmpty时允许空值否则用isValidTime校验sourceDataValidator批量加载/写入源数据时逐格校验同样基于isValidTime当单元格元数据allowEmpty为空值时放行以开头的字符串视为公式表达式由 Formulas 插件处理而跳过校验并标记rowIndependent true以允许源数据校验复用列级 meta 对象提升性能SOURCE_DATA_WARNING_MESSAGE源数据中出现不合法时间值时输出的警告文案明确指出期望HH:mm、HH:mm:ss或HH:mm:ss.SSS格式。intlTimeValidator直接委托timeValidator仅替换类型标识。因此两种单元格类型在编辑校验与源数据校验上行为一致。排序与过滤依赖底层值由于排序与过滤基于单元格底层值24 小时制字符串而非渲染后的显示文本相同时间在不同 locale/格式下仍能正确排序、过滤——这正是指南开头强调源数据必须 24 小时制的原因。演示中columnSorting: true与filters: true即为该能力的直接验证。相关文章相关指南单元格类型Cell type配置选项timeFormatlocaletypevalueFormattervalueParservalueSettervalueGetter核心方法getCellMeta()getCellMetaAtRow()getCellsMeta()getDataType()setCellMeta()setCellMetaObject()removeCellMeta()钩子HooksafterGetCellMetaafterSetCellMetabeforeGetCellMetabeforeSetCellMeta【免费下载链接】handsontableJavaScript Data Grid / Data Table with a Spreadsheet Look Feel. Works with React, Angular, and Vue. Supported by the Handsontable team ⚡项目地址: https://gitcode.com/gh_mirrors/ha/handsontable创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考