@codapet/design-system 0.4.3 → 0.4.5
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.d.mts +21 -12
- package/dist/index.mjs +120 -204
- package/dist/index.mjs.map +1 -1
- package/package.json +1 -1
package/dist/index.d.mts
CHANGED
|
@@ -251,9 +251,9 @@ interface InputProps extends Omit<React$1.ComponentProps<'input'>, 'size'>, Vari
|
|
|
251
251
|
declare const Input: React$1.ForwardRefExoticComponent<Omit<InputProps, "ref"> & React$1.RefAttributes<HTMLInputElement>>;
|
|
252
252
|
|
|
253
253
|
type DateFormat = 'MM/DD/YYYY' | 'DD/MM/YYYY' | 'YYYY-MM-DD' | 'DD-MM-YYYY' | 'MM-DD-YYYY' | 'DD.MM.YYYY' | 'MMMM D, YYYY' | 'D MMMM YYYY';
|
|
254
|
-
type NativeInputProps
|
|
255
|
-
type FlattenedCalendarProps$1 = Omit<React$1.ComponentProps<typeof Calendar>, keyof React$1.InputHTMLAttributes<HTMLInputElement> | 'className' | 'mode' | 'selected' | 'onSelect' | 'month' | 'onMonthChange' | 'disabled' | 'captionLayout' | 'showOutsideDays' | 'classNames'>;
|
|
256
|
-
interface DateInputProps extends NativeInputProps
|
|
254
|
+
type NativeInputProps = Omit<React$1.InputHTMLAttributes<HTMLInputElement>, 'value' | 'onChange' | 'min' | 'max' | 'size' | 'disabled' | 'onSelect'>;
|
|
255
|
+
type FlattenedCalendarProps$1 = Omit<React$1.ComponentProps<typeof Calendar>, keyof React$1.InputHTMLAttributes<HTMLInputElement> | 'className' | 'mode' | 'selected' | 'onSelect' | 'month' | 'onMonthChange' | 'disabled' | 'captionLayout' | 'showOutsideDays' | 'classNames' | 'components' | 'formatters' | 'buttonVariant'>;
|
|
256
|
+
interface DateInputProps extends NativeInputProps, FlattenedCalendarProps$1 {
|
|
257
257
|
date: Date | null;
|
|
258
258
|
setDate: (date: Date | null) => void;
|
|
259
259
|
maxDate?: Date | null;
|
|
@@ -273,12 +273,14 @@ interface DateInputProps extends NativeInputProps$2, FlattenedCalendarProps$1 {
|
|
|
273
273
|
captionLayout?: React$1.ComponentProps<typeof Calendar>['captionLayout'];
|
|
274
274
|
showOutsideDays?: React$1.ComponentProps<typeof Calendar>['showOutsideDays'];
|
|
275
275
|
classNames?: React$1.ComponentProps<typeof Calendar>['classNames'];
|
|
276
|
+
components?: React$1.ComponentProps<typeof Calendar>['components'];
|
|
277
|
+
formatters?: React$1.ComponentProps<typeof Calendar>['formatters'];
|
|
278
|
+
buttonVariant?: React$1.ComponentProps<typeof Calendar>['buttonVariant'];
|
|
276
279
|
}
|
|
277
|
-
declare function DateInput({ date, setDate, maxDate, minDate, disableFuture, className, inputClassName, calendarClassName, inputDisabled, dateFormat, mode, selected, onSelect, month, onMonthChange, disabled: calendarDisabled, captionLayout, showOutsideDays, classNames, placeholder, onBlur, ...restProps }: DateInputProps): react_jsx_runtime.JSX.Element;
|
|
280
|
+
declare function DateInput({ date, setDate, maxDate, minDate, disableFuture, className, inputClassName, calendarClassName, inputDisabled, dateFormat, mode, selected, onSelect, month, onMonthChange, disabled: calendarDisabled, captionLayout, showOutsideDays, classNames, components, formatters, buttonVariant, placeholder, onBlur, ...restProps }: DateInputProps): react_jsx_runtime.JSX.Element;
|
|
278
281
|
|
|
279
|
-
type
|
|
280
|
-
|
|
281
|
-
interface DateRangeInputProps extends NativeInputProps$1, FlattenedCalendarProps {
|
|
282
|
+
type FlattenedCalendarProps = Omit<React$1.ComponentProps<typeof Calendar>, keyof React$1.InputHTMLAttributes<HTMLInputElement> | 'className' | 'mode' | 'selected' | 'onSelect' | 'month' | 'onMonthChange' | 'disabled' | 'captionLayout' | 'showOutsideDays' | 'classNames' | 'components' | 'formatters' | 'buttonVariant'>;
|
|
283
|
+
interface DateRangeInputProps extends FlattenedCalendarProps {
|
|
282
284
|
dateRange: DateRange | undefined;
|
|
283
285
|
setDateRange: (range: DateRange | undefined) => void;
|
|
284
286
|
maxDate?: Date | null;
|
|
@@ -286,9 +288,11 @@ interface DateRangeInputProps extends NativeInputProps$1, FlattenedCalendarProps
|
|
|
286
288
|
disableFuture?: boolean;
|
|
287
289
|
inputDisabled?: boolean;
|
|
288
290
|
size?: VariantProps<typeof inputVariants>['size'];
|
|
291
|
+
className?: string;
|
|
289
292
|
inputClassName?: string;
|
|
290
293
|
calendarClassName?: string;
|
|
291
294
|
dateFormat?: DateFormat;
|
|
295
|
+
placeholder?: string;
|
|
292
296
|
selected?: DateRange;
|
|
293
297
|
onSelect?: (range: DateRange | undefined) => void;
|
|
294
298
|
month?: React$1.ComponentProps<typeof Calendar>['month'];
|
|
@@ -297,8 +301,11 @@ interface DateRangeInputProps extends NativeInputProps$1, FlattenedCalendarProps
|
|
|
297
301
|
captionLayout?: React$1.ComponentProps<typeof Calendar>['captionLayout'];
|
|
298
302
|
showOutsideDays?: React$1.ComponentProps<typeof Calendar>['showOutsideDays'];
|
|
299
303
|
classNames?: React$1.ComponentProps<typeof Calendar>['classNames'];
|
|
304
|
+
components?: React$1.ComponentProps<typeof Calendar>['components'];
|
|
305
|
+
formatters?: React$1.ComponentProps<typeof Calendar>['formatters'];
|
|
306
|
+
buttonVariant?: React$1.ComponentProps<typeof Calendar>['buttonVariant'];
|
|
300
307
|
}
|
|
301
|
-
declare function DateRangeInput({ dateRange, setDateRange, maxDate, minDate, disableFuture, className, inputClassName, calendarClassName, inputDisabled, dateFormat, selected, onSelect, month, onMonthChange, disabled: calendarDisabled, captionLayout, showOutsideDays, classNames, placeholder,
|
|
308
|
+
declare function DateRangeInput({ dateRange, setDateRange, maxDate, minDate, disableFuture, className, inputClassName, calendarClassName, inputDisabled, dateFormat, selected, onSelect, month, onMonthChange, disabled: calendarDisabled, captionLayout, showOutsideDays, classNames, components, formatters, buttonVariant, placeholder, size, ...restProps }: DateRangeInputProps): react_jsx_runtime.JSX.Element;
|
|
302
309
|
|
|
303
310
|
declare function Drawer({ ...props }: React$1.ComponentProps<typeof Drawer$1.Root>): react_jsx_runtime.JSX.Element;
|
|
304
311
|
declare function DrawerTrigger({ ...props }: React$1.ComponentProps<typeof Drawer$1.Trigger>): react_jsx_runtime.JSX.Element;
|
|
@@ -576,13 +583,13 @@ declare function TabsList({ className, ...props }: React$1.ComponentProps<typeof
|
|
|
576
583
|
declare function TabsTrigger({ className, ...props }: React$1.ComponentProps<typeof TabsPrimitive.Trigger>): react_jsx_runtime.JSX.Element;
|
|
577
584
|
declare function TabsContent({ className, ...props }: React$1.ComponentProps<typeof TabsPrimitive.Content>): react_jsx_runtime.JSX.Element;
|
|
578
585
|
|
|
579
|
-
type TimeFormat = '12h' | '24h';
|
|
586
|
+
type TimeFormat = '12h' | '24h' | 'h:mm a' | 'h:mm A';
|
|
580
587
|
interface TimeValue {
|
|
581
588
|
hours: number;
|
|
582
589
|
minutes: number;
|
|
583
590
|
}
|
|
584
|
-
type
|
|
585
|
-
interface TimeInputProps extends
|
|
591
|
+
type BaseInputProps = Omit<React$1.ComponentProps<typeof Input>, 'value' | 'onChange' | 'min' | 'max' | 'size' | 'disabled' | 'onSelect' | 'rightIcon' | 'ref'>;
|
|
592
|
+
interface TimeInputProps extends BaseInputProps {
|
|
586
593
|
time: TimeValue | null;
|
|
587
594
|
setTime: (time: TimeValue | null) => void;
|
|
588
595
|
timeFormat?: TimeFormat;
|
|
@@ -590,8 +597,10 @@ interface TimeInputProps extends NativeInputProps {
|
|
|
590
597
|
inputDisabled?: boolean;
|
|
591
598
|
size?: VariantProps<typeof inputVariants>['size'];
|
|
592
599
|
inputClassName?: string;
|
|
600
|
+
icon?: React$1.ReactNode;
|
|
601
|
+
formatDisplay?: (time: TimeValue) => string;
|
|
593
602
|
}
|
|
594
|
-
declare function TimeInput({ time, setTime, timeFormat, minuteStep, inputDisabled, className, inputClassName, size, placeholder, onBlur, ...restProps }: TimeInputProps): react_jsx_runtime.JSX.Element;
|
|
603
|
+
declare function TimeInput({ time, setTime, timeFormat, minuteStep, inputDisabled, className, inputClassName, size, placeholder, onBlur, icon, formatDisplay, ...restProps }: TimeInputProps): react_jsx_runtime.JSX.Element;
|
|
595
604
|
|
|
596
605
|
declare const toggleVariants: (props?: ({
|
|
597
606
|
variant?: "default" | "outline" | null | undefined;
|
package/dist/index.mjs
CHANGED
|
@@ -2174,6 +2174,9 @@ function DateInput({
|
|
|
2174
2174
|
captionLayout = "dropdown",
|
|
2175
2175
|
showOutsideDays = false,
|
|
2176
2176
|
classNames,
|
|
2177
|
+
components,
|
|
2178
|
+
formatters,
|
|
2179
|
+
buttonVariant,
|
|
2177
2180
|
placeholder,
|
|
2178
2181
|
onBlur,
|
|
2179
2182
|
...restProps
|
|
@@ -2269,6 +2272,9 @@ function DateInput({
|
|
|
2269
2272
|
calendarClassName
|
|
2270
2273
|
),
|
|
2271
2274
|
classNames,
|
|
2275
|
+
components,
|
|
2276
|
+
formatters,
|
|
2277
|
+
buttonVariant,
|
|
2272
2278
|
onSelect: onSelect ?? defaultCalendarOnSelect,
|
|
2273
2279
|
disabled: calendarDisabled ?? defaultCalendarDisabled
|
|
2274
2280
|
};
|
|
@@ -2351,7 +2357,7 @@ function DateInput({
|
|
|
2351
2357
|
|
|
2352
2358
|
// src/components/ui/date-range-input.tsx
|
|
2353
2359
|
import "class-variance-authority";
|
|
2354
|
-
import { format as dateFnsFormat2,
|
|
2360
|
+
import { format as dateFnsFormat2, isValid as isValid2 } from "date-fns";
|
|
2355
2361
|
import { CalendarDays as CalendarDays2 } from "lucide-react";
|
|
2356
2362
|
import * as React21 from "react";
|
|
2357
2363
|
import { jsx as jsx23, jsxs as jsxs11 } from "react/jsx-runtime";
|
|
@@ -2375,65 +2381,6 @@ var DATE_FORMAT_PLACEHOLDER2 = {
|
|
|
2375
2381
|
"MMMM D, YYYY": "Month d, yyyy",
|
|
2376
2382
|
"D MMMM YYYY": "d Month yyyy"
|
|
2377
2383
|
};
|
|
2378
|
-
var INPUT_PROP_KEYS2 = /* @__PURE__ */ new Set([
|
|
2379
|
-
"accept",
|
|
2380
|
-
"alt",
|
|
2381
|
-
"autoComplete",
|
|
2382
|
-
"autoFocus",
|
|
2383
|
-
"capture",
|
|
2384
|
-
"checked",
|
|
2385
|
-
"dirName",
|
|
2386
|
-
"form",
|
|
2387
|
-
"formAction",
|
|
2388
|
-
"formEncType",
|
|
2389
|
-
"formMethod",
|
|
2390
|
-
"formNoValidate",
|
|
2391
|
-
"formTarget",
|
|
2392
|
-
"height",
|
|
2393
|
-
"list",
|
|
2394
|
-
"maxLength",
|
|
2395
|
-
"minLength",
|
|
2396
|
-
"multiple",
|
|
2397
|
-
"name",
|
|
2398
|
-
"pattern",
|
|
2399
|
-
"readOnly",
|
|
2400
|
-
"required",
|
|
2401
|
-
"size",
|
|
2402
|
-
"src",
|
|
2403
|
-
"step",
|
|
2404
|
-
"type",
|
|
2405
|
-
"width",
|
|
2406
|
-
"id",
|
|
2407
|
-
"inputMode",
|
|
2408
|
-
"lang",
|
|
2409
|
-
"tabIndex",
|
|
2410
|
-
"title",
|
|
2411
|
-
"role",
|
|
2412
|
-
"style",
|
|
2413
|
-
"onFocus",
|
|
2414
|
-
"onFocusCapture",
|
|
2415
|
-
"onBlurCapture",
|
|
2416
|
-
"onInput",
|
|
2417
|
-
"onInvalid",
|
|
2418
|
-
"onKeyDownCapture",
|
|
2419
|
-
"onKeyPress",
|
|
2420
|
-
"onKeyPressCapture",
|
|
2421
|
-
"onKeyUp",
|
|
2422
|
-
"onKeyUpCapture",
|
|
2423
|
-
"onPaste",
|
|
2424
|
-
"onPasteCapture",
|
|
2425
|
-
"onPointerDown",
|
|
2426
|
-
"onPointerDownCapture",
|
|
2427
|
-
"onPointerUp",
|
|
2428
|
-
"onPointerUpCapture",
|
|
2429
|
-
"onMouseDown",
|
|
2430
|
-
"onMouseDownCapture",
|
|
2431
|
-
"onMouseUp",
|
|
2432
|
-
"onMouseUpCapture",
|
|
2433
|
-
"onCompositionEnd",
|
|
2434
|
-
"onCompositionStart",
|
|
2435
|
-
"onCompositionUpdate"
|
|
2436
|
-
]);
|
|
2437
2384
|
function formatDate2(date, dateFormat = "MM/DD/YYYY") {
|
|
2438
2385
|
if (!date || !isValid2(date)) {
|
|
2439
2386
|
return "";
|
|
@@ -2444,23 +2391,10 @@ function formatRange(range, dateFormat = "MM/DD/YYYY") {
|
|
|
2444
2391
|
if (!range) return "";
|
|
2445
2392
|
const from = formatDate2(range.from, dateFormat);
|
|
2446
2393
|
const to = formatDate2(range.to, dateFormat);
|
|
2447
|
-
if (from && to) return `${from} \u2013 ${to}`;
|
|
2448
|
-
if (from) return
|
|
2394
|
+
if (from && to) return from === to ? from : `${from} \u2013 ${to}`;
|
|
2395
|
+
if (from) return from;
|
|
2449
2396
|
return "";
|
|
2450
2397
|
}
|
|
2451
|
-
function parseRange(value, dateFormat = "MM/DD/YYYY") {
|
|
2452
|
-
if (!value) return null;
|
|
2453
|
-
const parts = value.split(/\s*[\u2013\-]\s*/);
|
|
2454
|
-
const fromStr = parts[0]?.trim();
|
|
2455
|
-
if (!fromStr) return null;
|
|
2456
|
-
const fromParsed = dateFnsParse2(fromStr, DATE_FORMAT_TOKENS2[dateFormat], /* @__PURE__ */ new Date());
|
|
2457
|
-
if (!isValid2(fromParsed)) return null;
|
|
2458
|
-
const toStr = parts[1]?.trim();
|
|
2459
|
-
if (!toStr) return { from: fromParsed, to: void 0 };
|
|
2460
|
-
const toParsed = dateFnsParse2(toStr, DATE_FORMAT_TOKENS2[dateFormat], /* @__PURE__ */ new Date());
|
|
2461
|
-
if (!isValid2(toParsed)) return { from: fromParsed, to: void 0 };
|
|
2462
|
-
return { from: fromParsed, to: toParsed };
|
|
2463
|
-
}
|
|
2464
2398
|
function rangePlaceholder(dateFormat) {
|
|
2465
2399
|
const p = DATE_FORMAT_PLACEHOLDER2[dateFormat];
|
|
2466
2400
|
return `${p} \u2013 ${p}`;
|
|
@@ -2484,8 +2418,11 @@ function DateRangeInput({
|
|
|
2484
2418
|
captionLayout = "dropdown",
|
|
2485
2419
|
showOutsideDays = false,
|
|
2486
2420
|
classNames,
|
|
2421
|
+
components,
|
|
2422
|
+
formatters,
|
|
2423
|
+
buttonVariant,
|
|
2487
2424
|
placeholder,
|
|
2488
|
-
|
|
2425
|
+
size,
|
|
2489
2426
|
...restProps
|
|
2490
2427
|
}) {
|
|
2491
2428
|
const resolvedPlaceholder = placeholder ?? rangePlaceholder(dateFormat);
|
|
@@ -2493,23 +2430,12 @@ function DateRangeInput({
|
|
|
2493
2430
|
const [monthState, setMonthState] = React21.useState(
|
|
2494
2431
|
dateRange?.from ?? null
|
|
2495
2432
|
);
|
|
2496
|
-
const
|
|
2497
|
-
|
|
2498
|
-
|
|
2499
|
-
|
|
2500
|
-
for (const [key, val] of Object.entries(restProps)) {
|
|
2501
|
-
const isInputProp = INPUT_PROP_KEYS2.has(key) || key.startsWith("aria-") || key.startsWith("data-");
|
|
2502
|
-
if (isInputProp) {
|
|
2503
|
-
nextInputProps[key] = val;
|
|
2504
|
-
} else {
|
|
2505
|
-
nextCalendarProps[key] = val;
|
|
2506
|
-
}
|
|
2433
|
+
const displayValue = formatRange(dateRange, dateFormat);
|
|
2434
|
+
React21.useEffect(() => {
|
|
2435
|
+
if (dateRange?.from) {
|
|
2436
|
+
setMonthState(dateRange.from);
|
|
2507
2437
|
}
|
|
2508
|
-
|
|
2509
|
-
nextInputProps,
|
|
2510
|
-
nextCalendarProps
|
|
2511
|
-
];
|
|
2512
|
-
}, [restProps]);
|
|
2438
|
+
}, [dateRange]);
|
|
2513
2439
|
const today = React21.useMemo(() => {
|
|
2514
2440
|
const d = /* @__PURE__ */ new Date();
|
|
2515
2441
|
d.setHours(0, 0, 0, 0);
|
|
@@ -2539,12 +2465,6 @@ function DateRangeInput({
|
|
|
2539
2465
|
}
|
|
2540
2466
|
return null;
|
|
2541
2467
|
}, [minDate]);
|
|
2542
|
-
React21.useEffect(() => {
|
|
2543
|
-
setValue(formatRange(dateRange, dateFormat));
|
|
2544
|
-
if (dateRange?.from) {
|
|
2545
|
-
setMonthState(dateRange.from);
|
|
2546
|
-
}
|
|
2547
|
-
}, [dateRange, dateFormat]);
|
|
2548
2468
|
const effectiveMonth = month ?? monthState ?? void 0;
|
|
2549
2469
|
const effectiveSelected = selected ?? dateRange;
|
|
2550
2470
|
const isInputDisabled = inputDisabled ?? (typeof calendarDisabled === "boolean" ? calendarDisabled : false);
|
|
@@ -2565,8 +2485,14 @@ function DateRangeInput({
|
|
|
2565
2485
|
}
|
|
2566
2486
|
setDateRange(range);
|
|
2567
2487
|
};
|
|
2488
|
+
const handleClear = () => {
|
|
2489
|
+
setDateRange(void 0);
|
|
2490
|
+
};
|
|
2491
|
+
const handleAdd = () => {
|
|
2492
|
+
setOpen(false);
|
|
2493
|
+
};
|
|
2568
2494
|
const resolvedCalendarProps = {
|
|
2569
|
-
...
|
|
2495
|
+
...restProps,
|
|
2570
2496
|
mode: "range",
|
|
2571
2497
|
selected: effectiveSelected,
|
|
2572
2498
|
captionLayout,
|
|
@@ -2578,93 +2504,56 @@ function DateRangeInput({
|
|
|
2578
2504
|
calendarClassName
|
|
2579
2505
|
),
|
|
2580
2506
|
classNames,
|
|
2507
|
+
components,
|
|
2508
|
+
formatters,
|
|
2509
|
+
buttonVariant,
|
|
2581
2510
|
onSelect: handleCalendarSelect,
|
|
2582
2511
|
disabled: calendarDisabled ?? defaultCalendarDisabled
|
|
2583
2512
|
};
|
|
2584
|
-
const handleInputChange = (e) => {
|
|
2585
|
-
const inputValue = e.target.value;
|
|
2586
|
-
setValue(inputValue);
|
|
2587
|
-
if (inputValue === "") {
|
|
2588
|
-
setDateRange(void 0);
|
|
2589
|
-
return;
|
|
2590
|
-
}
|
|
2591
|
-
const parsed = parseRange(inputValue, dateFormat);
|
|
2592
|
-
if (!parsed || !parsed.from) return;
|
|
2593
|
-
const from = new Date(parsed.from);
|
|
2594
|
-
from.setHours(0, 0, 0, 0);
|
|
2595
|
-
if (!isWithinBounds(from)) return;
|
|
2596
|
-
if (parsed.to) {
|
|
2597
|
-
const to = new Date(parsed.to);
|
|
2598
|
-
to.setHours(0, 0, 0, 0);
|
|
2599
|
-
if (isWithinBounds(to) && from <= to) {
|
|
2600
|
-
setDateRange(parsed);
|
|
2601
|
-
setMonthState(from);
|
|
2602
|
-
}
|
|
2603
|
-
} else {
|
|
2604
|
-
setDateRange({ from: parsed.from, to: void 0 });
|
|
2605
|
-
setMonthState(from);
|
|
2606
|
-
}
|
|
2607
|
-
};
|
|
2608
|
-
const handleBlur = (e) => {
|
|
2609
|
-
onBlur?.(e);
|
|
2610
|
-
if (value === "") {
|
|
2611
|
-
if (dateRange !== void 0) {
|
|
2612
|
-
setDateRange(void 0);
|
|
2613
|
-
}
|
|
2614
|
-
return;
|
|
2615
|
-
}
|
|
2616
|
-
const parsed = parseRange(value, dateFormat);
|
|
2617
|
-
if (!parsed || !parsed.from) {
|
|
2618
|
-
setValue(formatRange(dateRange, dateFormat));
|
|
2619
|
-
return;
|
|
2620
|
-
}
|
|
2621
|
-
const from = new Date(parsed.from);
|
|
2622
|
-
from.setHours(0, 0, 0, 0);
|
|
2623
|
-
if (!isWithinBounds(from)) {
|
|
2624
|
-
setValue(formatRange(dateRange, dateFormat));
|
|
2625
|
-
return;
|
|
2626
|
-
}
|
|
2627
|
-
if (parsed.to) {
|
|
2628
|
-
const to = new Date(parsed.to);
|
|
2629
|
-
to.setHours(0, 0, 0, 0);
|
|
2630
|
-
if (!isWithinBounds(to) || from > to) {
|
|
2631
|
-
setValue(formatRange(dateRange, dateFormat));
|
|
2632
|
-
}
|
|
2633
|
-
}
|
|
2634
|
-
};
|
|
2635
2513
|
return /* @__PURE__ */ jsx23("div", { className: cn("relative flex gap-2", className), children: /* @__PURE__ */ jsxs11(Popover, { open, onOpenChange: setOpen, children: [
|
|
2636
|
-
/* @__PURE__ */ jsx23(PopoverTrigger, { asChild: true, disabled: isInputDisabled, children: /* @__PURE__ */
|
|
2637
|
-
|
|
2514
|
+
/* @__PURE__ */ jsx23(PopoverTrigger, { asChild: true, disabled: isInputDisabled, children: /* @__PURE__ */ jsxs11(
|
|
2515
|
+
Button,
|
|
2638
2516
|
{
|
|
2639
|
-
|
|
2640
|
-
|
|
2641
|
-
className: cn(
|
|
2642
|
-
|
|
2643
|
-
|
|
2517
|
+
type: "button",
|
|
2518
|
+
variant: "outline",
|
|
2519
|
+
className: cn(
|
|
2520
|
+
inputVariants({ size }),
|
|
2521
|
+
"bg-background cursor-pointer w-full text-left flex items-center justify-between gap-2 font-normal",
|
|
2522
|
+
isInputDisabled && "pointer-events-none cursor-not-allowed opacity-50",
|
|
2523
|
+
inputClassName
|
|
2524
|
+
),
|
|
2644
2525
|
disabled: isInputDisabled,
|
|
2645
|
-
|
|
2646
|
-
|
|
2647
|
-
|
|
2648
|
-
|
|
2649
|
-
}
|
|
2650
|
-
},
|
|
2651
|
-
rightIcon: /* @__PURE__ */ jsx23(CalendarDays2, { className: "h-4 w-4 text-muted-foreground" }),
|
|
2652
|
-
rightIconOnClick: isInputDisabled ? void 0 : () => setOpen(!open),
|
|
2653
|
-
rightIconButtonProps: { disabled: isInputDisabled },
|
|
2654
|
-
...inputProps
|
|
2655
|
-
}
|
|
2656
|
-
) }) }),
|
|
2657
|
-
/* @__PURE__ */ jsx23(
|
|
2658
|
-
PopoverContent,
|
|
2659
|
-
{
|
|
2660
|
-
className: "w-auto overflow-hidden p-0",
|
|
2661
|
-
align: "end",
|
|
2662
|
-
alignOffset: -8,
|
|
2663
|
-
sideOffset: 10,
|
|
2664
|
-
side: "top",
|
|
2665
|
-
children: /* @__PURE__ */ jsx23(Calendar, { ...resolvedCalendarProps })
|
|
2526
|
+
children: [
|
|
2527
|
+
displayValue || resolvedPlaceholder,
|
|
2528
|
+
/* @__PURE__ */ jsx23(CalendarDays2, { className: "h-4 w-4 text-muted-foreground shrink-0" })
|
|
2529
|
+
]
|
|
2666
2530
|
}
|
|
2667
|
-
)
|
|
2531
|
+
) }),
|
|
2532
|
+
/* @__PURE__ */ jsxs11(PopoverContent, { className: "p-0 flex flex-col overflow-y-auto max-h-[min(90dvh,520px)] md:w-[350px] w-[var(--radix-popover-trigger-width)] ", children: [
|
|
2533
|
+
/* @__PURE__ */ jsx23(Calendar, { ...resolvedCalendarProps }),
|
|
2534
|
+
/* @__PURE__ */ jsxs11("div", { className: "flex flex-col gap-2 px-2 py-2", children: [
|
|
2535
|
+
/* @__PURE__ */ jsx23(
|
|
2536
|
+
Button,
|
|
2537
|
+
{
|
|
2538
|
+
variant: "ghost-secondary",
|
|
2539
|
+
size: "sm",
|
|
2540
|
+
onClick: handleClear,
|
|
2541
|
+
type: "button",
|
|
2542
|
+
children: "Clear"
|
|
2543
|
+
}
|
|
2544
|
+
),
|
|
2545
|
+
/* @__PURE__ */ jsx23(
|
|
2546
|
+
Button,
|
|
2547
|
+
{
|
|
2548
|
+
variant: "primary",
|
|
2549
|
+
size: "sm",
|
|
2550
|
+
onClick: handleAdd,
|
|
2551
|
+
type: "button",
|
|
2552
|
+
children: "Add"
|
|
2553
|
+
}
|
|
2554
|
+
)
|
|
2555
|
+
] })
|
|
2556
|
+
] })
|
|
2668
2557
|
] }) });
|
|
2669
2558
|
}
|
|
2670
2559
|
|
|
@@ -5309,26 +5198,47 @@ import "class-variance-authority";
|
|
|
5309
5198
|
import { Clock } from "lucide-react";
|
|
5310
5199
|
import * as React46 from "react";
|
|
5311
5200
|
import { jsx as jsx49, jsxs as jsxs24 } from "react/jsx-runtime";
|
|
5201
|
+
var TIME_FORMAT_PLACEHOLDER = {
|
|
5202
|
+
"12h": "hh:mm AM/PM",
|
|
5203
|
+
"24h": "HH:mm",
|
|
5204
|
+
"h:mm a": "h:mm am/pm",
|
|
5205
|
+
"h:mm A": "h:mm AM/PM"
|
|
5206
|
+
};
|
|
5207
|
+
function is24HourFormat(tf) {
|
|
5208
|
+
return tf === "24h";
|
|
5209
|
+
}
|
|
5312
5210
|
function formatTime(time, timeFormat = "12h") {
|
|
5313
5211
|
if (!time) return "";
|
|
5314
|
-
|
|
5315
|
-
|
|
5212
|
+
const { hours, minutes } = time;
|
|
5213
|
+
const h24 = String(hours).padStart(2, "0");
|
|
5214
|
+
const m = String(minutes).padStart(2, "0");
|
|
5215
|
+
const h12 = hours % 12 || 12;
|
|
5216
|
+
const h12p = String(h12).padStart(2, "0");
|
|
5217
|
+
const period = hours >= 12 ? "PM" : "AM";
|
|
5218
|
+
switch (timeFormat) {
|
|
5219
|
+
case "24h":
|
|
5220
|
+
return `${h24}:${m}`;
|
|
5221
|
+
case "h:mm a":
|
|
5222
|
+
return `${h12}:${m} ${period.toLowerCase()}`;
|
|
5223
|
+
case "h:mm A":
|
|
5224
|
+
return `${h12}:${m} ${period}`;
|
|
5225
|
+
case "12h":
|
|
5226
|
+
default:
|
|
5227
|
+
return `${h12p}:${m} ${period}`;
|
|
5316
5228
|
}
|
|
5317
|
-
const period = time.hours >= 12 ? "PM" : "AM";
|
|
5318
|
-
const h12 = time.hours % 12 || 12;
|
|
5319
|
-
return `${String(h12).padStart(2, "0")}:${String(time.minutes).padStart(2, "0")} ${period}`;
|
|
5320
5229
|
}
|
|
5321
5230
|
function parseTime(value, timeFormat = "12h") {
|
|
5322
5231
|
if (!value.trim()) return null;
|
|
5323
|
-
|
|
5324
|
-
|
|
5232
|
+
const v = value.trim();
|
|
5233
|
+
if (is24HourFormat(timeFormat)) {
|
|
5234
|
+
const match2 = v.match(/^(\d{1,2}):(\d{2})$/);
|
|
5325
5235
|
if (!match2) return null;
|
|
5326
5236
|
const hours2 = parseInt(match2[1], 10);
|
|
5327
5237
|
const minutes2 = parseInt(match2[2], 10);
|
|
5328
5238
|
if (hours2 < 0 || hours2 > 23 || minutes2 < 0 || minutes2 > 59) return null;
|
|
5329
5239
|
return { hours: hours2, minutes: minutes2 };
|
|
5330
5240
|
}
|
|
5331
|
-
const match =
|
|
5241
|
+
const match = v.match(/^(\d{1,2}):(\d{2})\s*(AM|PM|am|pm)$/i);
|
|
5332
5242
|
if (!match) return null;
|
|
5333
5243
|
let hours = parseInt(match[1], 10);
|
|
5334
5244
|
const minutes = parseInt(match[2], 10);
|
|
@@ -5339,7 +5249,7 @@ function parseTime(value, timeFormat = "12h") {
|
|
|
5339
5249
|
return { hours, minutes };
|
|
5340
5250
|
}
|
|
5341
5251
|
function getDisplayHour(hours, timeFormat) {
|
|
5342
|
-
if (timeFormat
|
|
5252
|
+
if (is24HourFormat(timeFormat)) return hours;
|
|
5343
5253
|
return hours % 12 || 12;
|
|
5344
5254
|
}
|
|
5345
5255
|
function getPeriod(hours) {
|
|
@@ -5356,17 +5266,27 @@ function TimeInput({
|
|
|
5356
5266
|
size,
|
|
5357
5267
|
placeholder,
|
|
5358
5268
|
onBlur,
|
|
5269
|
+
icon,
|
|
5270
|
+
formatDisplay,
|
|
5359
5271
|
...restProps
|
|
5360
5272
|
}) {
|
|
5361
|
-
const resolvedPlaceholder = placeholder ??
|
|
5273
|
+
const resolvedPlaceholder = placeholder ?? TIME_FORMAT_PLACEHOLDER[timeFormat];
|
|
5274
|
+
const displayFormat = React46.useCallback(
|
|
5275
|
+
(t) => {
|
|
5276
|
+
if (!t) return "";
|
|
5277
|
+
if (formatDisplay) return formatDisplay(t);
|
|
5278
|
+
return formatTime(t, timeFormat);
|
|
5279
|
+
},
|
|
5280
|
+
[formatDisplay, timeFormat]
|
|
5281
|
+
);
|
|
5362
5282
|
const [open, setOpen] = React46.useState(false);
|
|
5363
|
-
const [value, setValue] = React46.useState(
|
|
5283
|
+
const [value, setValue] = React46.useState(displayFormat(time));
|
|
5364
5284
|
const hoursRef = React46.useRef(null);
|
|
5365
5285
|
const minutesRef = React46.useRef(null);
|
|
5366
5286
|
const periodRef = React46.useRef(null);
|
|
5367
5287
|
React46.useEffect(() => {
|
|
5368
|
-
setValue(
|
|
5369
|
-
}, [time,
|
|
5288
|
+
setValue(displayFormat(time));
|
|
5289
|
+
}, [time, displayFormat]);
|
|
5370
5290
|
const scrollToSelected = React46.useCallback(() => {
|
|
5371
5291
|
requestAnimationFrame(() => {
|
|
5372
5292
|
for (const ref of [hoursRef, minutesRef, periodRef]) {
|
|
@@ -5404,12 +5324,12 @@ function TimeInput({
|
|
|
5404
5324
|
}
|
|
5405
5325
|
const parsed = parseTime(value, timeFormat);
|
|
5406
5326
|
if (!parsed) {
|
|
5407
|
-
setValue(
|
|
5327
|
+
setValue(displayFormat(time));
|
|
5408
5328
|
}
|
|
5409
5329
|
};
|
|
5410
5330
|
const handleHourSelect = (hour) => {
|
|
5411
5331
|
let h24;
|
|
5412
|
-
if (timeFormat
|
|
5332
|
+
if (is24HourFormat(timeFormat)) {
|
|
5413
5333
|
h24 = hour;
|
|
5414
5334
|
} else {
|
|
5415
5335
|
const currentPeriod = time ? getPeriod(time.hours) : "AM";
|
|
@@ -5430,7 +5350,7 @@ function TimeInput({
|
|
|
5430
5350
|
const newHours = period === "AM" ? currentH12 : currentH12 + 12;
|
|
5431
5351
|
setTime({ hours: newHours, minutes: time?.minutes ?? 0 });
|
|
5432
5352
|
};
|
|
5433
|
-
const hoursList = timeFormat
|
|
5353
|
+
const hoursList = is24HourFormat(timeFormat) ? Array.from({ length: 24 }, (_, i) => i) : Array.from({ length: 12 }, (_, i) => i + 1);
|
|
5434
5354
|
const minutesList = Array.from(
|
|
5435
5355
|
{ length: Math.ceil(60 / minuteStep) },
|
|
5436
5356
|
(_, i) => i * minuteStep
|
|
@@ -5458,21 +5378,17 @@ function TimeInput({
|
|
|
5458
5378
|
setOpen(true);
|
|
5459
5379
|
}
|
|
5460
5380
|
},
|
|
5461
|
-
rightIcon: /* @__PURE__ */ jsx49(Clock, { className: "h-4 w-4 text-muted-foreground" }),
|
|
5381
|
+
rightIcon: icon !== void 0 ? icon : /* @__PURE__ */ jsx49(Clock, { className: "h-4 w-4 text-muted-foreground" }),
|
|
5462
5382
|
...restProps
|
|
5463
5383
|
}
|
|
5464
5384
|
) }) }),
|
|
5465
5385
|
/* @__PURE__ */ jsx49(
|
|
5466
5386
|
PopoverContent,
|
|
5467
5387
|
{
|
|
5468
|
-
className: "w-auto p-0",
|
|
5469
|
-
align: "end",
|
|
5470
|
-
alignOffset: -8,
|
|
5471
|
-
sideOffset: 10,
|
|
5472
|
-
side: "top",
|
|
5388
|
+
className: "w-auto p-0 ",
|
|
5473
5389
|
onOpenAutoFocus: (e) => e.preventDefault(),
|
|
5474
5390
|
children: /* @__PURE__ */ jsxs24("div", { className: "flex divide-x", children: [
|
|
5475
|
-
/* @__PURE__ */ jsx49("div", { className: "h-56 w-16 overflow-y-auto overscroll-contain
|
|
5391
|
+
/* @__PURE__ */ jsx49("div", { className: "h-56 w-16 overflow-y-auto overscroll-y-contain [-webkit-overflow-scrolling:touch]", children: /* @__PURE__ */ jsx49("div", { ref: hoursRef, className: "flex flex-col p-1 ", children: hoursList.map((h) => /* @__PURE__ */ jsx49(
|
|
5476
5392
|
Button,
|
|
5477
5393
|
{
|
|
5478
5394
|
variant: "ghost",
|
|
@@ -5487,7 +5403,7 @@ function TimeInput({
|
|
|
5487
5403
|
},
|
|
5488
5404
|
h
|
|
5489
5405
|
)) }) }),
|
|
5490
|
-
/* @__PURE__ */ jsx49("div", { className: "h-56 w-16 overflow-y-auto overscroll-contain", children: /* @__PURE__ */ jsx49("div", { ref: minutesRef, className: "flex flex-col p-1", children: minutesList.map((m) => /* @__PURE__ */ jsx49(
|
|
5406
|
+
/* @__PURE__ */ jsx49("div", { className: "h-56 w-16 overflow-y-auto overscroll-y-contain [-webkit-overflow-scrolling:touch]", children: /* @__PURE__ */ jsx49("div", { ref: minutesRef, className: "flex flex-col p-1 ", children: minutesList.map((m) => /* @__PURE__ */ jsx49(
|
|
5491
5407
|
Button,
|
|
5492
5408
|
{
|
|
5493
5409
|
variant: "ghost",
|
|
@@ -5502,7 +5418,7 @@ function TimeInput({
|
|
|
5502
5418
|
},
|
|
5503
5419
|
m
|
|
5504
5420
|
)) }) }),
|
|
5505
|
-
timeFormat
|
|
5421
|
+
!is24HourFormat(timeFormat) && /* @__PURE__ */ jsx49("div", { className: "flex flex-col p-1 justify-center gap-1", children: ["AM", "PM"].map((p) => /* @__PURE__ */ jsx49(
|
|
5506
5422
|
Button,
|
|
5507
5423
|
{
|
|
5508
5424
|
variant: "ghost",
|