@comitor/ui 3.0.1 → 3.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (76) hide show
  1. package/dist/components/composite/confirm-dialog.js +56 -35
  2. package/dist/components/composite/confirm-dialog.js.map +1 -1
  3. package/dist/components/composite/search-filter-bar-constants.d.ts +3 -0
  4. package/dist/components/composite/search-filter-bar-constants.js.map +1 -1
  5. package/dist/components/composite/table-pagination-constants.d.ts +3 -1
  6. package/dist/components/composite/table-pagination-constants.js.map +1 -1
  7. package/dist/components/composite/table-pagination.js +10 -2
  8. package/dist/components/composite/table-pagination.js.map +1 -1
  9. package/dist/components/composite/text-utils.d.ts +4 -23
  10. package/dist/components/composite/text-utils.js +1 -11
  11. package/dist/components/composite/text-utils.js.map +1 -1
  12. package/dist/components/ui/banner.d.ts +8 -0
  13. package/dist/components/ui/banner.js +149 -35
  14. package/dist/components/ui/banner.js.map +1 -1
  15. package/dist/components/ui/mask-input-constants.d.ts +34 -2
  16. package/dist/components/ui/mask-input-constants.js +56 -5
  17. package/dist/components/ui/mask-input-constants.js.map +1 -1
  18. package/dist/components/ui/mask-input.d.ts +6 -5
  19. package/dist/components/ui/mask-input.js +5 -1
  20. package/dist/components/ui/mask-input.js.map +1 -1
  21. package/dist/components/ui/mention.d.ts +14 -2
  22. package/dist/components/ui/mention.js +33 -6
  23. package/dist/components/ui/mention.js.map +1 -1
  24. package/dist/components/ui/phone-input.d.ts +18 -8
  25. package/dist/components/ui/phone-input.js +120 -33
  26. package/dist/components/ui/phone-input.js.map +1 -1
  27. package/dist/components/ui/scroll-spy.js +46 -31
  28. package/dist/components/ui/scroll-spy.js.map +1 -1
  29. package/dist/components/ui/stepper.js +26 -3
  30. package/dist/components/ui/stepper.js.map +1 -1
  31. package/dist/components/ui/time-picker.d.ts +24 -4
  32. package/dist/components/ui/time-picker.js +425 -162
  33. package/dist/components/ui/time-picker.js.map +1 -1
  34. package/dist/components/ui/timeline.js +45 -9
  35. package/dist/components/ui/timeline.js.map +1 -1
  36. package/dist/data-grid/data-grid-cell-variants.js +4 -4
  37. package/dist/data-grid/data-grid-cell-variants.js.map +1 -1
  38. package/dist/data-grid/data-grid-cell-wrapper.d.ts +1 -1
  39. package/dist/data-grid/data-grid-cell-wrapper.js +6 -0
  40. package/dist/data-grid/data-grid-cell-wrapper.js.map +1 -1
  41. package/dist/data-grid/data-grid-row.js +1 -1
  42. package/dist/data-grid/data-grid-row.js.map +1 -1
  43. package/dist/data-grid/data-grid-select-column.js +6 -2
  44. package/dist/data-grid/data-grid-select-column.js.map +1 -1
  45. package/dist/data-grid/data-grid-skeleton.d.ts +5 -0
  46. package/dist/data-grid/data-grid-skeleton.js +1 -4
  47. package/dist/data-grid/data-grid-skeleton.js.map +1 -1
  48. package/dist/data-grid/data-grid.d.ts +1 -1
  49. package/dist/data-grid/data-grid.js +3 -2
  50. package/dist/data-grid/data-grid.js.map +1 -1
  51. package/dist/data-grid/filters.js +3 -2
  52. package/dist/data-grid/filters.js.map +1 -1
  53. package/dist/data-grid/types.d.ts +7 -0
  54. package/dist/data-grid/use-data-grid.d.ts +3 -2
  55. package/dist/data-grid/use-data-grid.js +70 -24
  56. package/dist/data-grid/use-data-grid.js.map +1 -1
  57. package/dist/data-grid/utils.d.ts +7 -0
  58. package/dist/data-grid/utils.js +3 -1
  59. package/dist/data-grid/utils.js.map +1 -1
  60. package/dist/i18n/namespaces/search-filter-bar.js +8 -6
  61. package/dist/i18n/namespaces/search-filter-bar.js.map +1 -1
  62. package/dist/i18n/namespaces/table-pagination.js +6 -4
  63. package/dist/i18n/namespaces/table-pagination.js.map +1 -1
  64. package/dist/index.d.ts +2 -1
  65. package/dist/lib/collect-item-elements.d.ts +47 -0
  66. package/dist/lib/collect-item-elements.js +22 -0
  67. package/dist/lib/collect-item-elements.js.map +1 -0
  68. package/dist/lib/text-search.d.ts +32 -0
  69. package/dist/lib/text-search.js +17 -0
  70. package/dist/lib/text-search.js.map +1 -0
  71. package/dist/shell/app-shell.d.ts +1 -0
  72. package/dist/shell/display-axis-provider.d.ts +1 -1
  73. package/dist/shell/index.d.ts +2 -1
  74. package/dist/shell/shell-context.d.ts +1 -0
  75. package/dist/shell/utils.d.ts +2 -1
  76. package/package.json +1 -1
