Calendar
ProA month of days to pick one from. Days follow the locale: month and weekday names, the first day of the week and the digits. Nothing is selected until the person picks a day; today is outlined, not selected. A day you mark unavailable stays reachable by keyboard, is aria-disabled, and says why (needs a TooltipProvider).
Keyboard: arrow keys move by a day or a week, Home and End to the start and end of the week, Page Up and Page Down by a month (with Shift by a year), Enter or Space selects. A day is a calendar date, not an instant.
Version 5.2.0· other versions
This page is for 5.2.0, the current release. An earlier release’s page is the Markdown that release published, so the docs match the version you have installed (candor-lock.json records it).
- 5.1.0
- 5.0.0
- 4.5.0
- 4.4.0
- 4.3.0
- 4.2.0
- 4.1.0
- 4.0.2
- 4.0.1
- 4.0.0
- 3.0.0
- 2.10.0
- 2.9.0
- 2.8.0
- 2.7.0
- 2.6.2
- 2.6.1
- 2.6.0
- 2.5.1
- 2.5.0
- 2.4.0
- 2.3.0
Not in the docs of 1.3.0, 1.4.0, 1.5.0, 1.5.1, 1.6.0, 1.7.0, 1.8.0, 1.8.1, 1.9.0, 1.9.1, 2.0.0, 2.1.0 and 2.2.0: the page came later, or had another name then.
Docs pages weren’t kept for 1.0.0, 1.0.1, 1.1.0, 1.1.1, 1.2.0 and 1.2.1: they are kept from 1.3.0 on, and before that only llms.txt was published.
Preview
Loading the preview
Install
First time? Get started sets up the registry and theme. Or with shadcn directly: npx shadcn@latest add @candor/calendar
Brings in: bidi, button, locale, locked, tokens, utils · npm: lucide-react@^1.67.0
Usage
"use client"
import * as React from "react"
import { Calendar, useDayFormat } from "@/components/candor/ui/calendar"
// Weekends are closed for deploys here, and each closed day says so. Nothing is selected until a day is picked.
export default function Example() {
const [day, setDay] = React.useState<Date | undefined>()
const format = useDayFormat()
return (
<div className="flex flex-col items-start gap-3">
<Calendar
defaultMonth={new Date(2026, 10, 1)}
today={new Date(2026, 10, 8)}
value={day ?? null}
onValueChange={setDay}
unavailable={(d) => (d.getDay() === 0 || d.getDay() === 6 ? "No deploys at weekends." : null)}
label="Deploy date"
/>
<p className="text-sm text-muted-foreground">{day ? `Deploy on ${format(day, "full")}.` : "Pick a weekday."}</p>
</div>
)
}<Calendar>
| Prop | Type | Default | Description |
|---|---|---|---|
| value | Date | null | undefined | — | The selected day, when you control it. `null` is nothing selected. |
| defaultValue | Date | undefined | — | The day selected at first, when you don't control it. Left out, no day is selected. |
| onValueChange | ((date: Date) => void) | undefined | — | Called with the day a person picks (at local midnight). |
| month | Date | undefined | — | The month shown, when you control it; any day in it. |
| defaultMonth | Date | undefined | — | The month shown at first: any day in it. Defaults to the selected day's month, else today's. Set it for server rendering, so the server and browser agree. |
| onMonthChange | ((month: Date) => void) | undefined | — | Called with the first of the month a person moves to. |
| unavailable | ((date: Date) => string | null | undefined | false) | undefined | — | Returns why a day can't be picked, or nothing when it can. The reason is shown to everyone, never swallowed. |
| weekStartsOn | number | undefined | — | The first day of the week, 0 (Sunday) to 6. Defaults to the locale's. |
| today | Date | undefined | — | The day to outline as today. Left out, the browser's today once the page has hydrated. |
| label | string | undefined | — | The grid's accessible name besides the month. Defaults to "Calendar". |
| className | string | undefined | — | Extra classes for the outer element. |
Functions
useDayFormat()Formats a calendar day in the locale: "8 Nov 2026". A day here is the date on the wall, not an instant, so this ignores LocaleProvider's time zone; a Date built from new Date(2026, 10, 8) reads as 8 November everywhere.
Strings
The fixed words, in English by default. Change any of them under calendar in <LocaleProvider strings={{ … }}>; the table is exported as calendarStrings.
| Key | English |
|---|---|
| label | Calendar |
| previousMonth | Previous month |
| nextMonth | Next month |
| gridName | {label}, {month} |
Motion
| Moment | Family | What it does |
|---|---|---|
| tint | tint | A day's background changes when the pointer is over it, and a ring fades in when it takes keyboard focus. The selected day's colours change when the person picks another day; a day that is selected when the calendar appears is drawn selected at once. |
Set with --cd-motion-calendar-<moment>-* in your brand file; the families are in the design reference.