Date picker
The custom element is <hui-date-picker>.
Overview
A form-associated text input with a calendar in a popover. Typing an ISO date and picking a day produce the same value, and what is submitted is always ISO whatever the display locale.
Example
Source
<hui-date-picker name="due" value="2024-02-15" aria-label="Due date"></hui-date-picker>The Go template that renders it:
<hui-date-picker name="{{ .Name }}" value="{{ .Value }}" min="{{ .Min }}" max="{{ .Max }}" aria-label="{{ .Label }}"></hui-date-picker>API
Attributes10
| Name | Type | Default | Description |
|---|---|---|---|
name | string | "" | The form field name. Without one the control submits nothing. |
value | string | "" | The selected ISO date. Reflects to the value attribute; a non-ISO value submits nothing. |
placeholder | string | "YYYY-MM-DD" | Placeholder shown in the input while it is empty. |
required | boolean | false | Marks the field required and blocks submission while no valid date is set. |
min | string | "" | Inclusive lower bound, forwarded to the calendar and the input. |
max | string | "" | Inclusive upper bound, forwarded to the calendar and the input. |
locale | string | "" | BCP 47 locale for the embedded calendar. |
week-start | number | 0 | First day of the week for the embedded calendar, 0 for Sunday. |
open | boolean | false | Whether the calendar panel is open. Reflects to the open attribute. |
disabled | boolean | false | Disables the input and the toggle, and prevents the panel from opening. |
Properties10
| Name | Type | Default | Description |
|---|---|---|---|
name | string | '' | Reflects to the name attribute. |
value | string | '' | Reflects to the value attribute. |
placeholder | string | 'YYYY-MM-DD' | Reflects to the placeholder attribute. |
required | boolean | false | Reflects to the required attribute. |
min | string | '' | Reflects to the min attribute. |
max | string | '' | Reflects to the max attribute. |
locale | string | '' | Reflects to the locale attribute. |
week-start | number | 0 | Reflects to the week-start attribute. |
open | boolean | false | Reflects to the open attribute. |
disabled | boolean | false | Reflects to the disabled attribute. |
Events4
| Name | Description |
|---|---|
input | Emitted on the host when a day is picked, a typed date is committed or the field is cleared. It bubbles and is composed. |
change | Emitted alongside input for the same commits. It bubbles and is composed. |
hui-open | Emitted when the calendar panel opens, including via the platform popover's light dismiss. It bubbles and is composed. |
hui-close | Emitted when the calendar panel closes. It bubbles and is composed. |
CSS custom properties5
| Name | Default | Description |
|---|---|---|
--hui-popover | oklch(1 0 0) | Background of the calendar panel. |
--hui-input | oklch(0.62 0.019 323.02) | Border of the field, and of the invalid field. |
--hui-destructive | oklch(0.56 0.245 27.325) | Border of the field while aria-invalid="true". |
--hui-radius-md | calc(var(--hui-radius, 0.45rem) * 0.8) | Corner radius of the field and the panel. |
--hui-muted-foreground | oklch(0.542 0.034 322.5) | Colour of the calendar toggle glyph. |
::part() hooks4
| Name | Description |
|---|---|
field | The bordered container that anchors the panel. |
input | The internal native text input. |
toggle | The "Choose date" button. |
panel | The popover containing the hui-calendar. |
States
Empty
With no value the trigger shows its placeholder until a date is chosen.
Source
<hui-date-picker name="other" placeholder="YYYY-MM-DD" aria-label="Other date"></hui-date-picker>Bounded and required
Bounds and required, passed through to both the calendar inside and the form outside.
Source
<hui-date-picker name="slot" value="2024-02-15" min="2024-02-10" max="2024-02-20" required aria-label="Slot"></hui-date-picker>Disabled
Disabled: the trigger does not open and the value still submits nothing.
Source
<hui-date-picker name="locked" value="2024-02-15" disabled aria-label="Locked date"></hui-date-picker>Server-side mechanics
The server renders <hui-date-picker> with a name and an ISO value, plus optional min, max, required, locale and week-start. It is form-associated: the ISO date submits under that name, a malformed typed date submits nothing and blocks submission, and with no name it submits nothing. The server must not send calendar markup, because the element builds the embedded <hui-calendar> itself. An hx-swap that replaces the picker while its panel is open closes the panel and discards any date typed but not committed.
Accessibility
- The internal input is the form control and receives the host's
aria-labelandaria-invalid. - A malformed typed date sets
badInput;requiredwith no valid date setsvalueMissing, both reported through ElementInternals. - The toggle has the accessible name "Choose date".
- The calendar panel is a native
popover="auto", so the platform supplies light dismiss.
Keyboard
| Keys | Action |
|---|---|
Printable characters | Type an ISO date; a valid one commits to the form, a malformed one blocks submission. |
Enter, Space | Activate the toggle to open or close the calendar. |
Calendar grid keys | Once open, the embedded calendar handles arrows, Page Up/Down and Home/End; Enter or Space picks the focused day and closes the panel. |
Gotchas
- The picker does not emit
hui-select: it listens for the embedded calendar'shui-selectand stops it, so only the syntheticinputandchangeescape to the host. - The submitted value is always ISO; a non-ISO
value, or a half-typed date, submits nothing and is reported asbadInputorvalueMissingthrough ElementInternals.