"use client"; import { CalendarDays } from "lucide-react"; import { useMemo, useState } from "react"; import { Calendar } from "@/components/motion/calendar"; import { MorphPopover, MorphPopoverContent, MorphPopoverTrigger, } from "@/components/motion/popover-morph"; import { cn } from "@/lib/utils"; const MEDIUM_DATE: Intl.DateTimeFormatOptions = { dateStyle: "medium" }; export interface DatePickerProps { value?: Date | null; defaultValue?: Date | null; onValueChange?: (date: Date) => void; placeholder?: string; /** Intl options for the trigger label. Default: medium date. */ formatOptions?: Intl.DateTimeFormatOptions; /** Default "en-US". */ locale?: string; minDate?: Date; maxDate?: Date; isDateDisabled?: (date: Date) => boolean; weekStartsOn?: 0 | 1 | 2 | 3 | 4 | 5 | 6; align?: "start" | "end"; disabled?: boolean; className?: string; "aria-label"?: string; } /** * Date field whose calendar morphs open from the trigger corner and closes * as soon as a day is picked. Controlled or uncontrolled. */ export function DatePicker({ value: controlledValue, defaultValue = null, onValueChange, placeholder = "Pick a date", formatOptions = MEDIUM_DATE, locale = "en-US", minDate, maxDate, isDateDisabled, weekStartsOn, align = "start", disabled, className, "aria-label": ariaLabel = "Choose date", }: DatePickerProps) { const [open, setOpen] = useState(false); const [internalValue, setInternalValue] = useState( defaultValue, ); const value = controlledValue !== undefined ? controlledValue : internalValue; const label = useMemo( () => value ? new Intl.DateTimeFormat(locale, formatOptions).format(value) : null, [value, locale, formatOptions], ); return ( { if (controlledValue === undefined) setInternalValue(d); onValueChange?.(d); setOpen(false); }} locale={locale} minDate={minDate} maxDate={maxDate} isDateDisabled={isDateDisabled} weekStartsOn={weekStartsOn} className="border-0 bg-transparent" /> ); }