@@ -1 +1 @@
1
- {"version":3,"sources":["../../../src/components/ui/time-picker.tsx"],"sourcesContent":["\"use client\";\n\n/*\n * Port từ Dice UI (https://diceui.com/docs/components/time-picker) — MIT, © 2024 Sadman Sakib.\n * Giữ nguyên cấu trúc thượng nguồn để còn đối chiếu ngược được; mọi chỗ đổi đều có chú thích.\n */\n\nimport { Slot } from \"@radix-ui/react-slot\";\nimport { Clock } from \"lucide-react\";\nimport * as React from \"react\";\nimport { useComitorLabels, useComitorLocale } from \"../../i18n/locale-provider.js\";\nimport { cn } from \"../../lib/cn.js\";\nimport { useComposedRefs } from \"../../lib/compose-refs.js\";\nimport { useAsRef } from \"../../lib/use-as-ref.js\";\nimport { useIsomorphicLayoutEffect } from \"../../lib/use-isomorphic-layout-effect.js\";\nimport { useLazyRef } from \"../../lib/use-lazy-ref.js\";\nimport { VisuallyHiddenInput } from \"../../lib/visually-hidden-input.js\";\nimport { Popover, PopoverAnchor, PopoverContent, PopoverTrigger } from \"./popover.js\";\nimport type { TimePickerLabels } from \"./time-picker-constants.js\";\n\nconst ROOT_NAME = \"TimePicker\";\nconst LABEL_NAME = \"TimePickerLabel\";\nconst INPUT_GROUP_NAME = \"TimePickerInputGroup\";\nconst INPUT_NAME = \"TimePickerInput\";\nconst TRIGGER_NAME = \"TimePickerTrigger\";\nconst CONTENT_NAME = \"TimePickerContent\";\nconst COLUMN_NAME = \"TimePickerColumn\";\nconst COLUMN_ITEM_NAME = \"TimePickerColumnItem\";\nconst HOUR_NAME = \"TimePickerHour\";\nconst MINUTE_NAME = \"TimePickerMinute\";\nconst SECOND_NAME = \"TimePickerSecond\";\nconst PERIOD_NAME = \"TimePickerPeriod\";\nconst CLEAR_NAME = \"TimePickerClear\";\n\nconst DEFAULT_STEP = 1;\nconst DEFAULT_SEGMENT_PLACEHOLDER = \"--\";\nconst SEGMENTS: Segment[] = [\"hour\", \"minute\", \"second\", \"period\"];\nconst PERIODS = [\"AM\", \"PM\"] as const;\n\ntype Segment = \"hour\" | \"minute\" | \"second\" | \"period\";\ntype SegmentFormat = \"numeric\" | \"2-digit\";\ntype Period = (typeof PERIODS)[number];\n\ninterface DivProps extends React.ComponentProps<\"div\"> {\n asChild?: boolean;\n}\n\ninterface ButtonProps extends React.ComponentProps<\"button\"> {\n asChild?: boolean;\n}\n\ntype PopoverContentProps = React.ComponentProps<typeof PopoverContent>;\n\ntype InputGroupElement = React.ComponentRef<typeof TimePickerInputGroup>;\ntype InputElement = React.ComponentRef<typeof TimePickerInput>;\ntype TriggerElement = React.ComponentRef<typeof TimePickerTrigger>;\ntype ColumnElement = React.ComponentRef<typeof TimePickerColumn>;\ntype ColumnItemElement = React.ComponentRef<typeof TimePickerColumnItem>;\n\ninterface TimeValue {\n hour?: number;\n minute?: number;\n second?: number;\n period?: Period;\n}\n\ninterface ItemData {\n value: number | string;\n ref: React.RefObject<ColumnItemElement | null>;\n selected: boolean;\n}\n\ninterface ColumnData {\n id: string;\n ref: React.RefObject<ColumnElement | null>;\n getSelectedItemRef: () => React.RefObject<ColumnItemElement | null> | null;\n getItems: () => ItemData[];\n}\n\nfunction focusFirst(candidates: React.RefObject<ColumnItemElement | null>[], preventScroll = false) {\n const PREVIOUSLY_FOCUSED_ELEMENT = document.activeElement;\n for (const candidateRef of candidates) {\n const candidate = candidateRef.current;\n if (!candidate) continue;\n if (candidate === PREVIOUSLY_FOCUSED_ELEMENT) return;\n candidate.focus({ preventScroll });\n if (document.activeElement !== PREVIOUSLY_FOCUSED_ELEMENT) return;\n }\n}\n\nfunction sortNodes<T extends { ref: React.RefObject<Element | null> }>(items: T[]): T[] {\n return items.sort((a, b) => {\n const elementA = a.ref.current;\n const elementB = b.ref.current;\n if (!elementA || !elementB) return 0;\n const position = elementA.compareDocumentPosition(elementB);\n if (position & Node.DOCUMENT_POSITION_FOLLOWING) {\n return -1;\n }\n if (position & Node.DOCUMENT_POSITION_PRECEDING) {\n return 1;\n }\n return 0;\n });\n}\n\nfunction getIs12Hour(locale?: string): boolean {\n const testDate = new Date(2000, 0, 1, 13, 0, 0);\n const formatted = new Intl.DateTimeFormat(locale, {\n hour: \"numeric\"\n }).format(testDate);\n\n return /am|pm/i.test(formatted) || !formatted.includes(\"13\");\n}\n\nfunction parseTimeString(timeString: string | undefined): TimeValue | null {\n if (!timeString) return null;\n\n const parts = timeString.split(\":\");\n if (parts.length < 2) return null;\n\n const result: TimeValue = {};\n\n if (parts[0] && parts[0] !== DEFAULT_SEGMENT_PLACEHOLDER) {\n const hour = Number.parseInt(parts[0], 10);\n if (!Number.isNaN(hour) && hour >= 0 && hour <= 23) {\n result.hour = hour;\n }\n }\n\n if (parts[1] && parts[1] !== DEFAULT_SEGMENT_PLACEHOLDER) {\n const minute = Number.parseInt(parts[1], 10);\n if (!Number.isNaN(minute) && minute >= 0 && minute <= 59) {\n result.minute = minute;\n }\n }\n\n if (parts[2] && parts[2] !== DEFAULT_SEGMENT_PLACEHOLDER) {\n const second = Number.parseInt(parts[2], 10);\n if (!Number.isNaN(second) && second >= 0 && second <= 59) {\n result.second = second;\n }\n }\n if (result.hour === undefined && result.minute === undefined && result.second === undefined) {\n return null;\n }\n\n return result;\n}\n\nfunction formatTimeValue(value: TimeValue, showSeconds: boolean): string {\n const hourStr = value.hour !== undefined ? value.hour.toString().padStart(2, \"0\") : DEFAULT_SEGMENT_PLACEHOLDER;\n const minuteStr = value.minute !== undefined ? value.minute.toString().padStart(2, \"0\") : DEFAULT_SEGMENT_PLACEHOLDER;\n const secondStr = value.second !== undefined ? value.second.toString().padStart(2, \"0\") : DEFAULT_SEGMENT_PLACEHOLDER;\n\n if (showSeconds) {\n return `${hourStr}:${minuteStr}:${secondStr}`;\n }\n return `${hourStr}:${minuteStr}`;\n}\n\nfunction to12Hour(hour24: number): { hour: number; period: Period } {\n const period: Period = hour24 >= 12 ? \"PM\" : \"AM\";\n const hour = hour24 % 12 || 12;\n return { hour, period };\n}\n\nfunction to24Hour(hour12: number, period: Period): number {\n if (hour12 === 12) {\n return period === \"PM\" ? 12 : 0;\n }\n return period === \"PM\" ? hour12 + 12 : hour12;\n}\n\nfunction clamp(value: number, min: number, max: number) {\n return Math.min(Math.max(value, min), max);\n}\n\n/*\n * ⚠ Khác thượng nguồn: bản gốc in thẳng mã buổi \"AM\"/\"PM\" ra ô và ra cột. Ở đây mã buổi vẫn là\n * thứ chạy trong state (`editValue`, `updateTimeValue`) — chỉ lúc VẼ mới đổi sang nhãn hiển thị\n * (`labels.am`/`labels.pm` — \"AM\"/\"PM\" ở tiếng Anh, \"SA\"/\"CH\" ở tiếng Việt), nên logic bàn phím\n * của thượng nguồn giữ nguyên.\n */\nfunction getPeriodLabel(value: string, labels: Pick<TimePickerLabels, \"am\" | \"pm\">): string {\n if (value === \"AM\") return labels.am;\n if (value === \"PM\") return labels.pm;\n return value;\n}\n\n/*\n * ⚠ Khác thượng nguồn: bản gốc chỉ nhận `A`/`1` → AM và `P`/`2` → PM (viết thẳng ở hai chỗ).\n * Nhãn tiếng Việt là \"SA\"/\"CH\" thì người dùng sẽ gõ `S`/`C`, nên ký tự đầu của nhãn cũng là phím\n * tắt. Phím của thượng nguồn được xét TRƯỚC và vẫn chạy.\n */\nfunction getPeriodFromKey(key: string, labels: Pick<TimePickerLabels, \"am\" | \"pm\">): Period | null {\n const lowerKey = key.toLowerCase();\n if (lowerKey === \"a\" || lowerKey === \"1\") return \"AM\";\n if (lowerKey === \"p\" || lowerKey === \"2\") return \"PM\";\n if (lowerKey.length !== 1) return null;\n if (lowerKey === labels.am.charAt(0).toLowerCase()) return \"AM\";\n if (lowerKey === labels.pm.charAt(0).toLowerCase()) return \"PM\";\n return null;\n}\n\ninterface StoreState {\n value: string;\n open: boolean;\n openedViaFocus: boolean;\n}\n\ninterface Store {\n subscribe: (callback: () => void) => () => void;\n getState: () => StoreState;\n setState: <K extends keyof StoreState>(key: K, value: StoreState[K]) => void;\n notify: () => void;\n}\n\nconst StoreContext = React.createContext<Store | null>(null);\n\nfunction useStoreContext(consumerName: string) {\n const context = React.useContext(StoreContext);\n if (!context) {\n throw new Error(`\\`${consumerName}\\` phải nằm bên trong \\`${ROOT_NAME}\\``);\n }\n return context;\n}\n\nfunction useStore<T>(selector: (state: StoreState) => T, ogStore?: Store | null): T {\n const contextStore = React.useContext(StoreContext);\n\n const store = ogStore ?? contextStore;\n\n if (!store) {\n throw new Error(`\\`useTimePicker\\` phải được gọi bên trong \\`${ROOT_NAME}\\``);\n }\n\n const getSnapshot = React.useCallback(() => selector(store.getState()), [store, selector]);\n\n return React.useSyncExternalStore(store.subscribe, getSnapshot, getSnapshot);\n}\n\ntype SegmentPlaceholder =\n | string\n | {\n hour?: string;\n minute?: string;\n second?: string;\n period?: string;\n };\n\ninterface TimePickerContextValue {\n id: string;\n inputGroupId: string;\n labelId: string;\n triggerId: string;\n inputGroupRef: React.RefObject<InputGroupElement | null>;\n triggerRef: React.RefObject<TriggerElement | null>;\n openOnFocus: boolean;\n inputGroupClickAction: \"focus\" | \"open\";\n onInputGroupChange: (inputGroup: InputGroupElement | null) => void;\n disabled: boolean;\n readOnly: boolean;\n required: boolean;\n invalid: boolean;\n showSeconds: boolean;\n is12Hour: boolean;\n minuteStep: number;\n secondStep: number;\n hourStep: number;\n segmentPlaceholder: {\n hour: string;\n minute: string;\n second: string;\n period: string;\n };\n labels: TimePickerLabels;\n min?: string;\n max?: string;\n}\n\nconst TimePickerContext = React.createContext<TimePickerContextValue | null>(null);\n\nfunction useTimePickerContext(consumerName: string) {\n const context = React.useContext(TimePickerContext);\n if (!context) {\n throw new Error(`\\`${consumerName}\\` phải nằm bên trong \\`${ROOT_NAME}\\``);\n }\n return context;\n}\n\ninterface TimePickerProps extends DivProps {\n /** Giá trị có kiểm soát, LUÔN ở dạng 24 giờ: `\"HH:mm\"` hoặc `\"HH:mm:ss\"` — bất kể đồng hồ hiển thị. */\n value?: string;\n /** Giá trị ban đầu (không kiểm soát), cùng định dạng với `value`. */\n defaultValue?: string;\n onValueChange?: (value: string) => void;\n open?: boolean;\n defaultOpen?: boolean;\n onOpenChange?: (open: boolean) => void;\n /** Mở bảng chọn ngay khi một ô được focus. Mặc định `false`. */\n openOnFocus?: boolean;\n /** Bấm vào khoảng trống của nhóm ô: `\"focus\"` (mặc định) focus ô đầu, `\"open\"` mở bảng chọn. */\n inputGroupClickAction?: \"focus\" | \"open\";\n /**\n * ⚠ Thượng nguồn nhận `min`/`max` và đưa vào context nhưng CHƯA áp dụng ở đâu cả — không chặn\n * gõ, không làm mờ mục trong cột. Giữ để khớp API gốc; muốn ràng buộc khung giờ (ca làm, giờ\n * hành chính) thì app phải tự kiểm ở `onValueChange` / tầng validate của form.\n */\n min?: string;\n /** Xem `min`. */\n max?: string;\n hourStep?: number;\n minuteStep?: number;\n secondStep?: number;\n /** Chữ giữ chỗ của ô trống — một chuỗi cho mọi ô, hoặc từng ô. Mặc định `\"--\"`. */\n segmentPlaceholder?: SegmentPlaceholder;\n /**\n * Locale BCP 47 quyết định đồng hồ 12 hay 24 giờ — CHỈ vậy, không dịch nhãn (nhãn theo\n * `ComitorLocaleProvider`, xem `labels`).\n *\n * Không truyền thì lấy `locale` của `ComitorLocaleProvider`: không có provider → `\"en\"` → 12 giờ\n * (\"AM\"/\"PM\"); `\"vi\"` → 24 giờ; `\"en-GB\"` → 24 giờ. Trước `3.0.0` mặc định cứng là `\"vi-VN\"`.\n *\n * ⚠ Khác thượng nguồn: bản gốc để `undefined`, tức theo locale của MÔI TRƯỜNG CHẠY — xem chú\n * thích ở chỗ đọc prop này trong `TimePicker`. Muốn theo trình duyệt: truyền `navigator.language`\n * — nhưng chỉ sau khi hydrate, vì server không biết giá trị đó.\n */\n locale?: string;\n /**\n * Chuỗi hiển thị và nhãn trình đọc màn hình (tên từng ô, nhãn buổi, tên nút mở, nút xoá). Không\n * truyền thì theo namespace `timePicker` của `ComitorLocaleProvider` (mặc định tiếng Anh). Thêm\n * so với thượng nguồn.\n */\n labels?: Partial<TimePickerLabels>;\n name?: string;\n disabled?: boolean;\n invalid?: boolean;\n readOnly?: boolean;\n required?: boolean;\n showSeconds?: boolean;\n}\n\nfunction TimePicker(props: TimePickerProps) {\n const {\n value: valueProp,\n defaultValue,\n onValueChange,\n open,\n defaultOpen,\n onOpenChange,\n openOnFocus = false,\n inputGroupClickAction = \"focus\",\n min,\n max,\n hourStep = DEFAULT_STEP,\n minuteStep = DEFAULT_STEP,\n secondStep = DEFAULT_STEP,\n segmentPlaceholder = DEFAULT_SEGMENT_PLACEHOLDER,\n locale: localeProp,\n labels: labelsProp,\n name,\n asChild,\n disabled = false,\n invalid = false,\n readOnly = false,\n required = false,\n showSeconds = false,\n className,\n children,\n id,\n ...rootProps\n } = props;\n\n /*\n * ⚠ Khác thượng nguồn: bản gốc để `locale` là `undefined`, tức đồng hồ 12/24 giờ suy từ locale\n * của MÔI TRƯỜNG CHẠY — máy chủ Node thường là `en-US` (12 giờ) còn trình duyệt người dùng Việt là\n * `vi` (24 giờ), nên cùng \"14:30\" server in \"02\" còn client in \"14\": lệch hydrate (cùng lý do\n * `Calendar` bỏ `\"default\"`). Ở đây mặc định là `locale` của `ComitorLocaleProvider` — cùng một\n * giá trị ở cả hai phía. `Intl.DateTimeFormat(\"vi\", { hour: \"numeric\" })` in \"13 giờ\" cho 13:00\n * → `getIs12Hour` trả `false`; `\"en\"` in \"1 PM\" → `true`. Trước `3.0.0` mặc định cứng là `\"vi-VN\"`.\n */\n const { locale: providerLocale } = useComitorLocale();\n const locale = localeProp ?? providerLocale;\n\n const instanceId = React.useId();\n const rootId = id ?? instanceId;\n const inputGroupId = React.useId();\n const labelId = React.useId();\n const triggerId = React.useId();\n\n const inputGroupRef = React.useRef<InputGroupElement>(null);\n const triggerRef = React.useRef<TriggerElement>(null);\n\n const [inputGroup, setInputGroup] = React.useState<InputGroupElement | null>(null);\n const isFormControl = inputGroup ? !!inputGroup.closest(\"form\") : true;\n\n const listenersRef = useLazyRef(() => new Set<() => void>());\n const stateRef = useLazyRef<StoreState>(() => ({\n value: valueProp ?? defaultValue ?? \"\",\n open: open ?? defaultOpen ?? false,\n openedViaFocus: false\n }));\n\n const propsRef = useAsRef({ onValueChange, onOpenChange });\n\n const store: Store = React.useMemo(() => {\n return {\n subscribe: (cb) => {\n listenersRef.current.add(cb);\n return () => listenersRef.current.delete(cb);\n },\n getState: () => stateRef.current,\n setState: (key, value) => {\n if (Object.is(stateRef.current[key], value)) return;\n\n if (key === \"value\" && typeof value === \"string\") {\n stateRef.current.value = value;\n propsRef.current.onValueChange?.(value);\n } else if (key === \"open\" && typeof value === \"boolean\") {\n stateRef.current.open = value;\n propsRef.current.onOpenChange?.(value);\n if (!value) {\n stateRef.current.openedViaFocus = false;\n }\n } else {\n stateRef.current[key] = value;\n }\n\n store.notify();\n },\n notify: () => {\n for (const cb of listenersRef.current) {\n cb();\n }\n }\n };\n }, [listenersRef, stateRef, propsRef]);\n\n const value = useStore((state) => state.value, store);\n\n useIsomorphicLayoutEffect(() => {\n if (valueProp !== undefined) {\n store.setState(\"value\", valueProp);\n }\n }, [valueProp]);\n\n useIsomorphicLayoutEffect(() => {\n if (open !== undefined) {\n store.setState(\"open\", open);\n }\n }, [open]);\n\n const storeOpen = useStore((state) => state.open, store);\n\n const onPopoverOpenChange = React.useCallback((newOpen: boolean) => store.setState(\"open\", newOpen), [store]);\n\n const is12Hour = React.useMemo(() => getIs12Hour(locale), [locale]);\n\n const normalizedPlaceholder = React.useMemo(() => {\n if (typeof segmentPlaceholder === \"string\") {\n return {\n hour: segmentPlaceholder,\n minute: segmentPlaceholder,\n second: segmentPlaceholder,\n period: segmentPlaceholder\n };\n }\n return {\n hour: segmentPlaceholder.hour ?? DEFAULT_SEGMENT_PLACEHOLDER,\n minute: segmentPlaceholder.minute ?? DEFAULT_SEGMENT_PLACEHOLDER,\n second: segmentPlaceholder.second ?? DEFAULT_SEGMENT_PLACEHOLDER,\n period: segmentPlaceholder.period ?? DEFAULT_SEGMENT_PLACEHOLDER\n };\n }, [segmentPlaceholder]);\n\n const labels = useComitorLabels(\"timePicker\", labelsProp);\n\n const rootContext = React.useMemo<TimePickerContextValue>(\n () => ({\n id: rootId,\n inputGroupId,\n labelId,\n triggerId,\n inputGroupRef,\n triggerRef,\n openOnFocus,\n inputGroupClickAction,\n onInputGroupChange: setInputGroup,\n disabled,\n readOnly,\n required,\n invalid,\n showSeconds,\n is12Hour,\n minuteStep,\n secondStep,\n hourStep,\n segmentPlaceholder: normalizedPlaceholder,\n labels,\n min,\n max\n }),\n [\n rootId,\n inputGroupId,\n labelId,\n triggerId,\n openOnFocus,\n inputGroupClickAction,\n disabled,\n readOnly,\n required,\n invalid,\n showSeconds,\n is12Hour,\n minuteStep,\n secondStep,\n hourStep,\n normalizedPlaceholder,\n labels,\n min,\n max\n ]\n );\n\n const RootPrimitive = asChild ? Slot : \"div\";\n\n return (\n <>\n <StoreContext.Provider value={store}>\n <TimePickerContext.Provider value={rootContext}>\n <Popover open={storeOpen} onOpenChange={onPopoverOpenChange}>\n <RootPrimitive\n data-slot=\"time-picker\"\n data-disabled={disabled ? \"\" : undefined}\n data-invalid={invalid ? \"\" : undefined}\n {...rootProps}\n className={cn(\"relative\", className)}\n >\n {children}\n </RootPrimitive>\n </Popover>\n </TimePickerContext.Provider>\n </StoreContext.Provider>\n {isFormControl && (\n <VisuallyHiddenInput\n type=\"hidden\"\n control={inputGroup}\n name={name}\n value={value}\n disabled={disabled}\n readOnly={readOnly}\n required={required}\n />\n )}\n </>\n );\n}\n\ninterface TimePickerLabelProps extends React.ComponentProps<\"label\"> {\n asChild?: boolean;\n}\n\nfunction TimePickerLabel(props: TimePickerLabelProps) {\n const { asChild, className, ...labelProps } = props;\n\n const { labelId } = useTimePickerContext(LABEL_NAME);\n\n const LabelPrimitive = asChild ? Slot : \"label\";\n\n return (\n <LabelPrimitive\n data-slot=\"time-picker-label\"\n {...labelProps}\n /*\n * ⚠ Khác thượng nguồn: bản gốc đặt `htmlFor={labelId}` mà KHÔNG phần tử nào mang\n * `id={labelId}` — nhóm ô trỏ `aria-labelledby={labelId}` vào hư không nên trình đọc màn\n * hình đọc một nhóm không tên, và `htmlFor` trỏ vào chính một id không tồn tại. Nhãn giờ\n * MANG id đó; `htmlFor` (nếu app cần) đi qua `labelProps`.\n */\n id={labelId}\n className={cn(\n \"text-sm leading-none font-medium peer-disabled:cursor-not-allowed peer-disabled:opacity-70\",\n className\n )}\n />\n );\n}\n\ninterface TimePickerInputGroupContextValue {\n onInputRegister: (segment: Segment, ref: React.RefObject<InputElement | null>) => void;\n onInputUnregister: (segment: Segment) => void;\n getNextInput: (currentSegment: Segment) => React.RefObject<InputElement | null> | null;\n}\n\nconst TimePickerInputGroupContext = React.createContext<TimePickerInputGroupContextValue | null>(null);\n\nfunction useTimePickerInputGroupContext(consumerName: string) {\n const context = React.useContext(TimePickerInputGroupContext);\n if (!context) {\n throw new Error(`\\`${consumerName}\\` phải nằm bên trong \\`${INPUT_GROUP_NAME}\\``);\n }\n return context;\n}\n\ntype TimePickerInputGroupProps = DivProps;\n\nfunction TimePickerInputGroup(props: TimePickerInputGroupProps) {\n const {\n onPointerDown: onPointerDownProp,\n onClick: onClickProp,\n asChild,\n className,\n style,\n ref,\n ...inputGroupProps\n } = props;\n\n const {\n inputGroupId,\n labelId,\n onInputGroupChange,\n disabled,\n readOnly,\n invalid,\n segmentPlaceholder,\n labels,\n inputGroupRef,\n triggerRef,\n inputGroupClickAction\n } = useTimePickerContext(INPUT_GROUP_NAME);\n\n const store = useStoreContext(INPUT_GROUP_NAME);\n\n const composedRef = useComposedRefs(ref, inputGroupRef, onInputGroupChange);\n\n const inputRefsMap = React.useRef<Map<Segment, React.RefObject<InputElement | null>>>(new Map());\n\n const onInputRegister = React.useCallback((segment: Segment, ref: React.RefObject<InputElement | null>) => {\n inputRefsMap.current.set(segment, ref);\n }, []);\n\n const onInputUnregister = React.useCallback((segment: Segment) => {\n inputRefsMap.current.delete(segment);\n }, []);\n\n const getNextInput = React.useCallback((currentSegment: Segment): React.RefObject<InputElement | null> | null => {\n const segmentOrder: Segment[] = [\"hour\", \"minute\", \"second\", \"period\"];\n const currentIndex = segmentOrder.indexOf(currentSegment);\n\n if (currentIndex === -1 || currentIndex === segmentOrder.length - 1) {\n return null;\n }\n\n for (let i = currentIndex + 1; i < segmentOrder.length; i++) {\n const nextSegment = segmentOrder[i];\n if (nextSegment) {\n const nextRef = inputRefsMap.current.get(nextSegment);\n if (nextRef?.current) {\n return nextRef;\n }\n }\n }\n\n return null;\n }, []);\n\n const onPointerDown = React.useCallback(\n (event: React.PointerEvent<InputGroupElement>) => {\n onPointerDownProp?.(event);\n if (disabled || readOnly || event.defaultPrevented) return;\n\n const target = event.target as HTMLElement;\n\n if (target.tagName === \"INPUT\" || target.closest(\"input\")) {\n return;\n }\n\n if (triggerRef.current?.contains(target)) {\n return;\n }\n\n event.preventDefault();\n },\n [onPointerDownProp, disabled, readOnly, triggerRef]\n );\n\n const onClick = React.useCallback(\n (event: React.MouseEvent<InputGroupElement>) => {\n onClickProp?.(event);\n if (disabled || readOnly || event.defaultPrevented) return;\n\n const target = event.target as HTMLElement;\n\n if (target.tagName === \"INPUT\" || target.closest(\"input\")) {\n return;\n }\n\n if (triggerRef.current?.contains(target)) {\n return;\n }\n\n if (inputGroupClickAction === \"open\") {\n store.setState(\"open\", true);\n } else {\n const activeElement = document.activeElement;\n const isInputAlreadyFocused =\n activeElement && activeElement.tagName === \"INPUT\" && inputGroupRef.current?.contains(activeElement);\n\n if (!isInputAlreadyFocused) {\n for (const segment of SEGMENTS) {\n const inputRef = inputRefsMap.current.get(segment);\n if (inputRef?.current) {\n inputRef.current.focus();\n inputRef.current.select();\n break;\n }\n }\n }\n }\n },\n [onClickProp, disabled, readOnly, inputGroupClickAction, store, triggerRef, inputGroupRef]\n );\n\n const inputGroupContextValue = React.useMemo<TimePickerInputGroupContextValue>(\n () => ({\n onInputRegister,\n onInputUnregister,\n getNextInput\n }),\n [onInputRegister, onInputUnregister, getNextInput]\n );\n\n const InputGroupPrimitive = asChild ? Slot : \"div\";\n\n return (\n <TimePickerInputGroupContext.Provider value={inputGroupContextValue}>\n <PopoverAnchor asChild>\n <InputGroupPrimitive\n role=\"group\"\n id={inputGroupId}\n aria-labelledby={labelId}\n data-slot=\"time-picker-input-group\"\n data-disabled={disabled ? \"\" : undefined}\n data-invalid={invalid ? \"\" : undefined}\n {...inputGroupProps}\n className={cn(\n /*\n * ⚠ Khác thượng nguồn: khung ô đi theo `Input` của gói (ô ngày của `DatePicker` là\n * một `Input`, và hai thứ này hay đứng chung một hàng biểu mẫu): `h-9` thay `h-10`,\n * bỏ `shadow-xs`, hover đậm viền `--control-edge-strong`, focus viền\n * `--primary-ink` + quầng `ring-2 ring-ring/50` KHÔNG offset (quy ước họ ô nhập —\n * xem `InputGroup`), lỗi viền `--destructive-ink`. Số đo ở chú thích đầu `input.tsx`.\n */\n \"flex h-9 w-full cursor-text items-center gap-0.5 rounded-md border border-input bg-background px-3 py-2 text-sm text-foreground transition-colors duration-150 ease-out outline-none hover:border-control-edge-strong\",\n \"has-[input:focus]:border-primary-ink has-[input:focus]:ring-2 has-[input:focus]:ring-ring/50\",\n invalid &&\n \"border-destructive-ink hover:border-destructive-ink has-[input:focus]:border-destructive-ink has-[input:focus]:ring-destructive/30\",\n /*\n * ⚠ Khác thượng nguồn: bản gốc ghép `disabled && \"cursor-not-allowed opacity-50\"` —\n * lớp gắn VÔ ĐIỀU KIỆN vào chuỗi, nên `pnpm lint:a11y` đo viền/chữ lúc NGHỈ đã nhân\n * 50% (viền 1,75:1, chữ 3,49:1 ✗). Neo vào `:disabled` gốc của các ô con (cổng miễn\n * trừ đúng nhánh này — WCAG 1.4.3/1.4.11 không đòi tương phản cho control vô hiệu);\n * `disabled` ở gốc khoá MỌI ô nên hai cách cho cùng kết quả. Thêm `bg-muted` theo `Input`.\n */\n \"has-[input:disabled]:cursor-not-allowed has-[input:disabled]:bg-muted has-[input:disabled]:opacity-50\",\n className\n )}\n style={\n {\n \"--time-picker-hour-input-width\": `${segmentPlaceholder.hour.length}ch`,\n \"--time-picker-minute-input-width\": `${segmentPlaceholder.minute.length}ch`,\n \"--time-picker-second-input-width\": `${segmentPlaceholder.second.length}ch`,\n // ⚠ Khác thượng nguồn: tính cả độ dài nhãn buổi (`labels.am`/`labels.pm`) — bản gốc\n // chỉ có \"AM\"/\"PM\" 2 ký tự nên ghim sàn 2; nhãn do app đặt có thể dài hơn.\n \"--time-picker-period-input-width\": `${Math.max(segmentPlaceholder.period.length, labels.am.length, labels.pm.length, 2) + 0.5}ch`,\n ...style\n } as React.CSSProperties\n }\n ref={composedRef}\n onPointerDown={onPointerDown}\n onClick={onClick}\n />\n </PopoverAnchor>\n </TimePickerInputGroupContext.Provider>\n );\n}\n\ninterface TimePickerInputProps extends Omit<React.ComponentProps<\"input\">, \"type\" | \"value\"> {\n segment: Segment;\n}\n\nfunction TimePickerInput(props: TimePickerInputProps) {\n const {\n segment,\n onBlur: onBlurProp,\n onChange: onChangeProp,\n onClick: onClickProp,\n onFocus: onFocusProp,\n onKeyDown: onKeyDownProp,\n disabled: disabledProp,\n readOnly: readOnlyProp,\n className,\n style,\n ref,\n ...inputProps\n } = props;\n\n const { is12Hour, showSeconds, disabled, readOnly, invalid, segmentPlaceholder, labels, openOnFocus } =\n useTimePickerContext(INPUT_NAME);\n const store = useStoreContext(INPUT_NAME);\n const inputGroupContext = useTimePickerInputGroupContext(INPUT_NAME);\n\n const isDisabled = disabledProp || disabled;\n const isReadOnly = readOnlyProp || readOnly;\n\n const value = useStore((state) => state.value);\n const timeValue = parseTimeString(value);\n\n const inputRef = React.useRef<HTMLInputElement>(null);\n const composedRef = useComposedRefs(ref, inputRef);\n\n useIsomorphicLayoutEffect(() => {\n if (segment) {\n inputGroupContext.onInputRegister(segment as Segment, inputRef);\n return () => inputGroupContext.onInputUnregister(segment as Segment);\n }\n }, [inputGroupContext, segment]);\n\n const getSegmentValue = React.useCallback(() => {\n if (!timeValue) {\n if (!segment) return \"\";\n return segmentPlaceholder[segment];\n }\n switch (segment) {\n case \"hour\": {\n if (timeValue.hour === undefined) return segmentPlaceholder.hour;\n if (is12Hour) {\n return to12Hour(timeValue.hour).hour.toString().padStart(2, \"0\");\n }\n return timeValue.hour.toString().padStart(2, \"0\");\n }\n case \"minute\":\n if (timeValue.minute === undefined) return segmentPlaceholder.minute;\n return timeValue.minute.toString().padStart(2, \"0\");\n case \"second\":\n if (timeValue.second === undefined) return segmentPlaceholder.second;\n return timeValue.second.toString().padStart(2, \"0\");\n case \"period\": {\n if (!timeValue || timeValue.hour === undefined) return segmentPlaceholder.period;\n return to12Hour(timeValue.hour).period;\n }\n default:\n return \"\";\n }\n }, [timeValue, segment, is12Hour, segmentPlaceholder]);\n\n const [editValue, setEditValue] = React.useState(getSegmentValue());\n const [isEditing, setIsEditing] = React.useState(false);\n const [pendingDigit, setPendingDigit] = React.useState<string | null>(null);\n\n React.useEffect(() => {\n if (!isEditing) {\n setEditValue(getSegmentValue());\n setPendingDigit(null);\n }\n }, [getSegmentValue, isEditing]);\n\n const updateTimeValue = React.useCallback(\n (newSegmentValue: string | undefined, shouldCreateIfEmpty = false) => {\n const placeholder = segment ? segmentPlaceholder[segment] : DEFAULT_SEGMENT_PLACEHOLDER;\n if (!newSegmentValue || newSegmentValue === placeholder) return;\n if (!timeValue && !shouldCreateIfEmpty) return;\n\n const currentTime = timeValue ?? {};\n const newTime = { ...currentTime };\n\n switch (segment) {\n case \"hour\": {\n const displayHour = Number.parseInt(newSegmentValue, 10);\n if (!Number.isNaN(displayHour)) {\n if (is12Hour) {\n const clampedHour = clamp(displayHour, 1, 12);\n let currentPeriod: Period;\n if (timeValue?.period !== undefined) {\n currentPeriod = timeValue.period;\n } else if (timeValue?.hour !== undefined) {\n currentPeriod = to12Hour(timeValue.hour).period;\n } else {\n const now = new Date();\n currentPeriod = to12Hour(now.getHours()).period;\n }\n const hour24 = to24Hour(clampedHour, currentPeriod);\n newTime.hour = hour24;\n if (timeValue?.period !== undefined) {\n newTime.period = timeValue.period;\n }\n } else {\n newTime.hour = clamp(displayHour, 0, 23);\n }\n }\n break;\n }\n case \"minute\": {\n const minute = Number.parseInt(newSegmentValue, 10);\n if (!Number.isNaN(minute)) {\n newTime.minute = clamp(minute, 0, 59);\n }\n break;\n }\n case \"second\": {\n const second = Number.parseInt(newSegmentValue, 10);\n if (!Number.isNaN(second)) {\n newTime.second = clamp(second, 0, 59);\n }\n break;\n }\n case \"period\": {\n if (newSegmentValue === \"AM\" || newSegmentValue === \"PM\") {\n newTime.period = newSegmentValue;\n if (timeValue && timeValue.hour !== undefined) {\n const currentDisplay = to12Hour(timeValue.hour);\n newTime.hour = to24Hour(currentDisplay.hour, newSegmentValue);\n }\n }\n break;\n }\n }\n\n const newValue = formatTimeValue(newTime, showSeconds);\n store.setState(\"value\", newValue);\n },\n [timeValue, segment, is12Hour, showSeconds, store, segmentPlaceholder]\n );\n\n const onBlur = React.useCallback(\n (event: React.FocusEvent<InputElement>) => {\n onBlurProp?.(event);\n if (event.defaultPrevented) return;\n\n setIsEditing(false);\n\n const placeholder = segment ? segmentPlaceholder[segment] : DEFAULT_SEGMENT_PLACEHOLDER;\n if (editValue && editValue !== placeholder && editValue.length > 0) {\n let valueToUpdate = editValue;\n\n if (segment !== \"period\") {\n if (editValue.length === 2) {\n valueToUpdate = editValue;\n } else if (editValue.length === 1) {\n const numValue = Number.parseInt(editValue, 10);\n if (!Number.isNaN(numValue)) {\n valueToUpdate = numValue.toString().padStart(2, \"0\");\n }\n }\n }\n\n updateTimeValue(valueToUpdate, true);\n\n // Ô còn trống sau khi rời một ô đã gõ → lấp bằng giờ hiện tại (hành vi gốc).\n queueMicrotask(() => {\n const currentTimeValue = parseTimeString(store.getState().value);\n if (currentTimeValue) {\n const now = new Date();\n const newTime = { ...currentTimeValue };\n let needsUpdate = false;\n\n if (newTime.hour === undefined) {\n newTime.hour = now.getHours();\n needsUpdate = true;\n }\n\n if (newTime.minute === undefined) {\n newTime.minute = now.getMinutes();\n needsUpdate = true;\n }\n\n if (showSeconds && newTime.second === undefined) {\n newTime.second = now.getSeconds();\n needsUpdate = true;\n }\n\n if (needsUpdate) {\n const newValue = formatTimeValue(newTime, showSeconds);\n store.setState(\"value\", newValue);\n }\n }\n });\n }\n\n setEditValue(getSegmentValue());\n setPendingDigit(null);\n },\n [onBlurProp, editValue, updateTimeValue, getSegmentValue, segment, segmentPlaceholder, showSeconds, store]\n );\n\n const onChange = React.useCallback(\n (event: React.ChangeEvent<InputElement>) => {\n onChangeProp?.(event);\n if (event.defaultPrevented) return;\n\n let newValue = event.target.value;\n\n const placeholder = segment ? segmentPlaceholder[segment] : DEFAULT_SEGMENT_PLACEHOLDER;\n if (editValue === placeholder && newValue.length > 0 && newValue !== placeholder) {\n newValue = newValue.replace(new RegExp(`^${placeholder}`), \"\");\n }\n\n if (segment === \"period\") {\n const newPeriod = getPeriodFromKey(newValue.charAt(0), labels);\n\n if (newPeriod) {\n setEditValue(newPeriod);\n updateTimeValue(newPeriod, true);\n queueMicrotask(() => {\n inputRef.current?.select();\n });\n }\n return;\n }\n\n if (segment === \"hour\" || segment === \"minute\" || segment === \"second\") {\n newValue = newValue.replace(/\\D/g, \"\");\n }\n\n if (newValue.length > 2) {\n newValue = newValue.slice(0, 2);\n }\n if (segment === \"hour\" || segment === \"minute\" || segment === \"second\") {\n const numValue = Number.parseInt(newValue, 10);\n\n if (!Number.isNaN(numValue) && newValue.length > 0) {\n if (pendingDigit !== null && newValue.length === 1) {\n const twoDigitValue = pendingDigit + newValue;\n const combinedNum = Number.parseInt(twoDigitValue, 10);\n\n if (!Number.isNaN(combinedNum)) {\n const paddedValue = combinedNum.toString().padStart(2, \"0\");\n setEditValue(paddedValue);\n updateTimeValue(paddedValue, true);\n setPendingDigit(null);\n\n queueMicrotask(() => {\n if (segment) {\n const nextInputRef = inputGroupContext.getNextInput(segment);\n if (nextInputRef?.current) {\n nextInputRef.current.focus();\n nextInputRef.current.select();\n }\n }\n });\n return;\n }\n }\n\n const maxFirstDigit = segment === \"hour\" ? (is12Hour ? 1 : 2) : 5;\n\n const firstDigit = Number.parseInt(newValue[0] ?? \"0\", 10);\n const shouldAutoAdvance = firstDigit > maxFirstDigit;\n\n if (newValue.length === 1) {\n if (shouldAutoAdvance) {\n const paddedValue = numValue.toString().padStart(2, \"0\");\n setEditValue(paddedValue);\n updateTimeValue(paddedValue, true);\n setPendingDigit(null);\n\n queueMicrotask(() => {\n if (segment) {\n const nextInputRef = inputGroupContext.getNextInput(segment);\n if (nextInputRef?.current) {\n nextInputRef.current.focus();\n nextInputRef.current.select();\n }\n }\n });\n } else {\n const paddedValue = numValue.toString().padStart(2, \"0\");\n setEditValue(paddedValue);\n setPendingDigit(newValue);\n queueMicrotask(() => {\n inputRef.current?.select();\n });\n }\n } else if (newValue.length === 2) {\n const paddedValue = numValue.toString().padStart(2, \"0\");\n setEditValue(paddedValue);\n updateTimeValue(paddedValue, true);\n setPendingDigit(null);\n\n queueMicrotask(() => {\n if (segment) {\n const nextInputRef = inputGroupContext.getNextInput(segment);\n if (nextInputRef?.current) {\n nextInputRef.current.focus();\n nextInputRef.current.select();\n }\n }\n });\n }\n } else if (newValue.length === 0) {\n setEditValue(\"\");\n setPendingDigit(null);\n }\n }\n },\n [\n segment,\n updateTimeValue,\n onChangeProp,\n editValue,\n is12Hour,\n inputGroupContext,\n pendingDigit,\n segmentPlaceholder,\n labels\n ]\n );\n\n const onClick = React.useCallback(\n (event: React.MouseEvent<InputElement>) => {\n onClickProp?.(event);\n if (event.defaultPrevented) return;\n\n event.currentTarget.select();\n },\n [onClickProp]\n );\n\n const onFocus = React.useCallback(\n (event: React.FocusEvent<InputElement>) => {\n onFocusProp?.(event);\n if (event.defaultPrevented) return;\n\n setIsEditing(true);\n setPendingDigit(null);\n\n if (openOnFocus && !store.getState().open) {\n store.setState(\"openedViaFocus\", true);\n store.setState(\"open\", true);\n }\n\n queueMicrotask(() => event.target.select());\n },\n [onFocusProp, openOnFocus, store]\n );\n\n const onKeyDown = React.useCallback(\n (event: React.KeyboardEvent<InputElement>) => {\n onKeyDownProp?.(event);\n if (event.defaultPrevented) return;\n\n if (event.key === \"ArrowLeft\" || event.key === \"ArrowRight\") {\n event.preventDefault();\n\n const goToPrevious = event.key === \"ArrowLeft\";\n const inputGroup = inputRef.current?.closest('[data-slot=\"time-picker-input-group\"]');\n\n if (inputGroup && inputRef.current) {\n const allInputs = Array.from(inputGroup.querySelectorAll('input[type=\"text\"]')) as HTMLInputElement[];\n const currentIdx = allInputs.indexOf(inputRef.current);\n\n if (currentIdx !== -1) {\n const targetIdx = goToPrevious\n ? Math.max(0, currentIdx - 1)\n : Math.min(allInputs.length - 1, currentIdx + 1);\n\n const targetInput = allInputs[targetIdx];\n if (targetInput && targetInput !== inputRef.current) {\n targetInput.focus();\n targetInput.select();\n }\n }\n }\n return;\n }\n\n if (event.key === \"Backspace\" || event.key === \"Delete\") {\n const input = inputRef.current;\n if (input && input.selectionStart === 0 && input.selectionEnd === input.value.length) {\n event.preventDefault();\n const placeholder = segment ? segmentPlaceholder[segment] : DEFAULT_SEGMENT_PLACEHOLDER;\n setEditValue(placeholder);\n setPendingDigit(null);\n\n if (timeValue) {\n const newTime = { ...timeValue };\n switch (segment) {\n case \"hour\":\n delete newTime.hour;\n break;\n case \"minute\":\n delete newTime.minute;\n break;\n case \"second\":\n delete newTime.second;\n break;\n case \"period\":\n delete newTime.period;\n break;\n }\n\n if (\n newTime.hour !== undefined ||\n newTime.minute !== undefined ||\n newTime.second !== undefined ||\n newTime.period !== undefined\n ) {\n const newValue = formatTimeValue(newTime, showSeconds);\n store.setState(\"value\", newValue);\n } else {\n store.setState(\"value\", \"\");\n }\n } else {\n store.setState(\"value\", \"\");\n }\n\n queueMicrotask(() => {\n inputRef.current?.select();\n });\n return;\n }\n }\n\n if (segment === \"period\") {\n const newPeriodFromKey = getPeriodFromKey(event.key, labels);\n if (newPeriodFromKey) {\n event.preventDefault();\n setEditValue(newPeriodFromKey);\n updateTimeValue(newPeriodFromKey, true);\n queueMicrotask(() => {\n inputRef.current?.select();\n });\n } else if (event.key === \"ArrowUp\" || event.key === \"ArrowDown\") {\n event.preventDefault();\n const placeholder = segmentPlaceholder.period;\n const currentPeriod = editValue === placeholder || editValue === \"\" ? \"AM\" : editValue;\n const newPeriod = currentPeriod === \"AM\" || currentPeriod === \"A\" ? \"PM\" : \"AM\";\n setEditValue(newPeriod);\n updateTimeValue(newPeriod, true);\n queueMicrotask(() => {\n inputRef.current?.select();\n });\n }\n return;\n }\n\n if (event.key === \"Tab\") {\n const placeholder = segment ? segmentPlaceholder[segment] : DEFAULT_SEGMENT_PLACEHOLDER;\n if (editValue && editValue.length > 0 && editValue !== placeholder) {\n if (editValue.length === 2) {\n updateTimeValue(editValue, true);\n } else if (editValue.length === 1) {\n const numValue = Number.parseInt(editValue, 10);\n if (!Number.isNaN(numValue)) {\n const paddedValue = numValue.toString().padStart(2, \"0\");\n updateTimeValue(paddedValue, true);\n }\n }\n }\n return;\n }\n\n if (event.key === \"Enter\") {\n event.preventDefault();\n const placeholder = segment ? segmentPlaceholder[segment] : DEFAULT_SEGMENT_PLACEHOLDER;\n if (editValue && editValue.length > 0 && editValue !== placeholder) {\n if (editValue.length === 2) {\n updateTimeValue(editValue, true);\n } else if (editValue.length === 1) {\n const numValue = Number.parseInt(editValue, 10);\n if (!Number.isNaN(numValue)) {\n const paddedValue = numValue.toString().padStart(2, \"0\");\n updateTimeValue(paddedValue, true);\n }\n }\n }\n queueMicrotask(() => {\n inputRef.current?.select();\n });\n }\n\n if (event.key === \"Escape\") {\n event.preventDefault();\n setEditValue(getSegmentValue());\n inputRef.current?.blur();\n }\n\n if (event.key === \"ArrowUp\") {\n event.preventDefault();\n const placeholder = segment ? segmentPlaceholder[segment] : DEFAULT_SEGMENT_PLACEHOLDER;\n if (editValue === placeholder || editValue === \"\") {\n const defaultValue = segment === \"hour\" ? (is12Hour ? 12 : 0) : 0;\n const formattedValue = defaultValue.toString().padStart(2, \"0\");\n setEditValue(formattedValue);\n updateTimeValue(formattedValue, true);\n queueMicrotask(() => {\n inputRef.current?.select();\n });\n return;\n }\n const currentValue = Number.parseInt(editValue, 10);\n if (!Number.isNaN(currentValue)) {\n let newValue: number;\n switch (segment) {\n case \"hour\":\n if (is12Hour) {\n newValue = currentValue === 12 ? 1 : currentValue + 1;\n } else {\n newValue = currentValue === 23 ? 0 : currentValue + 1;\n }\n break;\n case \"minute\":\n case \"second\":\n newValue = currentValue === 59 ? 0 : currentValue + 1;\n break;\n default:\n return;\n }\n const formattedValue = newValue.toString().padStart(2, \"0\");\n setEditValue(formattedValue);\n updateTimeValue(formattedValue, true);\n queueMicrotask(() => {\n inputRef.current?.select();\n });\n }\n }\n\n if (event.key === \"ArrowDown\") {\n event.preventDefault();\n const placeholder = segment ? segmentPlaceholder[segment] : DEFAULT_SEGMENT_PLACEHOLDER;\n if (editValue === placeholder || editValue === \"\") {\n const defaultValue = segment === \"hour\" ? (is12Hour ? 12 : 23) : 59;\n const formattedValue = defaultValue.toString().padStart(2, \"0\");\n setEditValue(formattedValue);\n updateTimeValue(formattedValue, true);\n queueMicrotask(() => {\n inputRef.current?.select();\n });\n return;\n }\n const currentValue = Number.parseInt(editValue, 10);\n if (!Number.isNaN(currentValue)) {\n let newValue: number;\n switch (segment) {\n case \"hour\":\n if (is12Hour) {\n newValue = currentValue === 1 ? 12 : currentValue - 1;\n } else {\n newValue = currentValue === 0 ? 23 : currentValue - 1;\n }\n break;\n case \"minute\":\n case \"second\":\n newValue = currentValue === 0 ? 59 : currentValue - 1;\n break;\n default:\n return;\n }\n const formattedValue = newValue.toString().padStart(2, \"0\");\n setEditValue(formattedValue);\n updateTimeValue(formattedValue, true);\n queueMicrotask(() => {\n inputRef.current?.select();\n });\n }\n }\n },\n [\n onKeyDownProp,\n editValue,\n segment,\n is12Hour,\n getSegmentValue,\n updateTimeValue,\n showSeconds,\n timeValue,\n store,\n segmentPlaceholder,\n labels\n ]\n );\n\n /*\n * ⚠ Khác thượng nguồn: ở đồng hồ 24 giờ bản gốc VẪN vẽ ô buổi (in \"PM\" cạnh \"14:30\"), và gõ `A`\n * vào đó biến 14:30 thành 02:30 — trong khi cột `TimePickerPeriod` của chính nó tự ẩn ở chế độ\n * này. Mọi demo thượng nguồn đều đặt sẵn `<TimePickerInput segment=\"period\" />`, và tiếng Việt\n * (cũng như `en-GB`) chạy 24 giờ, nên ô buổi ẩn theo cùng luật với cột. Đặt SAU mọi hook.\n */\n if (segment === \"period\" && !is12Hour) return null;\n\n const displayValue = isEditing ? editValue : getSegmentValue();\n\n const segmentWidth = segment ? `var(--time-picker-${segment}-input-width)` : \"2ch\";\n\n return (\n <input\n type=\"text\"\n inputMode={segment === \"period\" ? \"text\" : \"numeric\"}\n autoComplete=\"off\"\n autoCorrect=\"off\"\n autoCapitalize=\"off\"\n spellCheck={false}\n translate=\"no\"\n /*\n * ⚠ Khác thượng nguồn: bản gốc không đặt tên cho ô nào — trình đọc màn hình đọc bốn ô\n * \"sửa văn bản, 14\" liền nhau mà không biết ô nào là giờ, ô nào là phút. Tên lấy từ\n * `labels` (namespace `timePicker`: \"Hour\"/\"Minute\"/\"Second\"/\"AM/PM\" ở tiếng Anh); `aria-label`\n * của app vẫn đè được.\n * `aria-invalid` cũng vậy: bản gốc chỉ tô viền đỏ (`data-invalid`) mà không báo cho AT.\n */\n aria-label={labels[segment]}\n aria-invalid={invalid || undefined}\n {...inputProps}\n disabled={isDisabled}\n readOnly={isReadOnly}\n className={cn(\n \"inline-flex h-full items-center justify-center border-0 bg-transparent text-center text-sm tabular-nums transition-colors outline-none focus:bg-transparent disabled:cursor-not-allowed disabled:opacity-50\",\n className\n )}\n style={{ width: segmentWidth, ...style }}\n ref={composedRef}\n value={segment === \"period\" ? getPeriodLabel(displayValue, labels) : displayValue}\n onBlur={onBlur}\n onChange={onChange}\n onClick={onClick}\n onFocus={onFocus}\n onKeyDown={onKeyDown}\n />\n );\n}\n\ntype TimePickerTriggerProps = ButtonProps;\n\nfunction TimePickerTrigger(props: TimePickerTriggerProps) {\n const { className, children, disabled: disabledProp, ref, ...triggerProps } = props;\n\n const { triggerId, disabled, labels, triggerRef } = useTimePickerContext(TRIGGER_NAME);\n\n const isDisabled = disabledProp || disabled;\n\n const composedRef = useComposedRefs(ref, triggerRef);\n\n return (\n <PopoverTrigger\n type=\"button\"\n id={triggerId}\n data-slot=\"time-picker-trigger\"\n disabled={isDisabled}\n ref={composedRef}\n {...triggerProps}\n className={cn(\n // ⚠ Khác thượng nguồn: thêm viền focus theo khuôn `Button` của gói — bản gốc không có kiểu\n // focus nào, và viền mặc định của trình duyệt bị lớp nền `outline-ring/50` pha còn gold 50%.\n \"ml-auto flex items-center rounded-sm text-muted-foreground transition-colors hover:text-foreground focus-visible:outline-2 focus-visible:outline-ring focus-visible:outline-offset-2 disabled:pointer-events-none [&>svg:not([class*='size-'])]:size-4\",\n className\n )}\n >\n {/*\n * ⚠ Khác thượng nguồn: nút mặc định chỉ có icon đồng hồ nên là một nút KHÔNG TÊN. Tên đi qua\n * `sr-only` (cùng khuôn nút mở lịch của `DatePicker`), không qua `aria-label`, để khi app\n * truyền `children` có chữ thì chữ đó là tên — không bị một nhãn ẩn đè lên.\n */}\n {children ?? (\n <>\n <Clock aria-hidden=\"true\" />\n <span className=\"sr-only\">{labels.openPicker}</span>\n </>\n )}\n </PopoverTrigger>\n );\n}\n\ninterface TimePickerGroupContextValue {\n getColumns: () => ColumnData[];\n onColumnRegister: (column: ColumnData) => void;\n onColumnUnregister: (id: string) => void;\n}\n\nconst TimePickerGroupContext = React.createContext<TimePickerGroupContextValue | null>(null);\n\nfunction useTimePickerGroupContext(consumerName: string) {\n const context = React.useContext(TimePickerGroupContext);\n if (!context) {\n // Bản gốc báo `TimePicker`; thứ thật sự cung cấp context này là `TimePickerContent`.\n throw new Error(`\\`${consumerName}\\` phải nằm bên trong \\`${CONTENT_NAME}\\``);\n }\n return context;\n}\n\ninterface TimePickerContentProps extends DivProps, React.ComponentProps<typeof PopoverContent> {}\n\nfunction TimePickerContent(props: TimePickerContentProps) {\n const {\n side = \"bottom\",\n align = \"start\",\n sideOffset = 6,\n className,\n onOpenAutoFocus: onOpenAutoFocusProp,\n onInteractOutside: onInteractOutsideProp,\n ...contentProps\n } = props;\n\n const store = useStoreContext(CONTENT_NAME);\n const { openOnFocus, inputGroupRef } = useTimePickerContext(CONTENT_NAME);\n const columnsRef = React.useRef<Map<string, Omit<ColumnData, \"id\">>>(new Map());\n\n const onColumnRegister = React.useCallback((column: ColumnData) => {\n columnsRef.current.set(column.id, column);\n }, []);\n\n const onColumnUnregister = React.useCallback((id: string) => {\n columnsRef.current.delete(id);\n }, []);\n\n const getColumns = React.useCallback(() => {\n const columns = Array.from(columnsRef.current.entries())\n .map(([id, { ref, getSelectedItemRef, getItems }]) => ({\n id,\n ref,\n getSelectedItemRef,\n getItems\n }))\n .filter((c) => c.ref.current !== null);\n return sortNodes(columns);\n }, []);\n\n const groupContextValue = React.useMemo<TimePickerGroupContextValue>(\n () => ({\n getColumns,\n onColumnRegister,\n onColumnUnregister\n }),\n [getColumns, onColumnRegister, onColumnUnregister]\n );\n\n const onOpenAutoFocus: NonNullable<PopoverContentProps[\"onOpenAutoFocus\"]> = React.useCallback(\n (event) => {\n onOpenAutoFocusProp?.(event);\n if (event.defaultPrevented) return;\n\n event.preventDefault();\n\n const { openedViaFocus } = store.getState();\n\n // Mở vì ô nhập được focus (`openOnFocus`) → để focus yên ở ô nhập.\n if (openedViaFocus) {\n store.setState(\"openedViaFocus\", false);\n return;\n }\n\n const columns = getColumns();\n const firstColumn = columns[0];\n\n if (!firstColumn) return;\n\n const items = firstColumn.getItems();\n const selectedItem = items.find((item) => item.selected);\n\n const candidateRefs = selectedItem\n ? [selectedItem.ref, ...items.map((item) => item.ref)]\n : items.map((item) => item.ref);\n\n focusFirst(candidateRefs, false);\n },\n [onOpenAutoFocusProp, getColumns, store]\n );\n\n const onInteractOutside: NonNullable<PopoverContentProps[\"onInteractOutside\"]> = React.useCallback(\n (event) => {\n onInteractOutsideProp?.(event);\n if (event.defaultPrevented) return;\n\n // `openOnFocus`: bấm vào nhóm ô không được tính là \"bấm ra ngoài\" rồi đóng bảng chọn.\n if (openOnFocus && inputGroupRef.current) {\n const target = event.target;\n if (!(target instanceof Node)) return;\n const isInsideInputGroup = inputGroupRef.current.contains(target);\n\n if (isInsideInputGroup) {\n event.preventDefault();\n }\n }\n },\n [onInteractOutsideProp, openOnFocus, inputGroupRef]\n );\n\n return (\n <TimePickerGroupContext.Provider value={groupContextValue}>\n <PopoverContent\n data-slot=\"time-picker-content\"\n side={side}\n align={align}\n sideOffset={sideOffset}\n {...contentProps}\n className={cn(\"flex w-auto max-w-(--radix-popover-trigger-width) p-0\", className)}\n onOpenAutoFocus={onOpenAutoFocus}\n onInteractOutside={onInteractOutside}\n />\n </TimePickerGroupContext.Provider>\n );\n}\n\ninterface TimePickerColumnContextValue {\n getItems: () => ItemData[];\n onItemRegister: (value: number | string, ref: React.RefObject<ColumnItemElement | null>, selected: boolean) => void;\n onItemUnregister: (value: number | string) => void;\n}\n\nconst TimePickerColumnContext = React.createContext<TimePickerColumnContextValue | null>(null);\n\nfunction useTimePickerColumnContext(consumerName: string) {\n const context = React.useContext(TimePickerColumnContext);\n if (!context) {\n throw new Error(`\\`${consumerName}\\` phải nằm bên trong một cột (\\`${COLUMN_NAME}\\`)`);\n }\n return context;\n}\n\ninterface TimePickerColumnProps extends DivProps {}\n\nfunction TimePickerColumn(props: TimePickerColumnProps) {\n const { children, className, ref, ...columnProps } = props;\n\n const columnId = React.useId();\n const columnRef = React.useRef<ColumnElement | null>(null);\n const composedRef = useComposedRefs(ref, columnRef);\n\n const itemsRef = React.useRef<\n Map<\n number | string,\n {\n ref: React.RefObject<ColumnItemElement | null>;\n selected: boolean;\n }\n >\n >(new Map());\n\n const groupContext = useTimePickerGroupContext(COLUMN_NAME);\n\n const onItemRegister = React.useCallback(\n (value: number | string, ref: React.RefObject<HTMLButtonElement | null>, selected: boolean) => {\n itemsRef.current.set(value, { ref, selected });\n },\n []\n );\n\n const onItemUnregister = React.useCallback((value: number | string) => {\n itemsRef.current.delete(value);\n }, []);\n\n const getItems = React.useCallback(() => {\n const items = Array.from(itemsRef.current.entries())\n .map(([value, { ref, selected }]) => ({\n value,\n ref,\n selected\n }))\n .filter((item) => item.ref.current);\n return sortNodes(items);\n }, []);\n\n const getSelectedItemRef = React.useCallback(() => {\n const items = getItems();\n return items.find((item) => item.selected)?.ref ?? null;\n }, [getItems]);\n\n useIsomorphicLayoutEffect(() => {\n groupContext.onColumnRegister({\n id: columnId,\n ref: columnRef,\n getSelectedItemRef,\n getItems\n });\n return () => groupContext.onColumnUnregister(columnId);\n }, [groupContext, columnId, getSelectedItemRef, getItems]);\n\n const columnContextValue = React.useMemo<TimePickerColumnContextValue>(\n () => ({\n getItems,\n onItemRegister,\n onItemUnregister\n }),\n [getItems, onItemRegister, onItemUnregister]\n );\n\n return (\n <TimePickerColumnContext.Provider value={columnContextValue}>\n {/*\n * ⚠ Khác thượng nguồn: bản gốc là một `div` trần chứa các `button` trần — trình đọc màn hình\n * đọc \"14, nút\" mà không biết đó là cột GIỜ hay PHÚT, cũng không biết mục nào ĐANG CHỌN.\n * Cột là `listbox` (tên do `TimePickerHour`/`…Minute`/`…` truyền xuống), mục là `option`\n * có `aria-selected` — đúng với hành vi sẵn có: mũi tên lên/xuống vừa di focus vừa chọn.\n */}\n <div\n role=\"listbox\"\n ref={composedRef}\n data-slot=\"time-picker-column\"\n {...columnProps}\n className={cn(\"flex flex-col gap-1 p-1 not-last:border-r\", className)}\n >\n {children}\n </div>\n </TimePickerColumnContext.Provider>\n );\n}\n\ninterface TimePickerColumnItemProps extends ButtonProps {\n value: number | string;\n selected?: boolean;\n format?: SegmentFormat;\n}\n\nfunction TimePickerColumnItem(props: TimePickerColumnItemProps) {\n const { value, selected = false, format = \"numeric\", className, children, ref, ...itemProps } = props;\n\n const itemRef = React.useRef<ColumnItemElement | null>(null);\n const composedRef = useComposedRefs(ref, itemRef);\n const columnContext = useTimePickerColumnContext(COLUMN_ITEM_NAME);\n const groupContext = useTimePickerGroupContext(COLUMN_ITEM_NAME);\n\n useIsomorphicLayoutEffect(() => {\n columnContext.onItemRegister(value, itemRef, selected);\n return () => columnContext.onItemUnregister(value);\n }, [columnContext, value, selected]);\n\n useIsomorphicLayoutEffect(() => {\n if (selected && itemRef.current) {\n itemRef.current.scrollIntoView({ block: \"nearest\" });\n }\n }, [selected]);\n\n const onClick = React.useCallback(\n (event: React.MouseEvent<ColumnItemElement>) => {\n itemProps.onClick?.(event);\n if (event.defaultPrevented) return;\n\n itemRef.current?.focus();\n },\n [itemProps.onClick]\n );\n\n const onKeyDown = React.useCallback(\n (event: React.KeyboardEvent<ColumnItemElement>) => {\n itemProps.onKeyDown?.(event);\n if (event.defaultPrevented) return;\n\n if (event.key === \"ArrowUp\" || event.key === \"ArrowDown\") {\n event.preventDefault();\n const items = columnContext.getItems().sort((a, b) => {\n if (typeof a.value === \"number\" && typeof b.value === \"number\") {\n return a.value - b.value;\n }\n return 0;\n });\n const currentIndex = items.findIndex((item) => item.value === value);\n\n let nextIndex: number;\n if (event.key === \"ArrowUp\") {\n nextIndex = currentIndex > 0 ? currentIndex - 1 : items.length - 1;\n } else {\n nextIndex = currentIndex < items.length - 1 ? currentIndex + 1 : 0;\n }\n\n const nextItem = items[nextIndex];\n nextItem?.ref.current?.focus();\n nextItem?.ref.current?.click();\n } else if ((event.key === \"Tab\" || event.key === \"ArrowLeft\" || event.key === \"ArrowRight\") && groupContext) {\n event.preventDefault();\n\n queueMicrotask(() => {\n const columns = groupContext.getColumns();\n\n if (columns.length === 0) return;\n\n const currentColumnIndex = columns.findIndex((c) => c.ref.current?.contains(itemRef.current) ?? false);\n\n if (currentColumnIndex === -1) return;\n\n const goToPrevious = event.key === \"ArrowLeft\" || (event.key === \"Tab\" && event.shiftKey);\n\n const nextColumnIndex = goToPrevious\n ? currentColumnIndex > 0\n ? currentColumnIndex - 1\n : columns.length - 1\n : currentColumnIndex < columns.length - 1\n ? currentColumnIndex + 1\n : 0;\n\n const nextColumn = columns[nextColumnIndex];\n if (nextColumn?.ref.current) {\n const items = nextColumn.getItems();\n const selectedItem = items.find((item) => item.selected);\n\n const candidateRefs = selectedItem\n ? [selectedItem.ref, ...items.map((item) => item.ref)]\n : items.map((item) => item.ref);\n\n focusFirst(candidateRefs, false);\n }\n });\n }\n },\n [itemProps.onKeyDown, columnContext, groupContext, value]\n );\n\n const formattedValue =\n typeof value === \"number\" && format === \"2-digit\" ? value.toString().padStart(2, \"0\") : value.toString();\n\n return (\n <button\n type=\"button\"\n // Xem chú thích ở `TimePickerColumn`: mục là `option`, trạng thái chọn đi qua `aria-selected`.\n role=\"option\"\n aria-selected={selected}\n {...itemProps}\n ref={composedRef}\n data-selected={selected ? \"\" : undefined}\n className={cn(\n /*\n * ⚠ Khác thượng nguồn: focus đi theo khuôn `Checkbox`/`Calendar` của gói (`focus-visible`,\n * có offset — mục đang chọn tô nền vàng, quầng vàng dính sát nền vàng thì không thấy);\n * mục đang chọn dùng cặp token của control BẬT `--control-on` / `--control-check` thay\n * `bg-primary text-primary-foreground` — cùng lý do và số đo với ô ngày đang chọn của\n * `Calendar` (chú thích đầu `calendar.tsx`). Hover chỉ áp cho mục CHƯA chọn\n * (`not-data-selected:`) thay vì để `data-selected:hover:` ghi đè lại: cùng kết quả trên\n * màn hình, nhưng cách cũ khiến `pnpm lint:a11y` ghép chữ hover `--accent-foreground`\n * với nền mục đang chọn (1,39:1 ở dark) — một cặp không bao giờ xuất hiện.\n */\n \"w-full rounded px-3 py-1.5 text-left text-sm not-data-selected:hover:bg-accent not-data-selected:hover:text-accent-foreground focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring/50 focus-visible:ring-offset-2 focus-visible:ring-offset-background\",\n \"data-selected:bg-control-on data-selected:text-control-check\",\n className\n )}\n onClick={onClick}\n onKeyDown={onKeyDown}\n >\n {/* ⚠ Khác thượng nguồn: nhận `children` (cột buổi in `labels.am`/`labels.pm` thay mã \"AM\"/\"PM\"). */}\n {children ?? formattedValue}\n </button>\n );\n}\n\ninterface TimePickerHourProps extends DivProps {\n format?: SegmentFormat;\n}\n\nfunction TimePickerHour(props: TimePickerHourProps) {\n const { asChild, format = \"numeric\", className, ...hourProps } = props;\n\n const { is12Hour, hourStep, showSeconds, disabled, readOnly, labels } = useTimePickerContext(HOUR_NAME);\n const store = useStoreContext(HOUR_NAME);\n\n const value = useStore((state) => state.value);\n const timeValue = parseTimeString(value);\n\n const hours = Array.from(\n {\n length: is12Hour ? Math.ceil(12 / hourStep) : Math.ceil(24 / hourStep)\n },\n (_, i) => {\n if (is12Hour) {\n const hour = (i * hourStep) % 12;\n return hour === 0 ? 12 : hour;\n }\n return i * hourStep;\n }\n );\n\n const onHourSelect = React.useCallback(\n (displayHour: number) => {\n /*\n * ⚠ Khác thượng nguồn: bản gốc cho cột đổi giá trị cả khi `readOnly`/`disabled` — bảng chọn\n * vẫn mở được (nút mở chỉ khoá theo `disabled`, `openOnFocus` không xét gì), nên một ô\n * \"chỉ đọc\" vẫn sửa được bằng chuột. `TimePickerClear` của chính nó đã chặn đúng hai cờ\n * này; bốn cột nay chặn theo cùng luật.\n */\n if (disabled || readOnly) return;\n\n const now = new Date();\n const currentTime = timeValue ?? {};\n\n let hour24 = displayHour;\n if (is12Hour) {\n let currentPeriod: Period;\n if (timeValue?.period !== undefined) {\n currentPeriod = timeValue.period;\n } else if (timeValue?.hour !== undefined) {\n currentPeriod = to12Hour(timeValue.hour).period;\n } else {\n currentPeriod = to12Hour(now.getHours()).period;\n }\n hour24 = to24Hour(displayHour, currentPeriod);\n }\n\n const newTime = { ...currentTime, hour: hour24 };\n if (timeValue && timeValue.period !== undefined) {\n newTime.period = timeValue.period;\n }\n\n if (newTime.minute === undefined) {\n newTime.minute = now.getMinutes();\n }\n\n if (showSeconds && newTime.second === undefined) {\n newTime.second = now.getSeconds();\n }\n\n const newValue = formatTimeValue(newTime, showSeconds);\n store.setState(\"value\", newValue);\n },\n [timeValue, showSeconds, is12Hour, disabled, readOnly, store]\n );\n\n const now = new Date();\n const referenceHour = timeValue?.hour ?? now.getHours();\n const displayHour = is12Hour ? to12Hour(referenceHour).hour : referenceHour;\n\n const HourPrimitive = asChild ? Slot : TimePickerColumn;\n\n return (\n <HourPrimitive\n data-slot=\"time-picker-hour\"\n aria-label={labels.hour}\n {...hourProps}\n className={cn(\"scrollbar-none flex max-h-[200px] flex-col gap-1 overflow-y-auto p-1\", className)}\n >\n {hours.map((hour) => (\n <TimePickerColumnItem\n key={hour}\n value={hour}\n selected={displayHour === hour}\n format={format}\n onClick={() => onHourSelect(hour)}\n />\n ))}\n </HourPrimitive>\n );\n}\n\ninterface TimePickerMinuteProps extends DivProps {\n format?: SegmentFormat;\n}\n\nfunction TimePickerMinute(props: TimePickerMinuteProps) {\n const { asChild, format = \"2-digit\", className, ...minuteProps } = props;\n\n const { minuteStep, showSeconds, disabled, readOnly, labels } = useTimePickerContext(MINUTE_NAME);\n const store = useStoreContext(MINUTE_NAME);\n\n const value = useStore((state) => state.value);\n const timeValue = parseTimeString(value);\n\n const minutes = Array.from({ length: Math.ceil(60 / minuteStep) }, (_, i) => i * minuteStep);\n\n const onMinuteSelect = React.useCallback(\n (minute: number) => {\n // Chặn `readOnly`/`disabled` — xem `TimePickerHour`.\n if (disabled || readOnly) return;\n\n const now = new Date();\n const currentTime = timeValue ?? {};\n const newTime = { ...currentTime, minute };\n\n if (newTime.hour === undefined) {\n newTime.hour = now.getHours();\n }\n\n if (showSeconds && newTime.second === undefined) {\n newTime.second = now.getSeconds();\n }\n\n const newValue = formatTimeValue(newTime, showSeconds);\n store.setState(\"value\", newValue);\n },\n [timeValue, showSeconds, disabled, readOnly, store]\n );\n\n const MinutePrimitive = asChild ? Slot : TimePickerColumn;\n\n const now = new Date();\n const referenceMinute = timeValue?.minute ?? now.getMinutes();\n\n return (\n <MinutePrimitive\n data-slot=\"time-picker-minute\"\n aria-label={labels.minute}\n {...minuteProps}\n className={cn(\"scrollbar-none flex max-h-[200px] flex-col gap-1 overflow-y-auto p-1\", className)}\n >\n {minutes.map((minute) => (\n <TimePickerColumnItem\n key={minute}\n value={minute}\n selected={referenceMinute === minute}\n format={format}\n onClick={() => onMinuteSelect(minute)}\n />\n ))}\n </MinutePrimitive>\n );\n}\n\ninterface TimePickerSecondProps extends DivProps {\n format?: SegmentFormat;\n}\n\nfunction TimePickerSecond(props: TimePickerSecondProps) {\n const { asChild, format = \"2-digit\", className, ...secondProps } = props;\n\n const { secondStep, disabled, readOnly, labels } = useTimePickerContext(SECOND_NAME);\n const store = useStoreContext(SECOND_NAME);\n\n const value = useStore((state) => state.value);\n const timeValue = parseTimeString(value);\n\n const seconds = Array.from({ length: Math.ceil(60 / secondStep) }, (_, i) => i * secondStep);\n\n const onSecondSelect = React.useCallback(\n (second: number) => {\n // Chặn `readOnly`/`disabled` — xem `TimePickerHour`.\n if (disabled || readOnly) return;\n\n const now = new Date();\n const currentTime = timeValue ?? {};\n const newTime = { ...currentTime, second };\n\n if (newTime.hour === undefined) {\n newTime.hour = now.getHours();\n }\n\n if (newTime.minute === undefined) {\n newTime.minute = now.getMinutes();\n }\n\n const newValue = formatTimeValue(newTime, true);\n store.setState(\"value\", newValue);\n },\n [timeValue, disabled, readOnly, store]\n );\n\n const SecondPrimitive = asChild ? Slot : TimePickerColumn;\n\n const now = new Date();\n const referenceSecond = timeValue?.second ?? now.getSeconds();\n\n return (\n <SecondPrimitive\n data-slot=\"time-picker-second\"\n aria-label={labels.second}\n {...secondProps}\n className={cn(\"scrollbar-none flex max-h-[200px] flex-col gap-1 overflow-y-auto p-1\", className)}\n >\n {seconds.map((second) => (\n <TimePickerColumnItem\n key={second}\n value={second}\n selected={referenceSecond === second}\n format={format}\n onClick={() => onSecondSelect(second)}\n />\n ))}\n </SecondPrimitive>\n );\n}\n\ntype TimePickerPeriodProps = DivProps;\n\nfunction TimePickerPeriod(props: TimePickerPeriodProps) {\n const { asChild, className, ...periodProps } = props;\n\n const { is12Hour, showSeconds, disabled, readOnly, labels } = useTimePickerContext(PERIOD_NAME);\n const store = useStoreContext(PERIOD_NAME);\n\n const value = useStore((state) => state.value);\n const timeValue = parseTimeString(value);\n\n const onPeriodToggle = React.useCallback(\n (period: Period) => {\n // Chặn `readOnly`/`disabled` — xem `TimePickerHour`.\n if (disabled || readOnly) return;\n\n const now = new Date();\n const currentTime = timeValue ?? {};\n\n const currentHour = currentTime.hour !== undefined ? currentTime.hour : now.getHours();\n const currentDisplay = to12Hour(currentHour);\n const new24Hour = to24Hour(currentDisplay.hour, period);\n\n const newTime = { ...currentTime, hour: new24Hour };\n\n if (newTime.minute === undefined) {\n newTime.minute = now.getMinutes();\n }\n\n if (showSeconds && newTime.second === undefined) {\n newTime.second = now.getSeconds();\n }\n\n const newValue = formatTimeValue(newTime, showSeconds);\n store.setState(\"value\", newValue);\n },\n [timeValue, showSeconds, disabled, readOnly, store]\n );\n\n if (!is12Hour) return null;\n\n const now = new Date();\n const referenceHour = timeValue?.hour ?? now.getHours();\n const currentPeriod = to12Hour(referenceHour).period;\n\n const PeriodPrimitive = asChild ? Slot : TimePickerColumn;\n\n return (\n <PeriodPrimitive\n data-slot=\"time-picker-period\"\n aria-label={labels.period}\n {...periodProps}\n className={cn(\"flex flex-col gap-1 p-1\", className)}\n >\n {PERIODS.map((period) => (\n <TimePickerColumnItem\n key={period}\n value={period}\n selected={currentPeriod === period}\n onClick={() => onPeriodToggle(period)}\n >\n {getPeriodLabel(period, labels)}\n </TimePickerColumnItem>\n ))}\n </PeriodPrimitive>\n );\n}\n\ninterface TimePickerSeparatorProps extends React.ComponentProps<\"span\"> {\n asChild?: boolean;\n}\n\nfunction TimePickerSeparator(props: TimePickerSeparatorProps) {\n const { asChild, children, ...separatorProps } = props;\n\n const SeparatorPrimitive = asChild ? Slot : \"span\";\n\n return (\n <SeparatorPrimitive aria-hidden=\"true\" data-slot=\"time-picker-separator\" {...separatorProps}>\n {children ?? \":\"}\n </SeparatorPrimitive>\n );\n}\n\ntype TimePickerClearProps = ButtonProps;\n\nfunction TimePickerClear(props: TimePickerClearProps) {\n const { asChild, className, children, disabled: disabledProp, ...clearProps } = props;\n\n const { disabled, readOnly, labels } = useTimePickerContext(CLEAR_NAME);\n const store = useStoreContext(CLEAR_NAME);\n\n const isDisabled = disabledProp || disabled;\n\n const onClick = React.useCallback(\n (event: React.MouseEvent<HTMLButtonElement>) => {\n clearProps.onClick?.(event);\n if (event.defaultPrevented) return;\n\n event.preventDefault();\n if (disabled || readOnly) return;\n store.setState(\"value\", \"\");\n },\n [clearProps.onClick, disabled, readOnly, store]\n );\n\n const ClearPrimitive = asChild ? Slot : \"button\";\n\n return (\n <ClearPrimitive\n type=\"button\"\n data-slot=\"time-picker-clear\"\n disabled={isDisabled}\n {...clearProps}\n className={cn(\n // Viền focus theo khuôn `Button` — xem `TimePickerTrigger`.\n \"inline-flex items-center justify-center rounded-sm text-sm font-medium transition-colors hover:bg-accent hover:text-accent-foreground focus-visible:outline-2 focus-visible:outline-ring focus-visible:outline-offset-2 disabled:pointer-events-none disabled:opacity-50\",\n className\n )}\n onClick={onClick}\n >\n {children ?? labels.clear}\n </ClearPrimitive>\n );\n}\n\nexport {\n TimePicker,\n TimePickerClear,\n type TimePickerClearProps,\n TimePickerContent,\n type TimePickerContentProps,\n TimePickerHour,\n type TimePickerHourProps,\n TimePickerInput,\n TimePickerInputGroup,\n type TimePickerInputGroupProps,\n type TimePickerInputProps,\n TimePickerLabel,\n type TimePickerLabelProps,\n TimePickerMinute,\n type TimePickerMinuteProps,\n TimePickerPeriod,\n type TimePickerPeriodProps,\n type TimePickerProps,\n TimePickerSecond,\n type TimePickerSecondProps,\n TimePickerSeparator,\n type TimePickerSeparatorProps,\n TimePickerTrigger,\n type TimePickerTriggerProps,\n useStore as useTimePicker\n};\n"],"mappings":"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","names":["value","ref","displayHour","now"]}
1
+ {"version":3,"sources":["../../../src/components/ui/time-picker.tsx"],"sourcesContent":["\"use client\";\n\n/*\n * Port từ Dice UI (https://diceui.com/docs/components/time-picker) — MIT, © 2024 Sadman Sakib.\n * Giữ nguyên cấu trúc thượng nguồn để còn đối chiếu ngược được; mọi chỗ đổi đều có chú thích.\n */\n\nimport { Slot } from \"@radix-ui/react-slot\";\nimport { Clock } from \"lucide-react\";\nimport * as React from \"react\";\nimport { useComitorLabels, useComitorLocale } from \"../../i18n/locale-provider.js\";\nimport { cn } from \"../../lib/cn.js\";\nimport { useComposedRefs } from \"../../lib/compose-refs.js\";\nimport { useAsRef } from \"../../lib/use-as-ref.js\";\nimport { useIsomorphicLayoutEffect } from \"../../lib/use-isomorphic-layout-effect.js\";\nimport { useLazyRef } from \"../../lib/use-lazy-ref.js\";\nimport { VisuallyHiddenInput } from \"../../lib/visually-hidden-input.js\";\nimport { Popover, PopoverAnchor, PopoverContent, PopoverTrigger } from \"./popover.js\";\nimport type { TimePickerLabels } from \"./time-picker-constants.js\";\n\nconst ROOT_NAME = \"TimePicker\";\nconst LABEL_NAME = \"TimePickerLabel\";\nconst INPUT_GROUP_NAME = \"TimePickerInputGroup\";\nconst INPUT_NAME = \"TimePickerInput\";\nconst TRIGGER_NAME = \"TimePickerTrigger\";\nconst CONTENT_NAME = \"TimePickerContent\";\nconst COLUMN_NAME = \"TimePickerColumn\";\nconst COLUMN_ITEM_NAME = \"TimePickerColumnItem\";\nconst HOUR_NAME = \"TimePickerHour\";\nconst MINUTE_NAME = \"TimePickerMinute\";\nconst SECOND_NAME = \"TimePickerSecond\";\nconst PERIOD_NAME = \"TimePickerPeriod\";\nconst CLEAR_NAME = \"TimePickerClear\";\n\nconst DEFAULT_STEP = 1;\nconst DEFAULT_SEGMENT_PLACEHOLDER = \"--\";\nconst SEGMENTS: Segment[] = [\"hour\", \"minute\", \"second\", \"period\"];\nconst PERIODS = [\"AM\", \"PM\"] as const;\n\ntype Segment = \"hour\" | \"minute\" | \"second\" | \"period\";\ntype SegmentFormat = \"numeric\" | \"2-digit\";\ntype Period = (typeof PERIODS)[number];\n\ninterface DivProps extends React.ComponentProps<\"div\"> {\n asChild?: boolean;\n}\n\ninterface ButtonProps extends React.ComponentProps<\"button\"> {\n asChild?: boolean;\n}\n\ntype PopoverContentProps = React.ComponentProps<typeof PopoverContent>;\n\ntype InputGroupElement = React.ComponentRef<typeof TimePickerInputGroup>;\ntype InputElement = React.ComponentRef<typeof TimePickerInput>;\ntype TriggerElement = React.ComponentRef<typeof TimePickerTrigger>;\ntype ColumnElement = React.ComponentRef<typeof TimePickerColumn>;\ntype ColumnItemElement = React.ComponentRef<typeof TimePickerColumnItem>;\n\ninterface TimeValue {\n hour?: number;\n minute?: number;\n second?: number;\n period?: Period;\n}\n\ninterface ItemData {\n value: number | string;\n ref: React.RefObject<ColumnItemElement | null>;\n selected: boolean;\n /** Bị khoá theo `min`/`max` (3.1.0) — xem `isSegmentAllowed`. */\n disabled: boolean;\n}\n\ninterface ColumnData {\n id: string;\n ref: React.RefObject<ColumnElement | null>;\n getSelectedItemRef: () => React.RefObject<ColumnItemElement | null> | null;\n getItems: () => ItemData[];\n}\n\nfunction focusFirst(candidates: React.RefObject<ColumnItemElement | null>[], preventScroll = false) {\n const PREVIOUSLY_FOCUSED_ELEMENT = document.activeElement;\n for (const candidateRef of candidates) {\n const candidate = candidateRef.current;\n if (!candidate) continue;\n if (candidate === PREVIOUSLY_FOCUSED_ELEMENT) return;\n candidate.focus({ preventScroll });\n if (document.activeElement !== PREVIOUSLY_FOCUSED_ELEMENT) return;\n }\n}\n\nfunction sortNodes<T extends { ref: React.RefObject<Element | null> }>(items: T[]): T[] {\n return items.sort((a, b) => {\n const elementA = a.ref.current;\n const elementB = b.ref.current;\n if (!elementA || !elementB) return 0;\n const position = elementA.compareDocumentPosition(elementB);\n if (position & Node.DOCUMENT_POSITION_FOLLOWING) {\n return -1;\n }\n if (position & Node.DOCUMENT_POSITION_PRECEDING) {\n return 1;\n }\n return 0;\n });\n}\n\nfunction getIs12Hour(locale?: string): boolean {\n const testDate = new Date(2000, 0, 1, 13, 0, 0);\n const formatted = new Intl.DateTimeFormat(locale, {\n hour: \"numeric\"\n }).format(testDate);\n\n return /am|pm/i.test(formatted) || !formatted.includes(\"13\");\n}\n\nfunction parseTimeString(timeString: string | undefined): TimeValue | null {\n if (!timeString) return null;\n\n const parts = timeString.split(\":\");\n if (parts.length < 2) return null;\n\n const result: TimeValue = {};\n\n if (parts[0] && parts[0] !== DEFAULT_SEGMENT_PLACEHOLDER) {\n const hour = Number.parseInt(parts[0], 10);\n if (!Number.isNaN(hour) && hour >= 0 && hour <= 23) {\n result.hour = hour;\n }\n }\n\n if (parts[1] && parts[1] !== DEFAULT_SEGMENT_PLACEHOLDER) {\n const minute = Number.parseInt(parts[1], 10);\n if (!Number.isNaN(minute) && minute >= 0 && minute <= 59) {\n result.minute = minute;\n }\n }\n\n if (parts[2] && parts[2] !== DEFAULT_SEGMENT_PLACEHOLDER) {\n const second = Number.parseInt(parts[2], 10);\n if (!Number.isNaN(second) && second >= 0 && second <= 59) {\n result.second = second;\n }\n }\n if (result.hour === undefined && result.minute === undefined && result.second === undefined) {\n return null;\n }\n\n return result;\n}\n\nfunction formatTimeValue(value: TimeValue, showSeconds: boolean): string {\n const hourStr = value.hour !== undefined ? value.hour.toString().padStart(2, \"0\") : DEFAULT_SEGMENT_PLACEHOLDER;\n const minuteStr = value.minute !== undefined ? value.minute.toString().padStart(2, \"0\") : DEFAULT_SEGMENT_PLACEHOLDER;\n const secondStr = value.second !== undefined ? value.second.toString().padStart(2, \"0\") : DEFAULT_SEGMENT_PLACEHOLDER;\n\n if (showSeconds) {\n return `${hourStr}:${minuteStr}:${secondStr}`;\n }\n return `${hourStr}:${minuteStr}`;\n}\n\nfunction to12Hour(hour24: number): { hour: number; period: Period } {\n const period: Period = hour24 >= 12 ? \"PM\" : \"AM\";\n const hour = hour24 % 12 || 12;\n return { hour, period };\n}\n\nfunction to24Hour(hour12: number, period: Period): number {\n if (hour12 === 12) {\n return period === \"PM\" ? 12 : 0;\n }\n return period === \"PM\" ? hour12 + 12 : hour12;\n}\n\nfunction clamp(value: number, min: number, max: number) {\n return Math.min(Math.max(value, min), max);\n}\n\n/*\n * ⚠ Khác thượng nguồn: bản gốc in thẳng mã buổi \"AM\"/\"PM\" ra ô và ra cột. Ở đây mã buổi vẫn là\n * thứ chạy trong state (`editValue`, `updateTimeValue`) — chỉ lúc VẼ mới đổi sang nhãn hiển thị\n * (`labels.am`/`labels.pm` — \"AM\"/\"PM\" ở tiếng Anh, \"SA\"/\"CH\" ở tiếng Việt), nên logic bàn phím\n * của thượng nguồn giữ nguyên.\n */\nfunction getPeriodLabel(value: string, labels: Pick<TimePickerLabels, \"am\" | \"pm\">): string {\n if (value === \"AM\") return labels.am;\n if (value === \"PM\") return labels.pm;\n return value;\n}\n\n/*\n * ⚠ Khác thượng nguồn: bản gốc chỉ nhận `A`/`1` → AM và `P`/`2` → PM (viết thẳng ở hai chỗ).\n * Nhãn tiếng Việt là \"SA\"/\"CH\" thì người dùng sẽ gõ `S`/`C`, nên ký tự đầu của nhãn cũng là phím\n * tắt. Phím của thượng nguồn được xét TRƯỚC và vẫn chạy.\n */\nfunction getPeriodFromKey(key: string, labels: Pick<TimePickerLabels, \"am\" | \"pm\">): Period | null {\n const lowerKey = key.toLowerCase();\n if (lowerKey === \"a\" || lowerKey === \"1\") return \"AM\";\n if (lowerKey === \"p\" || lowerKey === \"2\") return \"PM\";\n if (lowerKey.length !== 1) return null;\n if (lowerKey === labels.am.charAt(0).toLowerCase()) return \"AM\";\n if (lowerKey === labels.pm.charAt(0).toLowerCase()) return \"PM\";\n return null;\n}\n\n/*\n * ⚠ Khác thượng nguồn (3.1.0): `min`/`max` được ÁP DỤNG — thượng nguồn chỉ lưu hai prop này vào\n * context. Toàn bộ luật nằm ở khối hàm thuần dưới đây (JSDoc của prop `min` tóm tắt cho app). Mọi phép\n * so tính bằng GIÂY kể từ 00:00:00. Không hiện giây thì giây của giá trị bị bỏ qua và cận có giây làm\n * tròn VÀO TRONG tới phút (`min` lên, `max` xuống): giá trị nào ghi ra được cũng thật sự nằm trong\n * khung, ở đúng độ chính xác của chính nó.\n */\n\nconst SECONDS_PER_HOUR = 3600;\nconst SECONDS_PER_HALF_DAY = 43_200;\nconst LAST_SECOND_OF_DAY = 86_399;\nconst LAST_MINUTE_OF_DAY = LAST_SECOND_OF_DAY - 59;\n\ninterface TimeRange {\n /** Cận dưới, giây kể từ 00:00:00. */\n min: number;\n /** Cận trên, giây kể từ 00:00:00. */\n max: number;\n /** `min` > `max`: khung VẮT QUA NỬA ĐÊM (ca đêm 22:00 → 06:00) — cùng luật với `<input type=\"time\">`. */\n wraps: boolean;\n}\n\ninterface ClockTime {\n hour: number;\n minute: number;\n second: number;\n}\n\nfunction toSeconds(time: TimeValue, showSeconds: boolean): number {\n return (time.hour ?? 0) * SECONDS_PER_HOUR + (time.minute ?? 0) * 60 + (showSeconds ? (time.second ?? 0) : 0);\n}\n\nfunction fromSeconds(seconds: number): ClockTime {\n return {\n hour: Math.floor(seconds / SECONDS_PER_HOUR),\n minute: Math.floor((seconds % SECONDS_PER_HOUR) / 60),\n second: seconds % 60\n };\n}\n\n/** Cận không đọc được (thiếu giờ hay phút, sai định dạng) coi như không đặt. */\nfunction parseTimeBound(bound: string | undefined): number | null {\n const time = parseTimeString(bound);\n if (!time || time.hour === undefined || time.minute === undefined) return null;\n return toSeconds(time, true);\n}\n\nfunction getTimeRange(min: string | undefined, max: string | undefined, showSeconds: boolean): TimeRange | null {\n const lower = parseTimeBound(min);\n const upper = parseTimeBound(max);\n if (lower === null && upper === null) return null;\n\n const range: TimeRange = { min: lower ?? 0, max: upper ?? LAST_SECOND_OF_DAY, wraps: false };\n range.wraps = range.min > range.max;\n\n if (!showSeconds) {\n range.min = Math.min(Math.ceil(range.min / 60) * 60, LAST_MINUTE_OF_DAY);\n range.max = Math.floor(range.max / 60) * 60;\n // Khung hẹp hơn một phút (vd 09:30:10–09:30:50) thì làm tròn ra khung rỗng → giữ phút của cận trên.\n if (!range.wraps && range.min > range.max) range.min = range.max;\n }\n\n return range;\n}\n\n/**\n * Thời điểm ĐƯỢC PHÉP gần `seconds` nhất, chỉ tìm trong [from, to]; `null` khi đoạn đó không có thời\n * điểm nào được phép.\n */\nfunction findNearestAllowed(seconds: number, range: TimeRange, from = 0, to = LAST_SECOND_OF_DAY): number | null {\n const intervals: [number, number][] = range.wraps\n ? [\n [0, range.max],\n [range.min, LAST_SECOND_OF_DAY]\n ]\n : [[range.min, range.max]];\n\n let nearest: number | null = null;\n for (const [start, end] of intervals) {\n const low = Math.max(start, from);\n const high = Math.min(end, to);\n if (low > high) continue;\n const candidate = clamp(seconds, low, high);\n if (nearest === null || Math.abs(candidate - seconds) < Math.abs(nearest - seconds)) {\n nearest = candidate;\n }\n }\n return nearest;\n}\n\n/**\n * Đoạn giây mà ô `segment` của `time` bao trùm: buổi → nửa ngày, giờ → cả 60 phút của nó, phút → cả\n * 60 giây của nó (không hiện giây thì ô giây cũng vậy), giây → đúng thời điểm đó.\n */\nfunction getSegmentSpan(time: TimeValue, segment: Segment, showSeconds: boolean): [number, number] | null {\n if (time.hour === undefined) return null;\n const hourStart = time.hour * SECONDS_PER_HOUR;\n\n if (segment === \"period\") {\n const halfDayStart = time.hour < 12 ? 0 : SECONDS_PER_HALF_DAY;\n return [halfDayStart, halfDayStart + SECONDS_PER_HALF_DAY - 1];\n }\n if (segment === \"hour\") return [hourStart, hourStart + SECONDS_PER_HOUR - 1];\n\n if (time.minute === undefined) return null;\n const minuteStart = hourStart + time.minute * 60;\n if (segment === \"minute\" || !showSeconds) return [minuteStart, minuteStart + 59];\n\n if (time.second === undefined) return null;\n return [minuteStart + time.second, minuteStart + time.second];\n}\n\n/**\n * Mục `segment` của `time` còn thời điểm nào được phép không. Mục của cột bị khoá khi KHÔNG còn — tức\n * xét các ô LỚN hơn đang chọn (buổi → giờ → phút), không xét các ô nhỏ hơn: những ô đó được kẹp lúc ghi\n * (`constrainTime`). Xét theo cả ô nhỏ hơn thì có ngõ cụt: đồng hồ 12 giờ, khung 09:00–17:00, đang\n * 10:30 SA — CH ra 22:30, 12 SA…8 SA ra 00:30…08:30, không đường nào sang buổi chiều.\n */\nfunction isSegmentAllowed(time: TimeValue, segment: Segment, range: TimeRange | null, showSeconds: boolean): boolean {\n if (!range) return true;\n const span = getSegmentSpan(time, segment, showSeconds);\n return !span || findNearestAllowed(span[0], range, span[0], span[1]) !== null;\n}\n\n/**\n * Thời điểm sẽ GHI thay cho `time`. Trong khung → chính `time` (cùng object). Ngoài khung → thời điểm\n * được phép GẦN NHẤT, ưu tiên trong đoạn của ô `keep` — thứ người dùng vừa chọn/gõ (max 17:00, đang\n * 09:45, chọn giờ 17 → 17:00: giờ vẫn là 17). Ô đó không còn thời điểm nào được phép thì là cận gần\n * nhất (gõ giờ 20 với max 17:00 → 17:00).\n *\n * Giá trị THIẾU ô (khoảnh khắc giữa lúc gõ xong giờ và lúc ô phút trống được lấp, hay sau khi xoá một\n * ô) chưa phải một thời điểm: giữ nguyên — trừ khi riêng giờ đã loại mọi thời điểm được phép.\n */\nfunction constrainTime(time: TimeValue, range: TimeRange | null, showSeconds: boolean, keep?: Segment): TimeValue {\n if (!range || time.hour === undefined) return time;\n\n const seconds = toSeconds(time, showSeconds);\n const isComplete = time.minute !== undefined && (!showSeconds || time.second !== undefined);\n\n if (isComplete) {\n if (findNearestAllowed(seconds, range, seconds, seconds) !== null) return time;\n } else {\n const hourStart = time.hour * SECONDS_PER_HOUR;\n if (findNearestAllowed(hourStart, range, hourStart, hourStart + SECONDS_PER_HOUR - 1) !== null) return time;\n }\n\n const span = keep && isComplete ? getSegmentSpan(time, keep, showSeconds) : null;\n const nearest =\n (span && findNearestAllowed(seconds, range, span[0], span[1])) ?? findNearestAllowed(seconds, range) ?? seconds;\n return fromSeconds(nearest);\n}\n\n/**\n * \"Bây giờ\" — thứ thượng nguồn dùng để LẤP ô trống và làm mục \"đang chọn\" của cột khi chưa có giá trị\n * — nhưng KẸP vào khung khi có `min`/`max`: ô được lấp không đẩy giá trị ra ngoài khung, và cột không mở\n * ra ở một mục bị khoá. Không có khung thì đúng là `new Date()` như bản gốc.\n */\nfunction getReferenceTime(range: TimeRange | null, showSeconds: boolean): ClockTime {\n const now = new Date();\n const time: ClockTime = { hour: now.getHours(), minute: now.getMinutes(), second: now.getSeconds() };\n if (!range) return time;\n const seconds = toSeconds(time, showSeconds);\n const nearest = findNearestAllowed(seconds, range);\n return nearest === null || nearest === seconds ? time : fromSeconds(nearest);\n}\n\n/*\n * ⚠ Khác thượng nguồn (3.1.0): bốn hàm dưới đây là THÂN của `onHourSelect` / `onMinuteSelect` /\n * `onSecondSelect` / `onPeriodToggle` của bản gốc, tách ra nguyên văn (chỉ thay `new Date()` bằng\n * `reference` — xem `getReferenceTime`) để cùng MỘT phép dựng vừa quyết mục nào bị khoá, vừa là thứ\n * được ghi khi chọn mục đó.\n */\n\nfunction buildHourTime(\n timeValue: TimeValue | null,\n displayHour: number,\n is12Hour: boolean,\n showSeconds: boolean,\n reference: ClockTime\n): TimeValue {\n const currentTime = timeValue ?? {};\n\n let hour24 = displayHour;\n if (is12Hour) {\n let currentPeriod: Period;\n if (timeValue?.period !== undefined) {\n currentPeriod = timeValue.period;\n } else if (timeValue?.hour !== undefined) {\n currentPeriod = to12Hour(timeValue.hour).period;\n } else {\n currentPeriod = to12Hour(reference.hour).period;\n }\n hour24 = to24Hour(displayHour, currentPeriod);\n }\n\n const newTime = { ...currentTime, hour: hour24 };\n if (timeValue && timeValue.period !== undefined) {\n newTime.period = timeValue.period;\n }\n\n if (newTime.minute === undefined) {\n newTime.minute = reference.minute;\n }\n\n if (showSeconds && newTime.second === undefined) {\n newTime.second = reference.second;\n }\n\n return newTime;\n}\n\nfunction buildMinuteTime(\n timeValue: TimeValue | null,\n minute: number,\n showSeconds: boolean,\n reference: ClockTime\n): TimeValue {\n const currentTime = timeValue ?? {};\n const newTime = { ...currentTime, minute };\n\n if (newTime.hour === undefined) {\n newTime.hour = reference.hour;\n }\n\n if (showSeconds && newTime.second === undefined) {\n newTime.second = reference.second;\n }\n\n return newTime;\n}\n\nfunction buildSecondTime(timeValue: TimeValue | null, second: number, reference: ClockTime): TimeValue {\n const currentTime = timeValue ?? {};\n const newTime = { ...currentTime, second };\n\n if (newTime.hour === undefined) {\n newTime.hour = reference.hour;\n }\n\n if (newTime.minute === undefined) {\n newTime.minute = reference.minute;\n }\n\n return newTime;\n}\n\nfunction buildPeriodTime(\n timeValue: TimeValue | null,\n period: Period,\n showSeconds: boolean,\n reference: ClockTime\n): TimeValue {\n const currentTime = timeValue ?? {};\n\n const currentHour = currentTime.hour !== undefined ? currentTime.hour : reference.hour;\n const currentDisplay = to12Hour(currentHour);\n const new24Hour = to24Hour(currentDisplay.hour, period);\n\n const newTime = { ...currentTime, hour: new24Hour };\n\n if (newTime.minute === undefined) {\n newTime.minute = reference.minute;\n }\n\n if (showSeconds && newTime.second === undefined) {\n newTime.second = reference.second;\n }\n\n return newTime;\n}\n\n/**\n * Mục ĐÓN focus khi đi vào một cột — bằng Tab, mũi tên trái/phải, hay lúc mở bảng chọn — và là mục\n * DUY NHẤT của cột có `tabIndex={0}`: mục đang chọn → mục đầu tiên không bị khoá → mục đang chọn dù bị\n * khoá → mục đầu.\n */\nfunction getColumnEntry<T extends { selected: boolean; disabled: boolean }>(items: T[]): T | undefined {\n return (\n items.find((item) => item.selected && !item.disabled) ??\n items.find((item) => !item.disabled) ??\n items.find((item) => item.selected) ??\n items[0]\n );\n}\n\n/** Ứng viên cho `focusFirst` khi đi vào một cột: mục đón trước, rồi mọi mục (như bản gốc). */\nfunction getColumnEntryRefs(items: ItemData[]): React.RefObject<ColumnItemElement | null>[] {\n const entry = getColumnEntry(items);\n const refs = items.map((item) => item.ref);\n return entry ? [entry.ref, ...refs] : refs;\n}\n\nfunction isHiddenWithin(element: HTMLElement, container: HTMLElement): boolean {\n if (getComputedStyle(element).visibility === \"hidden\") return true;\n for (let node: HTMLElement | null = element; node && node !== container; node = node.parentElement) {\n if (getComputedStyle(node).display === \"none\") return true;\n }\n return false;\n}\n\n/**\n * Phần tử nhận Tab được bên trong `container`, theo thứ tự DOM — cùng luật với `FocusScope` của Radix,\n * thứ lo vòng Tab của `PopoverContent` (vd `tabIndex` ≥ 0, không `disabled`, không bị ẩn).\n */\nfunction getTabbableElements(container: HTMLElement): HTMLElement[] {\n const elements: HTMLElement[] = [];\n const walker = document.createTreeWalker(container, NodeFilter.SHOW_ELEMENT, {\n acceptNode: (node) => {\n const element = node as HTMLElement;\n const isHiddenInput = element instanceof HTMLInputElement && element.type === \"hidden\";\n if ((element as { disabled?: boolean }).disabled || element.hidden || isHiddenInput) {\n return NodeFilter.FILTER_SKIP;\n }\n return element.tabIndex >= 0 ? NodeFilter.FILTER_ACCEPT : NodeFilter.FILTER_SKIP;\n }\n });\n while (walker.nextNode()) elements.push(walker.currentNode as HTMLElement);\n return elements.filter((element) => !isHiddenWithin(element, container));\n}\n\n/**\n * Đích của Tab (Shift+Tab) từ một mục của `column`: phần tử nhận Tab được đứng NGAY SAU (ngay trước)\n * CẢ cột trong bảng chọn — cột kế, hay một nút như `TimePickerClear` đặt trong bảng. Hết thì vòng về\n * phần tử đầu (cuối) bảng, đúng như `FocusScope loop` của mọi popover trong gói. Neo vào CỘT chứ không\n * vào mục đang focus: mục đang focus có thể không phải mục mang `tabIndex={0}` (vd `readOnly` — mũi tên\n * vẫn di focus nhưng không chọn), và Tab gốc từ đó sẽ rơi vào mục đón của CHÍNH cột này.\n */\nfunction getTabTarget(content: HTMLElement, column: HTMLElement, backward: boolean): HTMLElement | undefined {\n const tabbables = getTabbableElements(content);\n const isOutsideColumn = (element: HTMLElement) => !column.contains(element);\n\n if (backward) {\n for (let index = tabbables.length - 1; index >= 0; index--) {\n const element = tabbables[index];\n if (\n element &&\n isOutsideColumn(element) &&\n (column.compareDocumentPosition(element) & Node.DOCUMENT_POSITION_PRECEDING) !== 0\n ) {\n return element;\n }\n }\n return tabbables[tabbables.length - 1];\n }\n\n return (\n tabbables.find(\n (element) =>\n isOutsideColumn(element) && (column.compareDocumentPosition(element) & Node.DOCUMENT_POSITION_FOLLOWING) !== 0\n ) ?? tabbables[0]\n );\n}\n\nfunction focusTabbable(element: HTMLElement) {\n element.focus();\n // Như Tab gốc (và `FocusScope`): vào một ô nhập thì chọn sẵn chữ trong đó.\n if (element instanceof HTMLInputElement) element.select();\n}\n\ninterface StoreState {\n value: string;\n open: boolean;\n openedViaFocus: boolean;\n}\n\ninterface Store {\n subscribe: (callback: () => void) => () => void;\n getState: () => StoreState;\n setState: <K extends keyof StoreState>(key: K, value: StoreState[K]) => void;\n notify: () => void;\n}\n\nconst StoreContext = React.createContext<Store | null>(null);\n\nfunction useStoreContext(consumerName: string) {\n const context = React.useContext(StoreContext);\n if (!context) {\n throw new Error(`\\`${consumerName}\\` phải nằm bên trong \\`${ROOT_NAME}\\``);\n }\n return context;\n}\n\nfunction useStore<T>(selector: (state: StoreState) => T, ogStore?: Store | null): T {\n const contextStore = React.useContext(StoreContext);\n\n const store = ogStore ?? contextStore;\n\n if (!store) {\n throw new Error(`\\`useTimePicker\\` phải được gọi bên trong \\`${ROOT_NAME}\\``);\n }\n\n const getSnapshot = React.useCallback(() => selector(store.getState()), [store, selector]);\n\n return React.useSyncExternalStore(store.subscribe, getSnapshot, getSnapshot);\n}\n\ntype SegmentPlaceholder =\n | string\n | {\n hour?: string;\n minute?: string;\n second?: string;\n period?: string;\n };\n\ninterface TimePickerContextValue {\n id: string;\n inputGroupId: string;\n labelId: string;\n triggerId: string;\n inputGroupRef: React.RefObject<InputGroupElement | null>;\n triggerRef: React.RefObject<TriggerElement | null>;\n openOnFocus: boolean;\n inputGroupClickAction: \"focus\" | \"open\";\n onInputGroupChange: (inputGroup: InputGroupElement | null) => void;\n disabled: boolean;\n readOnly: boolean;\n required: boolean;\n invalid: boolean;\n showSeconds: boolean;\n is12Hour: boolean;\n minuteStep: number;\n secondStep: number;\n hourStep: number;\n segmentPlaceholder: {\n hour: string;\n minute: string;\n second: string;\n period: string;\n };\n labels: TimePickerLabels;\n min?: string;\n max?: string;\n /** `min`/`max` đã đọc thành giây (3.1.0); `null` = không ràng buộc. */\n timeRange: TimeRange | null;\n}\n\nconst TimePickerContext = React.createContext<TimePickerContextValue | null>(null);\n\nfunction useTimePickerContext(consumerName: string) {\n const context = React.useContext(TimePickerContext);\n if (!context) {\n throw new Error(`\\`${consumerName}\\` phải nằm bên trong \\`${ROOT_NAME}\\``);\n }\n return context;\n}\n\ninterface TimePickerProps extends DivProps {\n /** Giá trị có kiểm soát, LUÔN ở dạng 24 giờ: `\"HH:mm\"` hoặc `\"HH:mm:ss\"` — bất kể đồng hồ hiển thị. */\n value?: string;\n /** Giá trị ban đầu (không kiểm soát), cùng định dạng với `value`. */\n defaultValue?: string;\n onValueChange?: (value: string) => void;\n open?: boolean;\n defaultOpen?: boolean;\n onOpenChange?: (open: boolean) => void;\n /** Mở bảng chọn ngay khi một ô được focus. Mặc định `false`. */\n openOnFocus?: boolean;\n /** Bấm vào khoảng trống của nhóm ô: `\"focus\"` (mặc định) focus ô đầu, `\"open\"` mở bảng chọn. */\n inputGroupClickAction?: \"focus\" | \"open\";\n /**\n * Khung giờ cho phép (từ `3.1.0`), cùng định dạng 24 giờ với `value`: `\"HH:mm\"` hoặc `\"HH:mm:ss\"`.\n * Chỉ đặt một đầu thì đầu kia là 00:00 / 23:59:59. `min` > `max` là khung VẮT QUA NỬA ĐÊM (ca đêm\n * `min=\"22:00\" max=\"06:00\"`), như `<input type=\"time\">`. Không `showSeconds` thì so tới PHÚT: cận\n * có giây được làm tròn vào trong (`min` lên, `max` xuống). Không đặt cả hai thì không có gì đổi.\n *\n * - **Mục bị khoá** trong bảng chọn (`aria-disabled`, mờ, không bấm được, phím mũi tên bỏ qua) khi\n * KHÔNG thời điểm nào bắt đầu bằng nó nằm trong khung, xét các ô LỚN hơn đang chọn: giờ bị khoá\n * khi cả 60 phút của nó đều ngoài khung, phút khi cả phút đó ngoài khung (ở giờ đang chọn), giây\n * khi đúng thời điểm đó ngoài khung, AM/PM khi cả nửa ngày ngoài khung.\n * - **Kẹp**: chọn một mục hay gõ xong một ô mà ra thời điểm ngoài khung thì giá trị ghi là thời điểm\n * được phép GẦN NHẤT, giữ nguyên thứ vừa chọn/gõ nếu nó còn chỗ trong khung (`max=\"17:00\"`, đang\n * 09:45, chọn giờ 17 → `\"17:00\"`), không thì là cận gần nhất (gõ giờ 20 → `\"17:00\"`). Ô gõ được kẹp\n * đúng lúc nó được GHI như trước nay: gõ đủ hai chữ số (hay một chữ số không thể mở đầu số hai\n * chữ số) — lúc focus nhảy sang ô kế; Tab, Enter, rời ô; phím mũi tên; phím buổi. Chữ số đầu còn\n * chờ chữ số thứ hai thì chưa kẹp.\n * - Ô trống được lấp bằng giờ hiện tại ĐÃ KẸP vào khung, và cột mở ra ở giờ đó khi chưa có giá trị.\n *\n * Nhờ vậy `onValueChange` không bao giờ báo một thời điểm ngoài khung do NGƯỜI DÙNG tạo ra.\n * KHÔNG kẹp: giá trị APP đặt (`value` / `defaultValue` — hiện nguyên, mục của nó trong cột hiện bị\n * khoá; kiểm nó ở tầng validate của form), `min`/`max` đổi khi đã có giá trị, xoá một ô bằng\n * Backspace/Delete, `TimePickerClear`.\n *\n * ⚠ Khác thượng nguồn (3.1.0): thượng nguồn chỉ lưu hai prop này vào context, không áp dụng ở đâu.\n */\n min?: string;\n /** Cận trên của khung giờ — luật đầy đủ ở `min`. */\n max?: string;\n hourStep?: number;\n minuteStep?: number;\n secondStep?: number;\n /** Chữ giữ chỗ của ô trống — một chuỗi cho mọi ô, hoặc từng ô. Mặc định `\"--\"`. */\n segmentPlaceholder?: SegmentPlaceholder;\n /**\n * Locale BCP 47 quyết định đồng hồ 12 hay 24 giờ — CHỈ vậy, không dịch nhãn (nhãn theo\n * `ComitorLocaleProvider`, xem `labels`).\n *\n * Không truyền thì lấy `locale` của `ComitorLocaleProvider`: không có provider → `\"en\"` → 12 giờ\n * (\"AM\"/\"PM\"); `\"vi\"` → 24 giờ; `\"en-GB\"` → 24 giờ. Trước `3.0.0` mặc định cứng là `\"vi-VN\"`.\n *\n * ⚠ Khác thượng nguồn: bản gốc để `undefined`, tức theo locale của MÔI TRƯỜNG CHẠY — xem chú\n * thích ở chỗ đọc prop này trong `TimePicker`. Muốn theo trình duyệt: truyền `navigator.language`\n * — nhưng chỉ sau khi hydrate, vì server không biết giá trị đó.\n */\n locale?: string;\n /**\n * Chuỗi hiển thị và nhãn trình đọc màn hình (tên từng ô, nhãn buổi, tên nút mở, nút xoá). Không\n * truyền thì theo namespace `timePicker` của `ComitorLocaleProvider` (mặc định tiếng Anh). Thêm\n * so với thượng nguồn.\n */\n labels?: Partial<TimePickerLabels>;\n name?: string;\n disabled?: boolean;\n invalid?: boolean;\n readOnly?: boolean;\n required?: boolean;\n showSeconds?: boolean;\n}\n\nfunction TimePicker(props: TimePickerProps) {\n const {\n value: valueProp,\n defaultValue,\n onValueChange,\n open,\n defaultOpen,\n onOpenChange,\n openOnFocus = false,\n inputGroupClickAction = \"focus\",\n min,\n max,\n hourStep = DEFAULT_STEP,\n minuteStep = DEFAULT_STEP,\n secondStep = DEFAULT_STEP,\n segmentPlaceholder = DEFAULT_SEGMENT_PLACEHOLDER,\n locale: localeProp,\n labels: labelsProp,\n name,\n asChild,\n disabled = false,\n invalid = false,\n readOnly = false,\n required = false,\n showSeconds = false,\n className,\n children,\n id,\n ...rootProps\n } = props;\n\n /*\n * ⚠ Khác thượng nguồn: bản gốc để `locale` là `undefined`, tức đồng hồ 12/24 giờ suy từ locale\n * của MÔI TRƯỜNG CHẠY — máy chủ Node thường là `en-US` (12 giờ) còn trình duyệt người dùng Việt là\n * `vi` (24 giờ), nên cùng \"14:30\" server in \"02\" còn client in \"14\": lệch hydrate (cùng lý do\n * `Calendar` bỏ `\"default\"`). Ở đây mặc định là `locale` của `ComitorLocaleProvider` — cùng một\n * giá trị ở cả hai phía. `Intl.DateTimeFormat(\"vi\", { hour: \"numeric\" })` in \"13 giờ\" cho 13:00\n * → `getIs12Hour` trả `false`; `\"en\"` in \"1 PM\" → `true`. Trước `3.0.0` mặc định cứng là `\"vi-VN\"`.\n */\n const { locale: providerLocale } = useComitorLocale();\n const locale = localeProp ?? providerLocale;\n\n const instanceId = React.useId();\n const rootId = id ?? instanceId;\n const inputGroupId = React.useId();\n const labelId = React.useId();\n const triggerId = React.useId();\n\n const inputGroupRef = React.useRef<InputGroupElement>(null);\n const triggerRef = React.useRef<TriggerElement>(null);\n\n const [inputGroup, setInputGroup] = React.useState<InputGroupElement | null>(null);\n const isFormControl = inputGroup ? !!inputGroup.closest(\"form\") : true;\n\n const listenersRef = useLazyRef(() => new Set<() => void>());\n const stateRef = useLazyRef<StoreState>(() => ({\n value: valueProp ?? defaultValue ?? \"\",\n open: open ?? defaultOpen ?? false,\n openedViaFocus: false\n }));\n\n const propsRef = useAsRef({ onValueChange, onOpenChange });\n\n const store: Store = React.useMemo(() => {\n return {\n subscribe: (cb) => {\n listenersRef.current.add(cb);\n return () => listenersRef.current.delete(cb);\n },\n getState: () => stateRef.current,\n setState: (key, value) => {\n if (Object.is(stateRef.current[key], value)) return;\n\n if (key === \"value\" && typeof value === \"string\") {\n stateRef.current.value = value;\n propsRef.current.onValueChange?.(value);\n } else if (key === \"open\" && typeof value === \"boolean\") {\n stateRef.current.open = value;\n propsRef.current.onOpenChange?.(value);\n if (!value) {\n stateRef.current.openedViaFocus = false;\n }\n } else {\n stateRef.current[key] = value;\n }\n\n store.notify();\n },\n notify: () => {\n for (const cb of listenersRef.current) {\n cb();\n }\n }\n };\n }, [listenersRef, stateRef, propsRef]);\n\n const value = useStore((state) => state.value, store);\n\n useIsomorphicLayoutEffect(() => {\n if (valueProp !== undefined) {\n store.setState(\"value\", valueProp);\n }\n }, [valueProp]);\n\n useIsomorphicLayoutEffect(() => {\n if (open !== undefined) {\n store.setState(\"open\", open);\n }\n }, [open]);\n\n const storeOpen = useStore((state) => state.open, store);\n\n const onPopoverOpenChange = React.useCallback((newOpen: boolean) => store.setState(\"open\", newOpen), [store]);\n\n const is12Hour = React.useMemo(() => getIs12Hour(locale), [locale]);\n\n const normalizedPlaceholder = React.useMemo(() => {\n if (typeof segmentPlaceholder === \"string\") {\n return {\n hour: segmentPlaceholder,\n minute: segmentPlaceholder,\n second: segmentPlaceholder,\n period: segmentPlaceholder\n };\n }\n return {\n hour: segmentPlaceholder.hour ?? DEFAULT_SEGMENT_PLACEHOLDER,\n minute: segmentPlaceholder.minute ?? DEFAULT_SEGMENT_PLACEHOLDER,\n second: segmentPlaceholder.second ?? DEFAULT_SEGMENT_PLACEHOLDER,\n period: segmentPlaceholder.period ?? DEFAULT_SEGMENT_PLACEHOLDER\n };\n }, [segmentPlaceholder]);\n\n const labels = useComitorLabels(\"timePicker\", labelsProp);\n\n const timeRange = React.useMemo(() => getTimeRange(min, max, showSeconds), [min, max, showSeconds]);\n\n const rootContext = React.useMemo<TimePickerContextValue>(\n () => ({\n id: rootId,\n inputGroupId,\n labelId,\n triggerId,\n inputGroupRef,\n triggerRef,\n openOnFocus,\n inputGroupClickAction,\n onInputGroupChange: setInputGroup,\n disabled,\n readOnly,\n required,\n invalid,\n showSeconds,\n is12Hour,\n minuteStep,\n secondStep,\n hourStep,\n segmentPlaceholder: normalizedPlaceholder,\n labels,\n min,\n max,\n timeRange\n }),\n [\n rootId,\n inputGroupId,\n labelId,\n triggerId,\n openOnFocus,\n inputGroupClickAction,\n disabled,\n readOnly,\n required,\n invalid,\n showSeconds,\n is12Hour,\n minuteStep,\n secondStep,\n hourStep,\n normalizedPlaceholder,\n labels,\n min,\n max,\n timeRange\n ]\n );\n\n const RootPrimitive = asChild ? Slot : \"div\";\n\n return (\n <>\n <StoreContext.Provider value={store}>\n <TimePickerContext.Provider value={rootContext}>\n <Popover open={storeOpen} onOpenChange={onPopoverOpenChange}>\n <RootPrimitive\n data-slot=\"time-picker\"\n data-disabled={disabled ? \"\" : undefined}\n data-invalid={invalid ? \"\" : undefined}\n {...rootProps}\n className={cn(\"relative\", className)}\n >\n {children}\n </RootPrimitive>\n </Popover>\n </TimePickerContext.Provider>\n </StoreContext.Provider>\n {isFormControl && (\n <VisuallyHiddenInput\n type=\"hidden\"\n control={inputGroup}\n name={name}\n value={value}\n disabled={disabled}\n readOnly={readOnly}\n required={required}\n />\n )}\n </>\n );\n}\n\ninterface TimePickerLabelProps extends React.ComponentProps<\"label\"> {\n asChild?: boolean;\n}\n\nfunction TimePickerLabel(props: TimePickerLabelProps) {\n const { asChild, className, ...labelProps } = props;\n\n const { labelId } = useTimePickerContext(LABEL_NAME);\n\n const LabelPrimitive = asChild ? Slot : \"label\";\n\n return (\n <LabelPrimitive\n data-slot=\"time-picker-label\"\n {...labelProps}\n /*\n * ⚠ Khác thượng nguồn: bản gốc đặt `htmlFor={labelId}` mà KHÔNG phần tử nào mang\n * `id={labelId}` — nhóm ô trỏ `aria-labelledby={labelId}` vào hư không nên trình đọc màn\n * hình đọc một nhóm không tên, và `htmlFor` trỏ vào chính một id không tồn tại. Nhãn giờ\n * MANG id đó; `htmlFor` (nếu app cần) đi qua `labelProps`.\n */\n id={labelId}\n className={cn(\n \"text-sm leading-none font-medium peer-disabled:cursor-not-allowed peer-disabled:opacity-70\",\n className\n )}\n />\n );\n}\n\ninterface TimePickerInputGroupContextValue {\n onInputRegister: (segment: Segment, ref: React.RefObject<InputElement | null>) => void;\n onInputUnregister: (segment: Segment) => void;\n getNextInput: (currentSegment: Segment) => React.RefObject<InputElement | null> | null;\n}\n\nconst TimePickerInputGroupContext = React.createContext<TimePickerInputGroupContextValue | null>(null);\n\nfunction useTimePickerInputGroupContext(consumerName: string) {\n const context = React.useContext(TimePickerInputGroupContext);\n if (!context) {\n throw new Error(`\\`${consumerName}\\` phải nằm bên trong \\`${INPUT_GROUP_NAME}\\``);\n }\n return context;\n}\n\ntype TimePickerInputGroupProps = DivProps;\n\nfunction TimePickerInputGroup(props: TimePickerInputGroupProps) {\n const {\n onPointerDown: onPointerDownProp,\n onClick: onClickProp,\n asChild,\n className,\n style,\n ref,\n ...inputGroupProps\n } = props;\n\n const {\n inputGroupId,\n labelId,\n onInputGroupChange,\n disabled,\n readOnly,\n invalid,\n segmentPlaceholder,\n labels,\n inputGroupRef,\n triggerRef,\n inputGroupClickAction\n } = useTimePickerContext(INPUT_GROUP_NAME);\n\n const store = useStoreContext(INPUT_GROUP_NAME);\n\n const composedRef = useComposedRefs(ref, inputGroupRef, onInputGroupChange);\n\n const inputRefsMap = React.useRef<Map<Segment, React.RefObject<InputElement | null>>>(new Map());\n\n const onInputRegister = React.useCallback((segment: Segment, ref: React.RefObject<InputElement | null>) => {\n inputRefsMap.current.set(segment, ref);\n }, []);\n\n const onInputUnregister = React.useCallback((segment: Segment) => {\n inputRefsMap.current.delete(segment);\n }, []);\n\n const getNextInput = React.useCallback((currentSegment: Segment): React.RefObject<InputElement | null> | null => {\n const segmentOrder: Segment[] = [\"hour\", \"minute\", \"second\", \"period\"];\n const currentIndex = segmentOrder.indexOf(currentSegment);\n\n if (currentIndex === -1 || currentIndex === segmentOrder.length - 1) {\n return null;\n }\n\n for (let i = currentIndex + 1; i < segmentOrder.length; i++) {\n const nextSegment = segmentOrder[i];\n if (nextSegment) {\n const nextRef = inputRefsMap.current.get(nextSegment);\n if (nextRef?.current) {\n return nextRef;\n }\n }\n }\n\n return null;\n }, []);\n\n const onPointerDown = React.useCallback(\n (event: React.PointerEvent<InputGroupElement>) => {\n onPointerDownProp?.(event);\n if (disabled || readOnly || event.defaultPrevented) return;\n\n const target = event.target as HTMLElement;\n\n if (target.tagName === \"INPUT\" || target.closest(\"input\")) {\n return;\n }\n\n if (triggerRef.current?.contains(target)) {\n return;\n }\n\n event.preventDefault();\n },\n [onPointerDownProp, disabled, readOnly, triggerRef]\n );\n\n const onClick = React.useCallback(\n (event: React.MouseEvent<InputGroupElement>) => {\n onClickProp?.(event);\n if (disabled || readOnly || event.defaultPrevented) return;\n\n const target = event.target as HTMLElement;\n\n if (target.tagName === \"INPUT\" || target.closest(\"input\")) {\n return;\n }\n\n if (triggerRef.current?.contains(target)) {\n return;\n }\n\n if (inputGroupClickAction === \"open\") {\n store.setState(\"open\", true);\n } else {\n const activeElement = document.activeElement;\n const isInputAlreadyFocused =\n activeElement && activeElement.tagName === \"INPUT\" && inputGroupRef.current?.contains(activeElement);\n\n if (!isInputAlreadyFocused) {\n for (const segment of SEGMENTS) {\n const inputRef = inputRefsMap.current.get(segment);\n if (inputRef?.current) {\n inputRef.current.focus();\n inputRef.current.select();\n break;\n }\n }\n }\n }\n },\n [onClickProp, disabled, readOnly, inputGroupClickAction, store, triggerRef, inputGroupRef]\n );\n\n const inputGroupContextValue = React.useMemo<TimePickerInputGroupContextValue>(\n () => ({\n onInputRegister,\n onInputUnregister,\n getNextInput\n }),\n [onInputRegister, onInputUnregister, getNextInput]\n );\n\n const InputGroupPrimitive = asChild ? Slot : \"div\";\n\n return (\n <TimePickerInputGroupContext.Provider value={inputGroupContextValue}>\n <PopoverAnchor asChild>\n <InputGroupPrimitive\n role=\"group\"\n id={inputGroupId}\n aria-labelledby={labelId}\n data-slot=\"time-picker-input-group\"\n data-disabled={disabled ? \"\" : undefined}\n data-invalid={invalid ? \"\" : undefined}\n {...inputGroupProps}\n className={cn(\n /*\n * ⚠ Khác thượng nguồn: khung ô đi theo `Input` của gói (ô ngày của `DatePicker` là\n * một `Input`, và hai thứ này hay đứng chung một hàng biểu mẫu): `h-9` thay `h-10`,\n * bỏ `shadow-xs`, hover đậm viền `--control-edge-strong`, focus viền\n * `--primary-ink` + quầng `ring-2 ring-ring/50` KHÔNG offset (quy ước họ ô nhập —\n * xem `InputGroup`), lỗi viền `--destructive-ink`. Số đo ở chú thích đầu `input.tsx`.\n */\n \"flex h-9 w-full cursor-text items-center gap-0.5 rounded-md border border-input bg-background px-3 py-2 text-sm text-foreground transition-colors duration-150 ease-out outline-none hover:border-control-edge-strong\",\n \"has-[input:focus]:border-primary-ink has-[input:focus]:ring-2 has-[input:focus]:ring-ring/50\",\n invalid &&\n \"border-destructive-ink hover:border-destructive-ink has-[input:focus]:border-destructive-ink has-[input:focus]:ring-destructive/30\",\n /*\n * ⚠ Khác thượng nguồn: bản gốc ghép `disabled && \"cursor-not-allowed opacity-50\"` —\n * lớp gắn VÔ ĐIỀU KIỆN vào chuỗi, nên `pnpm lint:a11y` đo viền/chữ lúc NGHỈ đã nhân\n * 50% (viền 1,75:1, chữ 3,49:1 ✗). Neo vào `:disabled` gốc của các ô con (cổng miễn\n * trừ đúng nhánh này — WCAG 1.4.3/1.4.11 không đòi tương phản cho control vô hiệu);\n * `disabled` ở gốc khoá MỌI ô nên hai cách cho cùng kết quả. Thêm `bg-muted` theo `Input`.\n */\n \"has-[input:disabled]:cursor-not-allowed has-[input:disabled]:bg-muted has-[input:disabled]:opacity-50\",\n className\n )}\n style={\n {\n \"--time-picker-hour-input-width\": `${segmentPlaceholder.hour.length}ch`,\n \"--time-picker-minute-input-width\": `${segmentPlaceholder.minute.length}ch`,\n \"--time-picker-second-input-width\": `${segmentPlaceholder.second.length}ch`,\n // ⚠ Khác thượng nguồn: tính cả độ dài nhãn buổi (`labels.am`/`labels.pm`) — bản gốc\n // chỉ có \"AM\"/\"PM\" 2 ký tự nên ghim sàn 2; nhãn do app đặt có thể dài hơn.\n \"--time-picker-period-input-width\": `${Math.max(segmentPlaceholder.period.length, labels.am.length, labels.pm.length, 2) + 0.5}ch`,\n ...style\n } as React.CSSProperties\n }\n ref={composedRef}\n onPointerDown={onPointerDown}\n onClick={onClick}\n />\n </PopoverAnchor>\n </TimePickerInputGroupContext.Provider>\n );\n}\n\n/*\n * Thân của `getSegmentValue` (trong `TimePickerInput`) của bản gốc, tách ra nguyên văn — ⚠ Khác thượng\n * nguồn (3.1.0): để chữ của ô đang gõ đổi theo giá trị vừa bị KẸP (`updateTimeValue`), thứ không phải\n * giá trị của lượt render hiện tại.\n */\nfunction getSegmentText(\n timeValue: TimeValue | null,\n segment: Segment,\n is12Hour: boolean,\n segmentPlaceholder: TimePickerContextValue[\"segmentPlaceholder\"]\n): string {\n if (!timeValue) {\n if (!segment) return \"\";\n return segmentPlaceholder[segment];\n }\n switch (segment) {\n case \"hour\": {\n if (timeValue.hour === undefined) return segmentPlaceholder.hour;\n if (is12Hour) {\n return to12Hour(timeValue.hour).hour.toString().padStart(2, \"0\");\n }\n return timeValue.hour.toString().padStart(2, \"0\");\n }\n case \"minute\":\n if (timeValue.minute === undefined) return segmentPlaceholder.minute;\n return timeValue.minute.toString().padStart(2, \"0\");\n case \"second\":\n if (timeValue.second === undefined) return segmentPlaceholder.second;\n return timeValue.second.toString().padStart(2, \"0\");\n case \"period\": {\n if (!timeValue || timeValue.hour === undefined) return segmentPlaceholder.period;\n return to12Hour(timeValue.hour).period;\n }\n default:\n return \"\";\n }\n}\n\ninterface TimePickerInputProps extends Omit<React.ComponentProps<\"input\">, \"type\" | \"value\"> {\n segment: Segment;\n}\n\nfunction TimePickerInput(props: TimePickerInputProps) {\n const {\n segment,\n onBlur: onBlurProp,\n onChange: onChangeProp,\n onClick: onClickProp,\n onFocus: onFocusProp,\n onKeyDown: onKeyDownProp,\n disabled: disabledProp,\n readOnly: readOnlyProp,\n className,\n style,\n ref,\n ...inputProps\n } = props;\n\n const { is12Hour, showSeconds, disabled, readOnly, invalid, segmentPlaceholder, labels, openOnFocus, timeRange } =\n useTimePickerContext(INPUT_NAME);\n const store = useStoreContext(INPUT_NAME);\n const inputGroupContext = useTimePickerInputGroupContext(INPUT_NAME);\n\n const isDisabled = disabledProp || disabled;\n const isReadOnly = readOnlyProp || readOnly;\n\n const value = useStore((state) => state.value);\n const timeValue = parseTimeString(value);\n\n const inputRef = React.useRef<HTMLInputElement>(null);\n const composedRef = useComposedRefs(ref, inputRef);\n\n useIsomorphicLayoutEffect(() => {\n if (segment) {\n inputGroupContext.onInputRegister(segment as Segment, inputRef);\n return () => inputGroupContext.onInputUnregister(segment as Segment);\n }\n }, [inputGroupContext, segment]);\n\n const getSegmentValue = React.useCallback(\n () => getSegmentText(timeValue, segment, is12Hour, segmentPlaceholder),\n [timeValue, segment, is12Hour, segmentPlaceholder]\n );\n\n const [editValue, setEditValue] = React.useState(getSegmentValue());\n const [isEditing, setIsEditing] = React.useState(false);\n const [pendingDigit, setPendingDigit] = React.useState<string | null>(null);\n\n React.useEffect(() => {\n if (!isEditing) {\n setEditValue(getSegmentValue());\n setPendingDigit(null);\n }\n }, [getSegmentValue, isEditing]);\n\n const updateTimeValue = React.useCallback(\n (newSegmentValue: string | undefined, shouldCreateIfEmpty = false) => {\n const placeholder = segment ? segmentPlaceholder[segment] : DEFAULT_SEGMENT_PLACEHOLDER;\n if (!newSegmentValue || newSegmentValue === placeholder) return;\n if (!timeValue && !shouldCreateIfEmpty) return;\n\n const currentTime = timeValue ?? {};\n const newTime = { ...currentTime };\n\n switch (segment) {\n case \"hour\": {\n const displayHour = Number.parseInt(newSegmentValue, 10);\n if (!Number.isNaN(displayHour)) {\n if (is12Hour) {\n const clampedHour = clamp(displayHour, 1, 12);\n let currentPeriod: Period;\n if (timeValue?.period !== undefined) {\n currentPeriod = timeValue.period;\n } else if (timeValue?.hour !== undefined) {\n currentPeriod = to12Hour(timeValue.hour).period;\n } else {\n // ⚠ Khác thượng nguồn (3.1.0): \"bây giờ\" kẹp vào khung — xem `getReferenceTime`.\n currentPeriod = to12Hour(getReferenceTime(timeRange, showSeconds).hour).period;\n }\n const hour24 = to24Hour(clampedHour, currentPeriod);\n newTime.hour = hour24;\n if (timeValue?.period !== undefined) {\n newTime.period = timeValue.period;\n }\n } else {\n newTime.hour = clamp(displayHour, 0, 23);\n }\n }\n break;\n }\n case \"minute\": {\n const minute = Number.parseInt(newSegmentValue, 10);\n if (!Number.isNaN(minute)) {\n newTime.minute = clamp(minute, 0, 59);\n }\n break;\n }\n case \"second\": {\n const second = Number.parseInt(newSegmentValue, 10);\n if (!Number.isNaN(second)) {\n newTime.second = clamp(second, 0, 59);\n }\n break;\n }\n case \"period\": {\n if (newSegmentValue === \"AM\" || newSegmentValue === \"PM\") {\n newTime.period = newSegmentValue;\n if (timeValue && timeValue.hour !== undefined) {\n const currentDisplay = to12Hour(timeValue.hour);\n newTime.hour = to24Hour(currentDisplay.hour, newSegmentValue);\n }\n }\n break;\n }\n }\n\n const newValue = formatTimeValue(newTime, showSeconds);\n\n /*\n * ⚠ Khác thượng nguồn (3.1.0): kẹp theo `min`/`max` ngay lúc GHI — mọi đường gõ đều ghi qua\n * đây (đủ hai chữ số, Tab, Enter, rời ô, mũi tên, phím buổi), nên \"lúc kẹp\" chính là lúc\n * `onValueChange` vốn đã chạy. Ghi lại đúng giá trị đang có thì dừng như store vẫn tự dừng —\n * và không kẹp: chỉ focus rồi rời một ô của giá trị APP đặt sẵn ngoài khung (rời ô là ghi lại\n * chữ trong ô) không được lặng lẽ sửa giá trị đó.\n */\n if (newValue === store.getState().value) return;\n\n const committedTime = constrainTime(newTime, timeRange, showSeconds, segment);\n if (committedTime === newTime) {\n store.setState(\"value\", newValue);\n return;\n }\n\n store.setState(\"value\", formatTimeValue(committedTime, showSeconds));\n // Ô đang focus hiện `editValue` (chữ vừa gõ) chứ không hiện giá trị — cho nó theo giá trị đã kẹp.\n setEditValue(getSegmentText(committedTime, segment, is12Hour, segmentPlaceholder));\n setPendingDigit(null);\n },\n [timeValue, segment, is12Hour, showSeconds, store, segmentPlaceholder, timeRange]\n );\n\n const onBlur = React.useCallback(\n (event: React.FocusEvent<InputElement>) => {\n onBlurProp?.(event);\n if (event.defaultPrevented) return;\n\n setIsEditing(false);\n\n const placeholder = segment ? segmentPlaceholder[segment] : DEFAULT_SEGMENT_PLACEHOLDER;\n if (editValue && editValue !== placeholder && editValue.length > 0) {\n let valueToUpdate = editValue;\n\n if (segment !== \"period\") {\n if (editValue.length === 2) {\n valueToUpdate = editValue;\n } else if (editValue.length === 1) {\n const numValue = Number.parseInt(editValue, 10);\n if (!Number.isNaN(numValue)) {\n valueToUpdate = numValue.toString().padStart(2, \"0\");\n }\n }\n }\n\n updateTimeValue(valueToUpdate, true);\n\n // Ô còn trống sau khi rời một ô đã gõ → lấp bằng giờ hiện tại (hành vi gốc).\n // ⚠ Khác thượng nguồn (3.1.0): giờ hiện tại KẸP vào khung (`getReferenceTime`), và giá trị\n // vừa đủ ô được kẹp như mọi lần ghi khác — giữ ô vừa gõ nếu nó còn chỗ trong khung.\n queueMicrotask(() => {\n const currentTimeValue = parseTimeString(store.getState().value);\n if (currentTimeValue) {\n const now = getReferenceTime(timeRange, showSeconds);\n const newTime = { ...currentTimeValue };\n let needsUpdate = false;\n\n if (newTime.hour === undefined) {\n newTime.hour = now.hour;\n needsUpdate = true;\n }\n\n if (newTime.minute === undefined) {\n newTime.minute = now.minute;\n needsUpdate = true;\n }\n\n if (showSeconds && newTime.second === undefined) {\n newTime.second = now.second;\n needsUpdate = true;\n }\n\n if (needsUpdate) {\n const newValue = formatTimeValue(constrainTime(newTime, timeRange, showSeconds, segment), showSeconds);\n store.setState(\"value\", newValue);\n }\n }\n });\n }\n\n setEditValue(getSegmentValue());\n setPendingDigit(null);\n },\n [\n onBlurProp,\n editValue,\n updateTimeValue,\n getSegmentValue,\n segment,\n segmentPlaceholder,\n showSeconds,\n store,\n timeRange\n ]\n );\n\n const onChange = React.useCallback(\n (event: React.ChangeEvent<InputElement>) => {\n onChangeProp?.(event);\n if (event.defaultPrevented) return;\n\n let newValue = event.target.value;\n\n const placeholder = segment ? segmentPlaceholder[segment] : DEFAULT_SEGMENT_PLACEHOLDER;\n if (editValue === placeholder && newValue.length > 0 && newValue !== placeholder) {\n newValue = newValue.replace(new RegExp(`^${placeholder}`), \"\");\n }\n\n if (segment === \"period\") {\n const newPeriod = getPeriodFromKey(newValue.charAt(0), labels);\n\n if (newPeriod) {\n setEditValue(newPeriod);\n updateTimeValue(newPeriod, true);\n queueMicrotask(() => {\n inputRef.current?.select();\n });\n }\n return;\n }\n\n if (segment === \"hour\" || segment === \"minute\" || segment === \"second\") {\n newValue = newValue.replace(/\\D/g, \"\");\n }\n\n if (newValue.length > 2) {\n newValue = newValue.slice(0, 2);\n }\n if (segment === \"hour\" || segment === \"minute\" || segment === \"second\") {\n const numValue = Number.parseInt(newValue, 10);\n\n if (!Number.isNaN(numValue) && newValue.length > 0) {\n if (pendingDigit !== null && newValue.length === 1) {\n const twoDigitValue = pendingDigit + newValue;\n const combinedNum = Number.parseInt(twoDigitValue, 10);\n\n if (!Number.isNaN(combinedNum)) {\n const paddedValue = combinedNum.toString().padStart(2, \"0\");\n setEditValue(paddedValue);\n updateTimeValue(paddedValue, true);\n setPendingDigit(null);\n\n queueMicrotask(() => {\n if (segment) {\n const nextInputRef = inputGroupContext.getNextInput(segment);\n if (nextInputRef?.current) {\n nextInputRef.current.focus();\n nextInputRef.current.select();\n }\n }\n });\n return;\n }\n }\n\n const maxFirstDigit = segment === \"hour\" ? (is12Hour ? 1 : 2) : 5;\n\n const firstDigit = Number.parseInt(newValue[0] ?? \"0\", 10);\n const shouldAutoAdvance = firstDigit > maxFirstDigit;\n\n if (newValue.length === 1) {\n if (shouldAutoAdvance) {\n const paddedValue = numValue.toString().padStart(2, \"0\");\n setEditValue(paddedValue);\n updateTimeValue(paddedValue, true);\n setPendingDigit(null);\n\n queueMicrotask(() => {\n if (segment) {\n const nextInputRef = inputGroupContext.getNextInput(segment);\n if (nextInputRef?.current) {\n nextInputRef.current.focus();\n nextInputRef.current.select();\n }\n }\n });\n } else {\n const paddedValue = numValue.toString().padStart(2, \"0\");\n setEditValue(paddedValue);\n setPendingDigit(newValue);\n queueMicrotask(() => {\n inputRef.current?.select();\n });\n }\n } else if (newValue.length === 2) {\n const paddedValue = numValue.toString().padStart(2, \"0\");\n setEditValue(paddedValue);\n updateTimeValue(paddedValue, true);\n setPendingDigit(null);\n\n queueMicrotask(() => {\n if (segment) {\n const nextInputRef = inputGroupContext.getNextInput(segment);\n if (nextInputRef?.current) {\n nextInputRef.current.focus();\n nextInputRef.current.select();\n }\n }\n });\n }\n } else if (newValue.length === 0) {\n setEditValue(\"\");\n setPendingDigit(null);\n }\n }\n },\n [\n segment,\n updateTimeValue,\n onChangeProp,\n editValue,\n is12Hour,\n inputGroupContext,\n pendingDigit,\n segmentPlaceholder,\n labels\n ]\n );\n\n const onClick = React.useCallback(\n (event: React.MouseEvent<InputElement>) => {\n onClickProp?.(event);\n if (event.defaultPrevented) return;\n\n event.currentTarget.select();\n },\n [onClickProp]\n );\n\n const onFocus = React.useCallback(\n (event: React.FocusEvent<InputElement>) => {\n onFocusProp?.(event);\n if (event.defaultPrevented) return;\n\n setIsEditing(true);\n setPendingDigit(null);\n\n if (openOnFocus && !store.getState().open) {\n store.setState(\"openedViaFocus\", true);\n store.setState(\"open\", true);\n }\n\n queueMicrotask(() => event.target.select());\n },\n [onFocusProp, openOnFocus, store]\n );\n\n const onKeyDown = React.useCallback(\n (event: React.KeyboardEvent<InputElement>) => {\n onKeyDownProp?.(event);\n if (event.defaultPrevented) return;\n\n if (event.key === \"ArrowLeft\" || event.key === \"ArrowRight\") {\n event.preventDefault();\n\n const goToPrevious = event.key === \"ArrowLeft\";\n const inputGroup = inputRef.current?.closest('[data-slot=\"time-picker-input-group\"]');\n\n if (inputGroup && inputRef.current) {\n const allInputs = Array.from(inputGroup.querySelectorAll('input[type=\"text\"]')) as HTMLInputElement[];\n const currentIdx = allInputs.indexOf(inputRef.current);\n\n if (currentIdx !== -1) {\n const targetIdx = goToPrevious\n ? Math.max(0, currentIdx - 1)\n : Math.min(allInputs.length - 1, currentIdx + 1);\n\n const targetInput = allInputs[targetIdx];\n if (targetInput && targetInput !== inputRef.current) {\n targetInput.focus();\n targetInput.select();\n }\n }\n }\n return;\n }\n\n if (event.key === \"Backspace\" || event.key === \"Delete\") {\n const input = inputRef.current;\n if (input && input.selectionStart === 0 && input.selectionEnd === input.value.length) {\n event.preventDefault();\n const placeholder = segment ? segmentPlaceholder[segment] : DEFAULT_SEGMENT_PLACEHOLDER;\n setEditValue(placeholder);\n setPendingDigit(null);\n\n if (timeValue) {\n const newTime = { ...timeValue };\n switch (segment) {\n case \"hour\":\n delete newTime.hour;\n break;\n case \"minute\":\n delete newTime.minute;\n break;\n case \"second\":\n delete newTime.second;\n break;\n case \"period\":\n delete newTime.period;\n break;\n }\n\n if (\n newTime.hour !== undefined ||\n newTime.minute !== undefined ||\n newTime.second !== undefined ||\n newTime.period !== undefined\n ) {\n const newValue = formatTimeValue(newTime, showSeconds);\n store.setState(\"value\", newValue);\n } else {\n store.setState(\"value\", \"\");\n }\n } else {\n store.setState(\"value\", \"\");\n }\n\n queueMicrotask(() => {\n inputRef.current?.select();\n });\n return;\n }\n }\n\n if (segment === \"period\") {\n const newPeriodFromKey = getPeriodFromKey(event.key, labels);\n if (newPeriodFromKey) {\n event.preventDefault();\n setEditValue(newPeriodFromKey);\n updateTimeValue(newPeriodFromKey, true);\n queueMicrotask(() => {\n inputRef.current?.select();\n });\n } else if (event.key === \"ArrowUp\" || event.key === \"ArrowDown\") {\n event.preventDefault();\n const placeholder = segmentPlaceholder.period;\n const currentPeriod = editValue === placeholder || editValue === \"\" ? \"AM\" : editValue;\n const newPeriod = currentPeriod === \"AM\" || currentPeriod === \"A\" ? \"PM\" : \"AM\";\n setEditValue(newPeriod);\n updateTimeValue(newPeriod, true);\n queueMicrotask(() => {\n inputRef.current?.select();\n });\n }\n return;\n }\n\n if (event.key === \"Tab\") {\n const placeholder = segment ? segmentPlaceholder[segment] : DEFAULT_SEGMENT_PLACEHOLDER;\n if (editValue && editValue.length > 0 && editValue !== placeholder) {\n if (editValue.length === 2) {\n updateTimeValue(editValue, true);\n } else if (editValue.length === 1) {\n const numValue = Number.parseInt(editValue, 10);\n if (!Number.isNaN(numValue)) {\n const paddedValue = numValue.toString().padStart(2, \"0\");\n updateTimeValue(paddedValue, true);\n }\n }\n }\n return;\n }\n\n if (event.key === \"Enter\") {\n event.preventDefault();\n const placeholder = segment ? segmentPlaceholder[segment] : DEFAULT_SEGMENT_PLACEHOLDER;\n if (editValue && editValue.length > 0 && editValue !== placeholder) {\n if (editValue.length === 2) {\n updateTimeValue(editValue, true);\n } else if (editValue.length === 1) {\n const numValue = Number.parseInt(editValue, 10);\n if (!Number.isNaN(numValue)) {\n const paddedValue = numValue.toString().padStart(2, \"0\");\n updateTimeValue(paddedValue, true);\n }\n }\n }\n queueMicrotask(() => {\n inputRef.current?.select();\n });\n }\n\n if (event.key === \"Escape\") {\n event.preventDefault();\n setEditValue(getSegmentValue());\n inputRef.current?.blur();\n }\n\n if (event.key === \"ArrowUp\") {\n event.preventDefault();\n const placeholder = segment ? segmentPlaceholder[segment] : DEFAULT_SEGMENT_PLACEHOLDER;\n if (editValue === placeholder || editValue === \"\") {\n const defaultValue = segment === \"hour\" ? (is12Hour ? 12 : 0) : 0;\n const formattedValue = defaultValue.toString().padStart(2, \"0\");\n setEditValue(formattedValue);\n updateTimeValue(formattedValue, true);\n queueMicrotask(() => {\n inputRef.current?.select();\n });\n return;\n }\n const currentValue = Number.parseInt(editValue, 10);\n if (!Number.isNaN(currentValue)) {\n let newValue: number;\n switch (segment) {\n case \"hour\":\n if (is12Hour) {\n newValue = currentValue === 12 ? 1 : currentValue + 1;\n } else {\n newValue = currentValue === 23 ? 0 : currentValue + 1;\n }\n break;\n case \"minute\":\n case \"second\":\n newValue = currentValue === 59 ? 0 : currentValue + 1;\n break;\n default:\n return;\n }\n const formattedValue = newValue.toString().padStart(2, \"0\");\n setEditValue(formattedValue);\n updateTimeValue(formattedValue, true);\n queueMicrotask(() => {\n inputRef.current?.select();\n });\n }\n }\n\n if (event.key === \"ArrowDown\") {\n event.preventDefault();\n const placeholder = segment ? segmentPlaceholder[segment] : DEFAULT_SEGMENT_PLACEHOLDER;\n if (editValue === placeholder || editValue === \"\") {\n const defaultValue = segment === \"hour\" ? (is12Hour ? 12 : 23) : 59;\n const formattedValue = defaultValue.toString().padStart(2, \"0\");\n setEditValue(formattedValue);\n updateTimeValue(formattedValue, true);\n queueMicrotask(() => {\n inputRef.current?.select();\n });\n return;\n }\n const currentValue = Number.parseInt(editValue, 10);\n if (!Number.isNaN(currentValue)) {\n let newValue: number;\n switch (segment) {\n case \"hour\":\n if (is12Hour) {\n newValue = currentValue === 1 ? 12 : currentValue - 1;\n } else {\n newValue = currentValue === 0 ? 23 : currentValue - 1;\n }\n break;\n case \"minute\":\n case \"second\":\n newValue = currentValue === 0 ? 59 : currentValue - 1;\n break;\n default:\n return;\n }\n const formattedValue = newValue.toString().padStart(2, \"0\");\n setEditValue(formattedValue);\n updateTimeValue(formattedValue, true);\n queueMicrotask(() => {\n inputRef.current?.select();\n });\n }\n }\n },\n [\n onKeyDownProp,\n editValue,\n segment,\n is12Hour,\n getSegmentValue,\n updateTimeValue,\n showSeconds,\n timeValue,\n store,\n segmentPlaceholder,\n labels\n ]\n );\n\n /*\n * ⚠ Khác thượng nguồn: ở đồng hồ 24 giờ bản gốc VẪN vẽ ô buổi (in \"PM\" cạnh \"14:30\"), và gõ `A`\n * vào đó biến 14:30 thành 02:30 — trong khi cột `TimePickerPeriod` của chính nó tự ẩn ở chế độ\n * này. Mọi demo thượng nguồn đều đặt sẵn `<TimePickerInput segment=\"period\" />`, và tiếng Việt\n * (cũng như `en-GB`) chạy 24 giờ, nên ô buổi ẩn theo cùng luật với cột. Đặt SAU mọi hook.\n */\n if (segment === \"period\" && !is12Hour) return null;\n\n const displayValue = isEditing ? editValue : getSegmentValue();\n\n const segmentWidth = segment ? `var(--time-picker-${segment}-input-width)` : \"2ch\";\n\n return (\n <input\n type=\"text\"\n inputMode={segment === \"period\" ? \"text\" : \"numeric\"}\n autoComplete=\"off\"\n autoCorrect=\"off\"\n autoCapitalize=\"off\"\n spellCheck={false}\n translate=\"no\"\n /*\n * ⚠ Khác thượng nguồn: bản gốc không đặt tên cho ô nào — trình đọc màn hình đọc bốn ô\n * \"sửa văn bản, 14\" liền nhau mà không biết ô nào là giờ, ô nào là phút. Tên lấy từ\n * `labels` (namespace `timePicker`: \"Hour\"/\"Minute\"/\"Second\"/\"AM/PM\" ở tiếng Anh); `aria-label`\n * của app vẫn đè được.\n * `aria-invalid` cũng vậy: bản gốc chỉ tô viền đỏ (`data-invalid`) mà không báo cho AT.\n */\n aria-label={labels[segment]}\n aria-invalid={invalid || undefined}\n {...inputProps}\n disabled={isDisabled}\n readOnly={isReadOnly}\n className={cn(\n \"inline-flex h-full items-center justify-center border-0 bg-transparent text-center text-sm tabular-nums transition-colors outline-none focus:bg-transparent disabled:cursor-not-allowed disabled:opacity-50\",\n className\n )}\n style={{ width: segmentWidth, ...style }}\n ref={composedRef}\n value={segment === \"period\" ? getPeriodLabel(displayValue, labels) : displayValue}\n onBlur={onBlur}\n onChange={onChange}\n onClick={onClick}\n onFocus={onFocus}\n onKeyDown={onKeyDown}\n />\n );\n}\n\ntype TimePickerTriggerProps = ButtonProps;\n\nfunction TimePickerTrigger(props: TimePickerTriggerProps) {\n const { className, children, disabled: disabledProp, ref, ...triggerProps } = props;\n\n const { triggerId, disabled, labels, triggerRef } = useTimePickerContext(TRIGGER_NAME);\n\n const isDisabled = disabledProp || disabled;\n\n const composedRef = useComposedRefs(ref, triggerRef);\n\n return (\n <PopoverTrigger\n type=\"button\"\n id={triggerId}\n data-slot=\"time-picker-trigger\"\n disabled={isDisabled}\n ref={composedRef}\n {...triggerProps}\n className={cn(\n // ⚠ Khác thượng nguồn: thêm viền focus theo khuôn `Button` của gói — bản gốc không có kiểu\n // focus nào, và viền mặc định của trình duyệt bị lớp nền `outline-ring/50` pha còn gold 50%.\n \"ml-auto flex items-center rounded-sm text-muted-foreground transition-colors hover:text-foreground focus-visible:outline-2 focus-visible:outline-ring focus-visible:outline-offset-2 disabled:pointer-events-none [&>svg:not([class*='size-'])]:size-4\",\n className\n )}\n >\n {/*\n * ⚠ Khác thượng nguồn: nút mặc định chỉ có icon đồng hồ nên là một nút KHÔNG TÊN. Tên đi qua\n * `sr-only` (cùng khuôn nút mở lịch của `DatePicker`), không qua `aria-label`, để khi app\n * truyền `children` có chữ thì chữ đó là tên — không bị một nhãn ẩn đè lên.\n */}\n {children ?? (\n <>\n <Clock aria-hidden=\"true\" />\n <span className=\"sr-only\">{labels.openPicker}</span>\n </>\n )}\n </PopoverTrigger>\n );\n}\n\ninterface TimePickerGroupContextValue {\n getColumns: () => ColumnData[];\n onColumnRegister: (column: ColumnData) => void;\n onColumnUnregister: (id: string) => void;\n /** Phần tử của bảng chọn — cũng là vùng `FocusScope` của Radix lo vòng Tab (3.1.0). */\n contentRef: React.RefObject<HTMLDivElement | null>;\n}\n\nconst TimePickerGroupContext = React.createContext<TimePickerGroupContextValue | null>(null);\n\nfunction useTimePickerGroupContext(consumerName: string) {\n const context = React.useContext(TimePickerGroupContext);\n if (!context) {\n // Bản gốc báo `TimePicker`; thứ thật sự cung cấp context này là `TimePickerContent`.\n throw new Error(`\\`${consumerName}\\` phải nằm bên trong \\`${CONTENT_NAME}\\``);\n }\n return context;\n}\n\ninterface TimePickerContentProps extends DivProps, React.ComponentProps<typeof PopoverContent> {}\n\nfunction TimePickerContent(props: TimePickerContentProps) {\n const {\n side = \"bottom\",\n align = \"start\",\n sideOffset = 6,\n className,\n onOpenAutoFocus: onOpenAutoFocusProp,\n onInteractOutside: onInteractOutsideProp,\n ref,\n ...contentProps\n } = props;\n\n const store = useStoreContext(CONTENT_NAME);\n const { openOnFocus, inputGroupRef } = useTimePickerContext(CONTENT_NAME);\n const columnsRef = React.useRef<Map<string, Omit<ColumnData, \"id\">>>(new Map());\n const contentRef = React.useRef<HTMLDivElement | null>(null);\n const composedRef = useComposedRefs(ref, contentRef);\n\n const onColumnRegister = React.useCallback((column: ColumnData) => {\n columnsRef.current.set(column.id, column);\n }, []);\n\n const onColumnUnregister = React.useCallback((id: string) => {\n columnsRef.current.delete(id);\n }, []);\n\n const getColumns = React.useCallback(() => {\n const columns = Array.from(columnsRef.current.entries())\n .map(([id, { ref, getSelectedItemRef, getItems }]) => ({\n id,\n ref,\n getSelectedItemRef,\n getItems\n }))\n .filter((c) => c.ref.current !== null);\n return sortNodes(columns);\n }, []);\n\n const groupContextValue = React.useMemo<TimePickerGroupContextValue>(\n () => ({\n getColumns,\n onColumnRegister,\n onColumnUnregister,\n contentRef\n }),\n [getColumns, onColumnRegister, onColumnUnregister]\n );\n\n const onOpenAutoFocus: NonNullable<PopoverContentProps[\"onOpenAutoFocus\"]> = React.useCallback(\n (event) => {\n onOpenAutoFocusProp?.(event);\n if (event.defaultPrevented) return;\n\n event.preventDefault();\n\n const { openedViaFocus } = store.getState();\n\n // Mở vì ô nhập được focus (`openOnFocus`) → để focus yên ở ô nhập.\n if (openedViaFocus) {\n store.setState(\"openedViaFocus\", false);\n return;\n }\n\n const columns = getColumns();\n const firstColumn = columns[0];\n\n if (!firstColumn) return;\n\n // ⚠ Khác thượng nguồn (3.1.0): mục đón của cột (`getColumnEntry`) thay cho \"mục đang chọn\" —\n // bằng nhau, trừ khi mục đang chọn bị khoá theo `min`/`max`.\n focusFirst(getColumnEntryRefs(firstColumn.getItems()), false);\n },\n [onOpenAutoFocusProp, getColumns, store]\n );\n\n const onInteractOutside: NonNullable<PopoverContentProps[\"onInteractOutside\"]> = React.useCallback(\n (event) => {\n onInteractOutsideProp?.(event);\n if (event.defaultPrevented) return;\n\n // `openOnFocus`: bấm vào nhóm ô không được tính là \"bấm ra ngoài\" rồi đóng bảng chọn.\n if (openOnFocus && inputGroupRef.current) {\n const target = event.target;\n if (!(target instanceof Node)) return;\n const isInsideInputGroup = inputGroupRef.current.contains(target);\n\n if (isInsideInputGroup) {\n event.preventDefault();\n }\n }\n },\n [onInteractOutsideProp, openOnFocus, inputGroupRef]\n );\n\n return (\n <TimePickerGroupContext.Provider value={groupContextValue}>\n <PopoverContent\n data-slot=\"time-picker-content\"\n side={side}\n align={align}\n sideOffset={sideOffset}\n {...contentProps}\n ref={composedRef}\n className={cn(\"flex w-auto max-w-(--radix-popover-trigger-width) p-0\", className)}\n onOpenAutoFocus={onOpenAutoFocus}\n onInteractOutside={onInteractOutside}\n />\n </TimePickerGroupContext.Provider>\n );\n}\n\ninterface TimePickerColumnContextValue {\n getItems: () => ItemData[];\n onItemRegister: (\n value: number | string,\n ref: React.RefObject<ColumnItemElement | null>,\n selected: boolean,\n disabled: boolean\n ) => void;\n onItemUnregister: (value: number | string) => void;\n}\n\nconst TimePickerColumnContext = React.createContext<TimePickerColumnContextValue | null>(null);\n\nfunction useTimePickerColumnContext(consumerName: string) {\n const context = React.useContext(TimePickerColumnContext);\n if (!context) {\n throw new Error(`\\`${consumerName}\\` phải nằm bên trong một cột (\\`${COLUMN_NAME}\\`)`);\n }\n return context;\n}\n\ninterface TimePickerColumnProps extends DivProps {}\n\nfunction TimePickerColumn(props: TimePickerColumnProps) {\n const { children, className, ref, ...columnProps } = props;\n\n const columnId = React.useId();\n const columnRef = React.useRef<ColumnElement | null>(null);\n const composedRef = useComposedRefs(ref, columnRef);\n\n const itemsRef = React.useRef<\n Map<\n number | string,\n {\n ref: React.RefObject<ColumnItemElement | null>;\n selected: boolean;\n disabled: boolean;\n }\n >\n >(new Map());\n\n const groupContext = useTimePickerGroupContext(COLUMN_NAME);\n\n const onItemRegister = React.useCallback(\n (value: number | string, ref: React.RefObject<HTMLButtonElement | null>, selected: boolean, disabled: boolean) => {\n itemsRef.current.set(value, { ref, selected, disabled });\n },\n []\n );\n\n const onItemUnregister = React.useCallback((value: number | string) => {\n itemsRef.current.delete(value);\n }, []);\n\n const getItems = React.useCallback(() => {\n const items = Array.from(itemsRef.current.entries())\n .map(([value, { ref, selected, disabled }]) => ({\n value,\n ref,\n selected,\n disabled\n }))\n .filter((item) => item.ref.current);\n return sortNodes(items);\n }, []);\n\n const getSelectedItemRef = React.useCallback(() => {\n const items = getItems();\n return items.find((item) => item.selected)?.ref ?? null;\n }, [getItems]);\n\n useIsomorphicLayoutEffect(() => {\n groupContext.onColumnRegister({\n id: columnId,\n ref: columnRef,\n getSelectedItemRef,\n getItems\n });\n return () => groupContext.onColumnUnregister(columnId);\n }, [groupContext, columnId, getSelectedItemRef, getItems]);\n\n const columnContextValue = React.useMemo<TimePickerColumnContextValue>(\n () => ({\n getItems,\n onItemRegister,\n onItemUnregister\n }),\n [getItems, onItemRegister, onItemUnregister]\n );\n\n return (\n <TimePickerColumnContext.Provider value={columnContextValue}>\n {/*\n * ⚠ Khác thượng nguồn: bản gốc là một `div` trần chứa các `button` trần — trình đọc màn hình\n * đọc \"14, nút\" mà không biết đó là cột GIỜ hay PHÚT, cũng không biết mục nào ĐANG CHỌN.\n * Cột là `listbox` (tên do `TimePickerHour`/`…Minute`/`…` truyền xuống), mục là `option`\n * có `aria-selected` — đúng với hành vi sẵn có: mũi tên lên/xuống vừa di focus vừa chọn.\n */}\n <div\n role=\"listbox\"\n ref={composedRef}\n data-slot=\"time-picker-column\"\n {...columnProps}\n className={cn(\"flex flex-col gap-1 p-1 not-last:border-r\", className)}\n >\n {children}\n </div>\n </TimePickerColumnContext.Provider>\n );\n}\n\ninterface TimePickerColumnItemProps extends ButtonProps {\n value: number | string;\n selected?: boolean;\n format?: SegmentFormat;\n}\n\nfunction TimePickerColumnItem(props: TimePickerColumnItemProps) {\n const {\n value,\n selected = false,\n // ⚠ Khác thượng nguồn (3.1.0): mục bị khoá theo `min`/`max` — xem cuối chú thích ở thẻ `<button>`.\n disabled = false,\n format = \"numeric\",\n className,\n children,\n ref,\n ...itemProps\n } = props;\n\n const itemRef = React.useRef<ColumnItemElement | null>(null);\n const composedRef = useComposedRefs(ref, itemRef);\n const columnContext = useTimePickerColumnContext(COLUMN_ITEM_NAME);\n const groupContext = useTimePickerGroupContext(COLUMN_ITEM_NAME);\n\n useIsomorphicLayoutEffect(() => {\n columnContext.onItemRegister(value, itemRef, selected, disabled);\n return () => columnContext.onItemUnregister(value);\n }, [columnContext, value, selected, disabled]);\n\n useIsomorphicLayoutEffect(() => {\n if (selected && itemRef.current) {\n itemRef.current.scrollIntoView({ block: \"nearest\" });\n }\n }, [selected]);\n\n const onClick = React.useCallback(\n (event: React.MouseEvent<ColumnItemElement>) => {\n // Mục bị khoá không chọn được — chuột đã bị `pointer-events-none` chặn, còn Enter/Space thì tới đây.\n if (disabled) {\n event.preventDefault();\n return;\n }\n\n itemProps.onClick?.(event);\n if (event.defaultPrevented) return;\n\n itemRef.current?.focus();\n },\n [itemProps.onClick, disabled]\n );\n\n const onKeyDown = React.useCallback(\n (event: React.KeyboardEvent<ColumnItemElement>) => {\n itemProps.onKeyDown?.(event);\n if (event.defaultPrevented) return;\n\n if (event.key === \"ArrowUp\" || event.key === \"ArrowDown\") {\n event.preventDefault();\n const items = columnContext.getItems().sort((a, b) => {\n if (typeof a.value === \"number\" && typeof b.value === \"number\") {\n return a.value - b.value;\n }\n return 0;\n });\n const currentIndex = items.findIndex((item) => item.value === value);\n\n /*\n * ⚠ Khác thượng nguồn (3.1.0): bỏ qua mục bị khoá theo `min`/`max` (vẫn vòng từ cuối về đầu\n * như bản gốc). Mũi tên vừa di focus vừa CHỌN, nên dừng trên một mục không chọn được thì\n * focus và giá trị tách nhau. Không còn mục nào khác chọn được thì đứng yên.\n */\n const step = event.key === \"ArrowUp\" ? -1 : 1;\n const start = currentIndex === -1 ? (step > 0 ? -1 : items.length) : currentIndex;\n let nextItem: ItemData | undefined;\n for (let offset = 1; offset <= items.length; offset++) {\n const candidate = items[(((start + step * offset) % items.length) + items.length) % items.length];\n if (candidate && !candidate.disabled) {\n nextItem = candidate;\n break;\n }\n }\n\n nextItem?.ref.current?.focus();\n nextItem?.ref.current?.click();\n } else if (event.key === \"Tab\" && groupContext) {\n /*\n * ⚠ Khác thượng nguồn (3.1.0): Tab / Shift+Tab đi qua các cột theo thứ tự rồi RA KHỎI dải\n * cột, tới phần tử nhận focus được kế tiếp trong bảng chọn (vd `TimePickerClear` đặt trong\n * bảng); hết bảng thì vòng về đầu như `FocusScope loop` của mọi popover trong gói. Bản gốc\n * vòng giữa các cột, nên mọi nút đặt trong bảng chỉ bấm được bằng chuột. Cùng lúc, mỗi cột chỉ\n * còn MỘT mục nhận Tab (`tabIndex` do cột đặt — xem `getColumnEntry`): Tab gốc từ nút ấy lùi\n * về đúng mục đang chọn của cột cuối, không rơi vào mục cuối của nó.\n *\n * Đích tính NGAY (focus chưa đổi), chỉ focus ở microtask như bản gốc: `FocusScope` của Radix\n * cũng bắt Tab trên chính bảng (sau handler này, không xét `defaultPrevented`) và tự vòng về\n * đầu/cuối khi phần tử đang focus là phần tử cuối/đầu — focus ngay tại đây thì nó sẽ thấy\n * phần tử MỚI và vòng thêm một lần nữa. Microtask chạy sau nó nên lời của handler này là lời\n * cuối (hai bên luôn cùng đích ở ca vòng).\n */\n const content = groupContext.contentRef.current;\n const column = groupContext.getColumns().find((c) => c.ref.current?.contains(itemRef.current) ?? false)\n ?.ref.current;\n if (!content || !column) return;\n\n event.preventDefault();\n const target = getTabTarget(content, column, event.shiftKey);\n if (target) queueMicrotask(() => focusTabbable(target));\n } else if ((event.key === \"ArrowLeft\" || event.key === \"ArrowRight\") && groupContext) {\n event.preventDefault();\n\n queueMicrotask(() => {\n const columns = groupContext.getColumns();\n\n if (columns.length === 0) return;\n\n const currentColumnIndex = columns.findIndex((c) => c.ref.current?.contains(itemRef.current) ?? false);\n\n if (currentColumnIndex === -1) return;\n\n // Mũi tên trái/phải vẫn vòng GIỮA CÁC CỘT như bản gốc (Tab thì không nữa — xem nhánh trên).\n const goToPrevious = event.key === \"ArrowLeft\";\n\n const nextColumnIndex = goToPrevious\n ? currentColumnIndex > 0\n ? currentColumnIndex - 1\n : columns.length - 1\n : currentColumnIndex < columns.length - 1\n ? currentColumnIndex + 1\n : 0;\n\n const nextColumn = columns[nextColumnIndex];\n if (nextColumn?.ref.current) {\n // ⚠ Khác thượng nguồn (3.1.0): vào mục đón (`getColumnEntry`) — bỏ qua mục bị khoá.\n focusFirst(getColumnEntryRefs(nextColumn.getItems()), false);\n }\n });\n }\n },\n [itemProps.onKeyDown, columnContext, groupContext, value]\n );\n\n const formattedValue =\n typeof value === \"number\" && format === \"2-digit\" ? value.toString().padStart(2, \"0\") : value.toString();\n\n return (\n <button\n type=\"button\"\n // Xem chú thích ở `TimePickerColumn`: mục là `option`, trạng thái chọn đi qua `aria-selected`.\n role=\"option\"\n aria-selected={selected}\n aria-disabled={disabled || undefined}\n {...itemProps}\n ref={composedRef}\n data-selected={selected ? \"\" : undefined}\n data-disabled={disabled ? \"\" : undefined}\n className={cn(\n /*\n * ⚠ Khác thượng nguồn: focus đi theo khuôn `Checkbox`/`Calendar` của gói (`focus-visible`,\n * có offset — mục đang chọn tô nền vàng, quầng vàng dính sát nền vàng thì không thấy);\n * mục đang chọn dùng cặp token của control BẬT `--control-on` / `--control-check` thay\n * `bg-primary text-primary-foreground` — cùng lý do và số đo với ô ngày đang chọn của\n * `Calendar` (chú thích đầu `calendar.tsx`). Hover chỉ áp cho mục CHƯA chọn\n * (`not-data-selected:`) thay vì để `data-selected:hover:` ghi đè lại: cùng kết quả trên\n * màn hình, nhưng cách cũ khiến `pnpm lint:a11y` ghép chữ hover `--accent-foreground`\n * với nền mục đang chọn (1,39:1 ở dark) — một cặp không bao giờ xuất hiện.\n *\n * ⚠ Khác thượng nguồn (3.1.0): mục bị khoá theo `min`/`max` mờ và không nhận chuột theo đúng\n * khuôn mục vô hiệu của gói (`DropdownMenu`, `Select`, `Mention`…: `pointer-events-none` +\n * `opacity-50`). Dùng `aria-disabled` chứ KHÔNG dùng `disabled` gốc: mục vẫn nhận focus, nên\n * một cột bị khoá TOÀN BỘ vẫn là một điểm dừng Tab (mục đón rơi vào nó — `getColumnEntry`) mà\n * trình đọc màn hình đọc là \"không khả dụng\", thay vì cả cột biến mất khỏi thứ tự Tab. Chọn\n * thì không được: `onClick` chặn (Enter/Space), mũi tên lên/xuống bỏ qua.\n */\n \"w-full rounded px-3 py-1.5 text-left text-sm not-data-selected:hover:bg-accent not-data-selected:hover:text-accent-foreground focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring/50 focus-visible:ring-offset-2 focus-visible:ring-offset-background\",\n \"data-selected:bg-control-on data-selected:text-control-check\",\n \"data-disabled:pointer-events-none data-disabled:opacity-50\",\n className\n )}\n onClick={onClick}\n onKeyDown={onKeyDown}\n >\n {/* ⚠ Khác thượng nguồn: nhận `children` (cột buổi in `labels.am`/`labels.pm` thay mã \"AM\"/\"PM\"). */}\n {children ?? formattedValue}\n </button>\n );\n}\n\ninterface TimePickerHourProps extends DivProps {\n format?: SegmentFormat;\n}\n\nfunction TimePickerHour(props: TimePickerHourProps) {\n const { asChild, format = \"numeric\", className, ...hourProps } = props;\n\n const { is12Hour, hourStep, showSeconds, disabled, readOnly, labels, timeRange } = useTimePickerContext(HOUR_NAME);\n const store = useStoreContext(HOUR_NAME);\n\n const value = useStore((state) => state.value);\n const timeValue = parseTimeString(value);\n\n const hours = Array.from(\n {\n length: is12Hour ? Math.ceil(12 / hourStep) : Math.ceil(24 / hourStep)\n },\n (_, i) => {\n if (is12Hour) {\n const hour = (i * hourStep) % 12;\n return hour === 0 ? 12 : hour;\n }\n return i * hourStep;\n }\n );\n\n const onHourSelect = React.useCallback(\n (displayHour: number) => {\n /*\n * ⚠ Khác thượng nguồn: bản gốc cho cột đổi giá trị cả khi `readOnly`/`disabled` — bảng chọn\n * vẫn mở được (nút mở chỉ khoá theo `disabled`, `openOnFocus` không xét gì), nên một ô\n * \"chỉ đọc\" vẫn sửa được bằng chuột. `TimePickerClear` của chính nó đã chặn đúng hai cờ\n * này; bốn cột nay chặn theo cùng luật.\n */\n if (disabled || readOnly) return;\n\n // ⚠ Khác thượng nguồn (3.1.0): thân cũ nằm ở `buildHourTime`; giá trị dựng ra được kẹp theo\n // `min`/`max`, giữ giờ vừa chọn (`constrainTime`).\n const newTime = buildHourTime(\n timeValue,\n displayHour,\n is12Hour,\n showSeconds,\n getReferenceTime(timeRange, showSeconds)\n );\n const newValue = formatTimeValue(constrainTime(newTime, timeRange, showSeconds, \"hour\"), showSeconds);\n store.setState(\"value\", newValue);\n },\n [timeValue, showSeconds, is12Hour, disabled, readOnly, store, timeRange]\n );\n\n const reference = getReferenceTime(timeRange, showSeconds);\n const referenceHour = timeValue?.hour ?? reference.hour;\n const displayHour = is12Hour ? to12Hour(referenceHour).hour : referenceHour;\n\n /*\n * ⚠ Khác thượng nguồn (3.1.0), cho cả bốn cột:\n * - mục bị khoá khi ô của nó không còn thời điểm nào nằm trong `min`/`max` (`isSegmentAllowed`, xét\n * trên đúng giá trị mà bấm vào mục sẽ dựng ra);\n * - cột chỉ để MỘT mục nhận Tab — mục đón `getColumnEntry` (`tabIndex={0}`), còn lại `-1`. Bản gốc để\n * cả 24/60 mục là điểm dừng Tab: Tab gốc từ một nút khác trong bảng rơi vào mục đầu/cuối của cột\n * chứ không vào mục đang chọn, và `FocusScope` lấy mục cuối của cột cuối làm \"phần tử cuối bảng\".\n */\n const items = hours.map((hour) => ({\n value: hour,\n selected: displayHour === hour,\n disabled: !isSegmentAllowed(\n buildHourTime(timeValue, hour, is12Hour, showSeconds, reference),\n \"hour\",\n timeRange,\n showSeconds\n )\n }));\n const entry = getColumnEntry(items);\n\n const HourPrimitive = asChild ? Slot : TimePickerColumn;\n\n return (\n <HourPrimitive\n data-slot=\"time-picker-hour\"\n aria-label={labels.hour}\n {...hourProps}\n className={cn(\"scrollbar-none flex max-h-[200px] flex-col gap-1 overflow-y-auto p-1\", className)}\n >\n {items.map((item) => (\n <TimePickerColumnItem\n key={item.value}\n value={item.value}\n selected={item.selected}\n disabled={item.disabled}\n tabIndex={item === entry ? 0 : -1}\n format={format}\n onClick={() => onHourSelect(item.value)}\n />\n ))}\n </HourPrimitive>\n );\n}\n\ninterface TimePickerMinuteProps extends DivProps {\n format?: SegmentFormat;\n}\n\nfunction TimePickerMinute(props: TimePickerMinuteProps) {\n const { asChild, format = \"2-digit\", className, ...minuteProps } = props;\n\n const { minuteStep, showSeconds, disabled, readOnly, labels, timeRange } = useTimePickerContext(MINUTE_NAME);\n const store = useStoreContext(MINUTE_NAME);\n\n const value = useStore((state) => state.value);\n const timeValue = parseTimeString(value);\n\n const minutes = Array.from({ length: Math.ceil(60 / minuteStep) }, (_, i) => i * minuteStep);\n\n const onMinuteSelect = React.useCallback(\n (minute: number) => {\n // Chặn `readOnly`/`disabled` — xem `TimePickerHour`.\n if (disabled || readOnly) return;\n\n // ⚠ Khác thượng nguồn (3.1.0): thân cũ nằm ở `buildMinuteTime`; kẹp giữ phút vừa chọn.\n const newTime = buildMinuteTime(timeValue, minute, showSeconds, getReferenceTime(timeRange, showSeconds));\n const newValue = formatTimeValue(constrainTime(newTime, timeRange, showSeconds, \"minute\"), showSeconds);\n store.setState(\"value\", newValue);\n },\n [timeValue, showSeconds, disabled, readOnly, store, timeRange]\n );\n\n const MinutePrimitive = asChild ? Slot : TimePickerColumn;\n\n const reference = getReferenceTime(timeRange, showSeconds);\n const referenceMinute = timeValue?.minute ?? reference.minute;\n\n // Mục bị khoá + một điểm dừng Tab mỗi cột — xem `TimePickerHour`.\n const items = minutes.map((minute) => ({\n value: minute,\n selected: referenceMinute === minute,\n disabled: !isSegmentAllowed(\n buildMinuteTime(timeValue, minute, showSeconds, reference),\n \"minute\",\n timeRange,\n showSeconds\n )\n }));\n const entry = getColumnEntry(items);\n\n return (\n <MinutePrimitive\n data-slot=\"time-picker-minute\"\n aria-label={labels.minute}\n {...minuteProps}\n className={cn(\"scrollbar-none flex max-h-[200px] flex-col gap-1 overflow-y-auto p-1\", className)}\n >\n {items.map((item) => (\n <TimePickerColumnItem\n key={item.value}\n value={item.value}\n selected={item.selected}\n disabled={item.disabled}\n tabIndex={item === entry ? 0 : -1}\n format={format}\n onClick={() => onMinuteSelect(item.value)}\n />\n ))}\n </MinutePrimitive>\n );\n}\n\ninterface TimePickerSecondProps extends DivProps {\n format?: SegmentFormat;\n}\n\nfunction TimePickerSecond(props: TimePickerSecondProps) {\n const { asChild, format = \"2-digit\", className, ...secondProps } = props;\n\n const { secondStep, showSeconds, disabled, readOnly, labels, timeRange } = useTimePickerContext(SECOND_NAME);\n const store = useStoreContext(SECOND_NAME);\n\n const value = useStore((state) => state.value);\n const timeValue = parseTimeString(value);\n\n const seconds = Array.from({ length: Math.ceil(60 / secondStep) }, (_, i) => i * secondStep);\n\n const onSecondSelect = React.useCallback(\n (second: number) => {\n // Chặn `readOnly`/`disabled` — xem `TimePickerHour`.\n if (disabled || readOnly) return;\n\n // ⚠ Khác thượng nguồn (3.1.0): thân cũ nằm ở `buildSecondTime`; kẹp giữ giây vừa chọn.\n const newTime = buildSecondTime(timeValue, second, getReferenceTime(timeRange, showSeconds));\n const newValue = formatTimeValue(constrainTime(newTime, timeRange, showSeconds, \"second\"), true);\n store.setState(\"value\", newValue);\n },\n [timeValue, showSeconds, disabled, readOnly, store, timeRange]\n );\n\n const SecondPrimitive = asChild ? Slot : TimePickerColumn;\n\n const reference = getReferenceTime(timeRange, showSeconds);\n const referenceSecond = timeValue?.second ?? reference.second;\n\n // Mục bị khoá + một điểm dừng Tab mỗi cột — xem `TimePickerHour`.\n const items = seconds.map((second) => ({\n value: second,\n selected: referenceSecond === second,\n disabled: !isSegmentAllowed(buildSecondTime(timeValue, second, reference), \"second\", timeRange, showSeconds)\n }));\n const entry = getColumnEntry(items);\n\n return (\n <SecondPrimitive\n data-slot=\"time-picker-second\"\n aria-label={labels.second}\n {...secondProps}\n className={cn(\"scrollbar-none flex max-h-[200px] flex-col gap-1 overflow-y-auto p-1\", className)}\n >\n {items.map((item) => (\n <TimePickerColumnItem\n key={item.value}\n value={item.value}\n selected={item.selected}\n disabled={item.disabled}\n tabIndex={item === entry ? 0 : -1}\n format={format}\n onClick={() => onSecondSelect(item.value)}\n />\n ))}\n </SecondPrimitive>\n );\n}\n\ntype TimePickerPeriodProps = DivProps;\n\nfunction TimePickerPeriod(props: TimePickerPeriodProps) {\n const { asChild, className, ...periodProps } = props;\n\n const { is12Hour, showSeconds, disabled, readOnly, labels, timeRange } = useTimePickerContext(PERIOD_NAME);\n const store = useStoreContext(PERIOD_NAME);\n\n const value = useStore((state) => state.value);\n const timeValue = parseTimeString(value);\n\n const onPeriodToggle = React.useCallback(\n (period: Period) => {\n // Chặn `readOnly`/`disabled` — xem `TimePickerHour`.\n if (disabled || readOnly) return;\n\n // ⚠ Khác thượng nguồn (3.1.0): thân cũ nằm ở `buildPeriodTime`; kẹp giữ buổi vừa chọn (10:30 SA\n // sang CH với khung 09:00–17:00 → 17:00, không phải 22:30).\n const newTime = buildPeriodTime(timeValue, period, showSeconds, getReferenceTime(timeRange, showSeconds));\n const newValue = formatTimeValue(constrainTime(newTime, timeRange, showSeconds, \"period\"), showSeconds);\n store.setState(\"value\", newValue);\n },\n [timeValue, showSeconds, disabled, readOnly, store, timeRange]\n );\n\n if (!is12Hour) return null;\n\n const reference = getReferenceTime(timeRange, showSeconds);\n const referenceHour = timeValue?.hour ?? reference.hour;\n const currentPeriod = to12Hour(referenceHour).period;\n\n // Mục bị khoá + một điểm dừng Tab mỗi cột — xem `TimePickerHour`.\n const items = PERIODS.map((period) => ({\n value: period,\n selected: currentPeriod === period,\n disabled: !isSegmentAllowed(\n buildPeriodTime(timeValue, period, showSeconds, reference),\n \"period\",\n timeRange,\n showSeconds\n )\n }));\n const entry = getColumnEntry(items);\n\n const PeriodPrimitive = asChild ? Slot : TimePickerColumn;\n\n return (\n <PeriodPrimitive\n data-slot=\"time-picker-period\"\n aria-label={labels.period}\n {...periodProps}\n className={cn(\"flex flex-col gap-1 p-1\", className)}\n >\n {items.map((item) => (\n <TimePickerColumnItem\n key={item.value}\n value={item.value}\n selected={item.selected}\n disabled={item.disabled}\n tabIndex={item === entry ? 0 : -1}\n onClick={() => onPeriodToggle(item.value)}\n >\n {getPeriodLabel(item.value, labels)}\n </TimePickerColumnItem>\n ))}\n </PeriodPrimitive>\n );\n}\n\ninterface TimePickerSeparatorProps extends React.ComponentProps<\"span\"> {\n asChild?: boolean;\n}\n\nfunction TimePickerSeparator(props: TimePickerSeparatorProps) {\n const { asChild, children, ...separatorProps } = props;\n\n const SeparatorPrimitive = asChild ? Slot : \"span\";\n\n return (\n <SeparatorPrimitive aria-hidden=\"true\" data-slot=\"time-picker-separator\" {...separatorProps}>\n {children ?? \":\"}\n </SeparatorPrimitive>\n );\n}\n\ntype TimePickerClearProps = ButtonProps;\n\nfunction TimePickerClear(props: TimePickerClearProps) {\n const { asChild, className, children, disabled: disabledProp, ...clearProps } = props;\n\n const { disabled, readOnly, labels } = useTimePickerContext(CLEAR_NAME);\n const store = useStoreContext(CLEAR_NAME);\n\n const isDisabled = disabledProp || disabled;\n\n const onClick = React.useCallback(\n (event: React.MouseEvent<HTMLButtonElement>) => {\n clearProps.onClick?.(event);\n if (event.defaultPrevented) return;\n\n event.preventDefault();\n if (disabled || readOnly) return;\n store.setState(\"value\", \"\");\n },\n [clearProps.onClick, disabled, readOnly, store]\n );\n\n const ClearPrimitive = asChild ? Slot : \"button\";\n\n return (\n <ClearPrimitive\n type=\"button\"\n data-slot=\"time-picker-clear\"\n disabled={isDisabled}\n {...clearProps}\n className={cn(\n // Viền focus theo khuôn `Button` — xem `TimePickerTrigger`.\n \"inline-flex items-center justify-center rounded-sm text-sm font-medium transition-colors hover:bg-accent hover:text-accent-foreground focus-visible:outline-2 focus-visible:outline-ring focus-visible:outline-offset-2 disabled:pointer-events-none disabled:opacity-50\",\n className\n )}\n onClick={onClick}\n >\n {children ?? labels.clear}\n </ClearPrimitive>\n );\n}\n\nexport {\n TimePicker,\n TimePickerClear,\n type TimePickerClearProps,\n TimePickerContent,\n type TimePickerContentProps,\n TimePickerHour,\n type TimePickerHourProps,\n TimePickerInput,\n TimePickerInputGroup,\n type TimePickerInputGroupProps,\n type TimePickerInputProps,\n TimePickerLabel,\n type TimePickerLabelProps,\n TimePickerMinute,\n type TimePickerMinuteProps,\n TimePickerPeriod,\n type TimePickerPeriodProps,\n type TimePickerProps,\n TimePickerSecond,\n type TimePickerSecondProps,\n TimePickerSeparator,\n type TimePickerSeparatorProps,\n TimePickerTrigger,\n type TimePickerTriggerProps,\n useStore as useTimePicker\n};\n"],"mappings":"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","names":["value","ref","displayHour"]}