Skip to content

Date Picker

A single-date calendar picker. The day grid is dynamic, so you provide <template>s for a weekday header, a week row, and a day cell; stimulus-zag renders the month from Zag's calendar model and re-applies today/selected/disabled state.

html
<div data-controller="zag-date-picker" data-part="root" class="relative inline-block">
  <div data-part="control" class="flex">
    <input
      data-part="input"
      placeholder="YYYY-MM-DD"
      class="border-input bg-popover focus:ring-ring/50 rounded-l-lg border px-3 py-2 text-sm focus:outline-none focus:ring-2"
    />
    <button
      data-part="trigger"
      class="border-input hover:bg-accent rounded-r-lg border border-l-0 px-3"
      aria-label="Open calendar"
    >
      📅
    </button>
  </div>
  <div data-part="positioner">
    <div
      data-part="content"
      hidden
      class="border-border bg-popover z-50 mt-1 rounded-lg border p-3 shadow-lg"
    >
      <div data-part="view-control" class="mb-2 flex items-center justify-between">
        <button
          data-part="prev-trigger"
          class="hover:bg-accent rounded px-2 py-1"
          aria-label="Previous month"
        >

        </button>
        <button
          data-part="view-trigger"
          class="hover:bg-accent rounded px-2 py-1 text-sm font-medium"
        >
          <span data-part="range-text"></span>
        </button>
        <button
          data-part="next-trigger"
          class="hover:bg-accent rounded px-2 py-1"
          aria-label="Next month"
        >

        </button>
      </div>
      <div data-part="table">
        <div data-part="table-head">
          <div
            data-zag-date-picker-target="weekdays"
            role="row"
            class="grid grid-cols-7 text-center"
          ></div>
        </div>
        <div data-part="table-body" data-zag-date-picker-target="weeks" class="mt-1"></div>
      </div>
    </div>
  </div>

  <template data-zag-date-picker-target="weekdayTemplate"
    ><span role="columnheader" class="text-muted-foreground py-1 text-xs font-medium"></span
  ></template>
  <template data-zag-date-picker-target="dayRowTemplate"
    ><div data-part="table-row" role="row" class="grid grid-cols-7"></div
  ></template>
  <template data-zag-date-picker-target="dayCellTemplate">
    <div data-part="table-cell" class="p-0.5 text-center">
      <button
        data-part="table-cell-trigger"
        class="hover:bg-accent data-[selected]:bg-primary data-[outside-range]:text-muted-foreground data-[selected]:text-primary-foreground h-9 w-9 rounded-full text-sm data-[today]:font-bold data-[disabled]:opacity-30"
      ></button>
    </div>
  </template>
</div>

Uses divs with ARIA roles (Zag sets role="grid"/gridcell) so the grid works with any template. A real <table> works in browsers too.

Parts

root, label, control, input, trigger, clear-trigger, positioner, content, view-control, prev-trigger, next-trigger, view-trigger, range-text, table, table-head, table-body, table-row, table-cell, table-cell-trigger.

Targets: weekdays, weekdayTemplate, weeks, dayRowTemplate, dayCellTemplate.

Values

AttributeTypeDefaultDescription
data-zag-date-picker-value-valueArray[]Selected date(s), ISO YYYY-MM-DD.
data-zag-date-picker-min-valueString""Earliest selectable date (ISO).
data-zag-date-picker-max-valueString""Latest selectable date (ISO).
data-zag-date-picker-locale-valueString"en-US"Locale for formatting.
data-zag-date-picker-start-of-week-valueNumber0First day of week (0 = Sunday).
data-zag-date-picker-close-on-select-valueBooleantrueClose after selecting.
data-zag-date-picker-open-valueBooleanfalseOpen by default.
data-zag-date-picker-inline-valueBooleanfalseAlways-open inline calendar.
data-zag-date-picker-name-valueString""name for form submission.
data-zag-date-picker-disabled-valueBooleanfalseDisable the picker.
data-zag-date-picker-read-only-valueBooleanfalseRead-only.
data-zag-date-picker-required-valueBooleanfalseMark required.

Events

Emits zag-date-picker:change ({ value, dates }, value is ISO strings) and zag-date-picker:open-change.

Programmatic control

value (getter, ISO strings), setValue(isoStrings), clear(), open(), close(), isOpen.