import type { DayStates, RenderDayContent } from "./dayStates"; /** Governs which UI renders inside the popover — date grid, time selects, or both; inferred from dateFormat when omitted. */ export type PickerType = "date" | "time" | "datetime"; /** Fields shared by both picker variants — combined via `&` with Single/RangeDatePickerProps below, never used on its own. */ export type BaseDatePickerProps = { id?: string; name?: string; /** Label above the field; also the calendar popover's accessible name (falls back to "Choose date" / "Choose date range"). */ label?: string; /** Shows the label asterisk and sets native `required` via FormControl. */ isRequired?: boolean; /** Shows an info icon beside the label; needs both `label` and `informationMessage` to render. */ isInformation?: boolean; /** Tooltip text for the info icon; ignored unless `isInformation` is true. */ informationMessage?: string; /** Marks the field invalid (error border + `aria-invalid`) and swaps `helperText` for `errorMessage`. */ error?: boolean; /** Shown while `error` is true. Omitting it renders no message and still hides `helperText`. */ errorMessage?: string; /** Shown under the field when there is no error; linked via `aria-describedby`. */ helperText?: string; /** Field hint text; defaults to one derived from `dateFormat`. */ placeholder?: string; /** @deprecated Use `placeholder` — renamed to match every other field; `placeholder` wins when both are set. */ placeholderText?: string; /** date-fns format; defaults to `dd/MM/yyyy` (`HH:mm` for the time-only picker). Time tokens add time inputs. */ dateFormat?: string; /** Inferred from `dateFormat` when omitted: `H`/`h`/`mm`/`ss` mean time, so a lowercase `dd/mm/yyyy` is read as minutes and shows time selects while `dd/MM/yyyy` stays date-only. Ignored when `isRange`. */ pickerType?: PickerType; /** Earlier days are disabled in the calendar and rejected when typed. */ minDate?: Date; /** Later days are disabled in the calendar and rejected when typed. */ maxDate?: Date; /** Blocks every day after today; today stays selectable. */ disableFutureDates?: boolean; /** Blocks every day before today; today stays selectable. */ disablePastDates?: boolean; /** Defaults to `"off"` so browser suggestions don't cover the calendar; not read by the time-only picker. */ autoComplete?: string; /** Disables the field and its calendar/clock trigger. */ isDisabled?: boolean; /** @deprecated Use `isDisabled` — renamed to match every other field; `isDisabled` wins when both are set. */ disabled?: boolean; /** Width of the whole field; defaults to `"100%"`. */ width?: string | number; /** Blocks today in the calendar and in typed input; the single picker preselects tomorrow instead. */ disableToday?: boolean; /** Control-scale height: xs 32 · sm 38 · md 40 · lg 48px (default `sm`, like TextInput); also scales the calendar/clock icon. */ size?: "xs" | "sm" | "md" | "lg"; }; /** Single-date variant, Date API (default) — `isRange` must be false or omitted; this is the discriminant the DatePickerProps union switches on. */ export type SingleDatePickerDateProps = BaseDatePickerProps & { /** Omit or false for a single-date picker; the discriminant `DatePickerProps` switches on. */ isRange?: false; /** Omit, or set `"date"`, for the default Date-object API; `"iso"` switches value/onChange to ISO strings. */ valueFormat?: "date"; /** Controlled value; `value` wins when both are set. */ selectedDate?: Date | null; /** Alias for `selectedDate` (legacy / form libraries). */ value?: Date | null; /** Fires on day click in date-only mode; with time inputs, only on Apply, Clear or closing the popover. */ onChange: (date: Date | null) => void; }; /** Single-date variant, string API — `yyyy-MM-dd` / `HH:mm` / full local ISO datetime by pickerType; an unparsable incoming string reads as `null`. */ export type SingleDatePickerStringProps = BaseDatePickerProps & { /** Omit or false for a single-date picker; the discriminant `DatePickerProps` switches on. */ isRange?: false; /** `"iso"` opts into the string API for this instance. */ valueFormat: "iso"; /** Controlled ISO value; `value` wins when both are set. */ selectedDate?: string | null; /** Alias for `selectedDate` (legacy / form libraries). */ value?: string | null; /** Fires with an ISO string (or `null`) on the same triggers as the Date API. */ onChange: (value: string | null) => void; }; /** Discriminated on `valueFormat` — `"iso"` narrows to the string-value overload, everything else to the Date overload. */ export type SingleDatePickerProps = SingleDatePickerDateProps | SingleDatePickerStringProps; export declare const isStringValueProps: (props: SingleDatePickerProps) => props is SingleDatePickerStringProps; /** A date range's two endpoints, each independently nullable — used for both the controlled value and onChange's payload. */ export type RangeDate = { /** Range start, `null` until picked. */ from: Date | null; /** Range end, `null` until picked. */ to: Date | null; }; /** Range variant — `isRange` must be true; adds dayStates/renderDayContent day-marking on top of the shared base fields. */ export type RangeDatePickerProps = BaseDatePickerProps & { /** Must be true to render the range picker. */ isRange: true; /** Controlled range; `value` wins when both are set. */ selectedDate?: RangeDate | null; /** Alias for `selectedDate` (legacy / form libraries). */ value?: RangeDate | null; /** Only fires via Apply or Escape once both ends are picked — clicking outside the popover discards the pending range instead of committing it. */ onChange: (range: RangeDate | null) => void; /** * Marks individual days with zero or more state keys — `["weekly-off"]`, `["Onam", "holiday"]`, * `["excluded"]`. The keys in `DAY_STATE_KEYS` (`weekly-off`, `holiday`, `optional-holiday`, * `excluded`, `disabled`) carry built-in, token-driven styling; any other key is announced to a * screen reader but left unstyled, which is how a day gets named without a second prop. * * Marking is not disabling: a marked day stays selectable unless the caller also returns * `"disabled"`, or blocks the day with `minDate`/`maxDate`/`disablePastDates`/`disableFutureDates`. * * Supplying this also spells each day's accessible name out in full — "16 September 2025, Onam, * holiday" instead of "16". Called once per rendered day (42 per month), so keep it cheap and pure. */ dayStates?: DayStates; /** * Custom content rendered inside the day cell, centred under the day number — a dot, a short * label, a tooltip trigger. Receives that day's resolved state keys. Returning a node replaces * the built-in marker dot for that day; the number, the accessible name and hit target are * unchanged (the overlay does not take pointer events). */ renderDayContent?: RenderDayContent; /** Shortcut buttons above the calendar; each applies `range` to the pending selection (Apply still commits). Defaults to Today, Yesterday, Last 7 days, Last 30 days, This month; `[]` hides the row. */ presets?: { label: string; range: { from: Date; to: Date; }; }[]; }; /** Discriminated union consumed by ThemeDatePicker (exported as DatePicker) — `isRange` selects Single vs Range at the type level. */ export type DatePickerProps = SingleDatePickerProps | RangeDatePickerProps; /** Props for the Hour/Minute/AM-PM trio; `dateFormat` only toggles 12h vs 24h display — seconds aren't supported. */ export type TimePickerProps = { date: Date; onChange: (date: Date) => void; /** Only picks 12h vs 24h: an `h` followed later by `a` (e.g. `hh:mm a`) means 12h with AM/PM. */ dateFormat: string; /** Disables the hour/minute/AM-PM selects. */ isDisabled?: boolean; /** @deprecated Use `isDisabled` — renamed to match every other field; `isDisabled` wins when both are set. */ disabled?: boolean; };