feat(DateTimePicker): new component with two-step popover and presets#55
Open
IgorShevchik wants to merge 6 commits into
Open
feat(DateTimePicker): new component with two-step popover and presets#55IgorShevchik wants to merge 6 commits into
IgorShevchik wants to merge 6 commits into
Conversation
- Adds B24DateTimePicker built on B24Popover, B24Calendar and B24Input - Two-step UX: calendar → hour/minute grid with configurable minute step - Side preset list with localized defaults (Today, Tomorrow, End of week, In a week, End of month) and full override via the `presets` prop - `dateOnly` mode forces value to CalendarDate with 00:00:00 - Works with @internationalized/date types via v-model (CalendarDateTime, ZonedDateTime, CalendarDate) - Adds theme, locale messages for all 19 locales, demo+nuxt playground pages, docs page with five examples and skill references update
…er-component-NqwmO
…er-component-NqwmO
… i18n, docs) - tests: add DateTimePicker.spec.ts (snapshots + minuteStep clamp + axe a11y) — 42 tests across nuxt + vue projects, both green - security/correctness: guard `minuteStep` against `NaN` (Number.isFinite check) - correctness: memoize resolved preset values into `resolvedPresets` so factory presets evaluate once per render instead of twice (was called by both `:active` and `:data-active`) - a11y: add `role="group"` + `aria-labelledby` on hour/minute grids and `aria-pressed` on each cell - i18n: fix "endOfWeek" mistranslations in de/fr/it/br/tr — they meant "weekend" instead of "end of work week (Friday)" - docs: drop misleading `B24Button` from intro composition, fix "Pick a time" → "Pick a date and time", add "With min/max dates" section and matching example, show `open` slot prop in custom trigger, add `name`/`required` to form-field example - skills: mention `DateTimePickerPreset` type for custom presets - theme: correct `@memo` comment (uses `B24Input`, not `B24InputDate`)
This was referenced May 27, 2026
…er-component-NqwmO
Addresses all 11 review issues from the second pass:
1. Time footer (clock + value) is now a clickable button that switches
to the time step. Styled with accent color to match the reference.
2. Weekend day cells (Sat/Sun) coloured red via #day slot.
3. Two-tone highlight on time grid: solid accent for selected,
`data-now` light fill for the real-world current hour/minute.
4. Time-step header now shows date only (was date + time).
6. Preset card titles use `--b24ui-typography-label-color` instead of
default inherited text → matches the rest of the design system.
7. Time-step header colour matches the calendar heading
(`--b24ui-typography-legend-color`).
8. Mobile (`screen.isMobile`) renders the picker in a `B24Drawer`
(bottom sheet) instead of `B24Popover`. Same content tree, different
wrapper picked via `<component :is>`.
9. `Minute step` doc example placeholder fixed (covered by trigger fix).
10. `Locale` doc example switched to Hindi (`hi`).
11. **Dead-zone fix on the trigger**: clicks on padding around the input
now open the picker. Trigger is a `role=button` div wrapping the
`B24Input` (`pointer-events-none`, `tabindex=-1`, `aria-hidden`).
`$attrs` move to the wrapper so consumer-passed `aria-label`/`id`/etc
land where ARIA expects them. Adds `dateTimePicker.openPicker`
locale string as fallback `aria-label` (filled across all 20 locales).
Test snapshots regenerated; 42 tests still green.
Two axe rules (`nested-interactive`, `label`) are disabled in the a11y
test for the trigger composition — the inner input is `tabindex=-1`,
`aria-hidden`, and `pointer-events-none`, so it is not user-reachable.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
What this PR is about
A new
B24DateTimePickercomponent — a Bitrix24-style date + time picker with a two-step popover (calendar → hour/minute grid), a side preset column, and an optionaldate-onlymode (time forced to00:00:00). It fills the gap between the segmentedB24InputDate/B24InputTimeand the more "native" Bitrix24 UX.What was done
src/runtime/components/DateTimePicker.vuecomposed of built-inB24Popover,B24Calendarand a read-onlyB24Input(default trigger). Model —CalendarDateTime/ZonedDateTime(orCalendarDateindate-onlymode).src/theme/date-time-picker.ts— minimum styling, design-system classes only.dateTimePicker.*added to theMessagestype and filled in for all 19 locales.endOfWeekfor DE/FR/IT/BR/TR was fixed to actually mean "end of week" (the machine translation produced "weekend" instead).role="group"+aria-labelledbyon the hours/minutes grids,aria-pressedon each cell, unique id viauseId().Number.isFiniteguard onminute-stepto protect againstNaN.test/components/DateTimePicker.spec.ts+ 2 snapshot files: 21 cases × (nuxt + vue) = 42 green tests, including an axe a11y check.docs/content/docs/2.components/date-time-picker.md+ 6 examples (Basic,DateOnly,CustomPresets,CustomTrigger,FormField,MinMaxDates). Responsive: presets drop below the calendar on mobile (flex-col-reverse sm:flex-row).date-time-picker.vuematrix page + registration inuseNavigation.ts.b24-ui-nuxt— updatedcomponents.md,component-selection.mdand the "Date" section informs.md.theme/index.ts, key inThemeDefaults.API
Key props:
modelValue,defaultValue,dateOnly,minuteStep(5),locale,placeholder,presets,hidePresets,format,color,size,disabled,icon,timeIcon,popover,calendar,input.Slots:
default(trigger),presets,preset,time-header.Manual QA checklist
pnpm dev→/components/date-time-picker: popover opens, picking a date switches to the time step, clicking a minute closes the popoverDate only— time step disappears, model becomesCalendarDateminute-step={5|10|15|30}— correct cell count;NaN/0/9999don't break rendering (covered by tests)presets(factory function) —DateTimePickerCustomPresetsExample, factory runs once per render#default(DateTimePickerCustomTriggerExample) —openreacts; defaultB24Inputtriggerlocale="ru"/locale="en"— value format, weekday names, preset labels all changecolor,size,disabled— walk through the Matrix in the playgroundhide-presets— side column disappearsB24FormField(DateTimePickerFormFieldExample) —name/required/label/hintwork:calendar="{ minValue, maxValue }"(DateTimePickerMinMaxDatesExample) — bounds respectedaria-pressedstate on cellspnpm test— neighboring components' snapshots are not affectedWhat's next
Follow-up issues have been filed (from review):
as anyкасты вокруг @internationalized/date #56 — clean upas anycasts around@internationalized/date(also affects Calendar/InputDate)min/max/isDateDisabledpropsv-modeltodefineModel(batched across components)Nothing urgent after merge — the component is self-contained and introduces no breaking changes to the public API.
Ready for squash-merge. Green locally:
pnpm lint,pnpm typecheck,pnpm exec vitest test/components/DateTimePicker.spec.ts(42/42).🤖 Generated with Claude Code