DatePicker Composition

Typing and picking, both. Typing is what fast people do and what a date of birth needs; the calendar answers the "second Tuesday" questions a text field cannot.

Usage

Type 18/08/2026, or pick it.

Selected: 2026-08-18

tsx
<Field label="Invoice date">  <DatePicker value={date} onValueChange={setDate} min={start} max={end} /></Field>

What the parsing does

  • ISO first, then day-first with /, -, or .. Day-first because that is what most of the world writes, and an ambiguous 03/04 has to pick a side and say so.
  • A two-digit year expands into this century.
  • 31 February is rejected, rather than rolling quietly into March — the classic new Date() trap.
  • Unparseable text clears the value on blur instead of silently keeping the old date, which is the version that ships wrong data.
  • The grid is always six weeks, so the popover does not change height between months.

Do

Pass min and max when the range is known — out-of-range days are disabled rather than merely rejected afterwards.

Don't

Use it for a month or a year on its own; a Select with twelve options is faster and unambiguous.

Opening

Clicking the field opens the calendar, and so does the calendar button. Typing still works either way, and the popover anchors to the whole field rather than to the button, so it lines up with the control however it was opened. Times of day are the TimePicker's job.

Props

PropTypeDefaultNotes
value / defaultValueDate | nullLocal calendar dates. Time is ignored.
onValueChange(value: Date | null) => voidFires on blur and on picking a day.
min / maxDateInclusive bounds. Days outside are disabled.
format(date: Date) => stringHow the chosen date reads in the field. Defaults to the viewer’s locale.
weekStartsOn0 | 11Monday by default; 0 for Sunday.