@marcoschwartz/lite-ui 0.7.1 → 0.8.0
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 +31 -5
- package/dist/index.d.ts +31 -5
- package/dist/index.js +853 -185
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +852 -185
- package/dist/index.mjs.map +1 -1
- package/dist/styles.css +1 -1
- package/package.json +1 -1
package/dist/index.js
CHANGED
|
@@ -39,6 +39,7 @@ __export(index_exports, {
|
|
|
39
39
|
Badge: () => Badge,
|
|
40
40
|
BellIcon: () => BellIcon,
|
|
41
41
|
Button: () => Button,
|
|
42
|
+
Calendar: () => Calendar,
|
|
42
43
|
CalendarIcon: () => CalendarIcon,
|
|
43
44
|
CameraIcon: () => CameraIcon,
|
|
44
45
|
Card: () => Card,
|
|
@@ -300,6 +301,9 @@ var Select = ({
|
|
|
300
301
|
value: controlledValue,
|
|
301
302
|
defaultValue,
|
|
302
303
|
onChange,
|
|
304
|
+
label,
|
|
305
|
+
error,
|
|
306
|
+
helperText,
|
|
303
307
|
...props
|
|
304
308
|
}) => {
|
|
305
309
|
const { theme, themeName } = useTheme();
|
|
@@ -334,7 +338,8 @@ var Select = ({
|
|
|
334
338
|
const baseStyles = theme.select.base;
|
|
335
339
|
const sizeStyles2 = theme.select.sizes[size];
|
|
336
340
|
const disabledStyles = disabled ? theme.select.disabled : "";
|
|
337
|
-
const
|
|
341
|
+
const errorStyles = error ? "border-red-500 focus:ring-red-500 dark:border-red-500" : "";
|
|
342
|
+
const buttonClasses = `${baseStyles} ${sizeStyles2} ${disabledStyles} ${errorStyles}`.trim();
|
|
338
343
|
const iconColor = themeName === "minimalistic" ? disabled ? "text-gray-600" : "text-white" : disabled ? "text-gray-400" : "text-gray-500";
|
|
339
344
|
const dropdownBaseStyles = themeName === "minimalistic" ? "bg-black border-2 border-white" : "bg-white border border-gray-300 shadow-lg dark:bg-gray-800 dark:border-gray-600";
|
|
340
345
|
const optionBaseStyles = themeName === "minimalistic" ? "text-white hover:bg-white hover:text-black transition-colors duration-200" : "text-gray-900 hover:bg-blue-50 transition-colors duration-150 dark:text-gray-100 dark:hover:bg-gray-700";
|
|
@@ -344,51 +349,56 @@ var Select = ({
|
|
|
344
349
|
lg: "px-4 py-3 text-lg",
|
|
345
350
|
xl: "px-5 py-4 text-xl"
|
|
346
351
|
}[size];
|
|
347
|
-
return /* @__PURE__ */ (0, import_jsx_runtime3.jsxs)("div", { className:
|
|
348
|
-
/* @__PURE__ */ (0, import_jsx_runtime3.jsx)(
|
|
349
|
-
|
|
350
|
-
|
|
351
|
-
|
|
352
|
-
|
|
353
|
-
|
|
354
|
-
|
|
355
|
-
|
|
356
|
-
|
|
357
|
-
|
|
358
|
-
|
|
359
|
-
|
|
360
|
-
{
|
|
361
|
-
|
|
362
|
-
|
|
363
|
-
|
|
364
|
-
|
|
365
|
-
|
|
366
|
-
|
|
367
|
-
"
|
|
368
|
-
|
|
369
|
-
|
|
370
|
-
|
|
371
|
-
|
|
372
|
-
|
|
373
|
-
|
|
374
|
-
|
|
375
|
-
|
|
376
|
-
|
|
377
|
-
|
|
378
|
-
|
|
379
|
-
|
|
380
|
-
|
|
381
|
-
|
|
382
|
-
"
|
|
383
|
-
|
|
384
|
-
|
|
385
|
-
|
|
386
|
-
|
|
387
|
-
|
|
388
|
-
|
|
389
|
-
|
|
390
|
-
|
|
391
|
-
|
|
352
|
+
return /* @__PURE__ */ (0, import_jsx_runtime3.jsxs)("div", { className: `w-full ${className}`, children: [
|
|
353
|
+
label && /* @__PURE__ */ (0, import_jsx_runtime3.jsx)("label", { className: "block text-sm font-medium text-gray-700 dark:text-gray-300 mb-1", children: label }),
|
|
354
|
+
/* @__PURE__ */ (0, import_jsx_runtime3.jsxs)("div", { className: "relative inline-block w-full", ref: dropdownRef, ...props, children: [
|
|
355
|
+
/* @__PURE__ */ (0, import_jsx_runtime3.jsx)(
|
|
356
|
+
"button",
|
|
357
|
+
{
|
|
358
|
+
type: "button",
|
|
359
|
+
className: buttonClasses,
|
|
360
|
+
onClick: handleToggle,
|
|
361
|
+
disabled,
|
|
362
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime3.jsx)("span", { className: !selectedOption && placeholder ? "opacity-50" : "", children: displayText })
|
|
363
|
+
}
|
|
364
|
+
),
|
|
365
|
+
/* @__PURE__ */ (0, import_jsx_runtime3.jsx)("div", { className: "pointer-events-none absolute inset-y-0 right-0 flex items-center pr-4", children: /* @__PURE__ */ (0, import_jsx_runtime3.jsx)(
|
|
366
|
+
"svg",
|
|
367
|
+
{
|
|
368
|
+
className: `h-5 w-5 transition-transform duration-200 ${iconColor} ${isOpen ? "rotate-180" : ""}`,
|
|
369
|
+
xmlns: "http://www.w3.org/2000/svg",
|
|
370
|
+
viewBox: "0 0 20 20",
|
|
371
|
+
fill: "currentColor",
|
|
372
|
+
"aria-hidden": "true",
|
|
373
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime3.jsx)(
|
|
374
|
+
"path",
|
|
375
|
+
{
|
|
376
|
+
fillRule: "evenodd",
|
|
377
|
+
d: "M5.23 7.21a.75.75 0 011.06.02L10 11.168l3.71-3.938a.75.75 0 111.08 1.04l-4.25 4.5a.75.75 0 01-1.08 0l-4.25-4.5a.75.75 0 01.02-1.06z",
|
|
378
|
+
clipRule: "evenodd"
|
|
379
|
+
}
|
|
380
|
+
)
|
|
381
|
+
}
|
|
382
|
+
) }),
|
|
383
|
+
isOpen && !disabled && /* @__PURE__ */ (0, import_jsx_runtime3.jsx)(
|
|
384
|
+
"div",
|
|
385
|
+
{
|
|
386
|
+
className: `absolute z-50 w-full mt-1 ${dropdownBaseStyles} rounded-lg overflow-hidden`,
|
|
387
|
+
style: { maxHeight: "300px", overflowY: "auto" },
|
|
388
|
+
children: options.map((option) => /* @__PURE__ */ (0, import_jsx_runtime3.jsx)(
|
|
389
|
+
"div",
|
|
390
|
+
{
|
|
391
|
+
className: `${optionBaseStyles} ${optionSizeStyles} cursor-pointer ${value === option.value ? themeName === "minimalistic" ? "bg-white text-black" : "bg-blue-50 dark:bg-gray-700" : ""}`,
|
|
392
|
+
onClick: () => handleSelect(option.value),
|
|
393
|
+
children: option.label
|
|
394
|
+
},
|
|
395
|
+
option.value
|
|
396
|
+
))
|
|
397
|
+
}
|
|
398
|
+
)
|
|
399
|
+
] }),
|
|
400
|
+
error && /* @__PURE__ */ (0, import_jsx_runtime3.jsx)("p", { className: "mt-1 text-sm text-red-600 dark:text-red-400", children: error }),
|
|
401
|
+
helperText && !error && /* @__PURE__ */ (0, import_jsx_runtime3.jsx)("p", { className: "mt-1 text-sm text-gray-500 dark:text-gray-400", children: helperText })
|
|
392
402
|
] });
|
|
393
403
|
};
|
|
394
404
|
|
|
@@ -1515,30 +1525,220 @@ var Pagination = ({
|
|
|
1515
1525
|
|
|
1516
1526
|
// src/components/DatePicker.tsx
|
|
1517
1527
|
var import_react12 = require("react");
|
|
1528
|
+
var import_react_dom2 = require("react-dom");
|
|
1518
1529
|
var import_jsx_runtime51 = require("react/jsx-runtime");
|
|
1519
|
-
var
|
|
1520
|
-
|
|
1521
|
-
|
|
1522
|
-
|
|
1523
|
-
|
|
1524
|
-
|
|
1525
|
-
|
|
1526
|
-
|
|
1527
|
-
|
|
1528
|
-
|
|
1529
|
-
|
|
1530
|
-
|
|
1531
|
-
|
|
1532
|
-
|
|
1533
|
-
|
|
1534
|
-
|
|
1535
|
-
|
|
1536
|
-
|
|
1537
|
-
|
|
1538
|
-
|
|
1539
|
-
|
|
1530
|
+
var DAYS = ["Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat"];
|
|
1531
|
+
var MONTHS = [
|
|
1532
|
+
"January",
|
|
1533
|
+
"February",
|
|
1534
|
+
"March",
|
|
1535
|
+
"April",
|
|
1536
|
+
"May",
|
|
1537
|
+
"June",
|
|
1538
|
+
"July",
|
|
1539
|
+
"August",
|
|
1540
|
+
"September",
|
|
1541
|
+
"October",
|
|
1542
|
+
"November",
|
|
1543
|
+
"December"
|
|
1544
|
+
];
|
|
1545
|
+
var DatePicker = ({
|
|
1546
|
+
label,
|
|
1547
|
+
error,
|
|
1548
|
+
helperText,
|
|
1549
|
+
value,
|
|
1550
|
+
onChange,
|
|
1551
|
+
minDate,
|
|
1552
|
+
maxDate,
|
|
1553
|
+
disabled,
|
|
1554
|
+
className = "",
|
|
1555
|
+
placeholder = "Select date..."
|
|
1556
|
+
}) => {
|
|
1557
|
+
const { theme } = useTheme();
|
|
1558
|
+
const [isOpen, setIsOpen] = (0, import_react12.useState)(false);
|
|
1559
|
+
const [viewDate, setViewDate] = (0, import_react12.useState)(value || /* @__PURE__ */ new Date());
|
|
1560
|
+
const [mounted, setMounted] = (0, import_react12.useState)(false);
|
|
1561
|
+
const [calendarPosition, setCalendarPosition] = (0, import_react12.useState)(null);
|
|
1562
|
+
const inputRef = (0, import_react12.useRef)(null);
|
|
1563
|
+
const calendarRef = (0, import_react12.useRef)(null);
|
|
1564
|
+
(0, import_react12.useEffect)(() => {
|
|
1565
|
+
setMounted(true);
|
|
1566
|
+
}, []);
|
|
1567
|
+
(0, import_react12.useEffect)(() => {
|
|
1568
|
+
const handleClickOutside = (event) => {
|
|
1569
|
+
if (calendarRef.current && !calendarRef.current.contains(event.target) && inputRef.current && !inputRef.current.contains(event.target)) {
|
|
1570
|
+
setIsOpen(false);
|
|
1571
|
+
}
|
|
1572
|
+
};
|
|
1573
|
+
if (isOpen) {
|
|
1574
|
+
document.addEventListener("mousedown", handleClickOutside);
|
|
1575
|
+
return () => document.removeEventListener("mousedown", handleClickOutside);
|
|
1576
|
+
}
|
|
1577
|
+
}, [isOpen]);
|
|
1578
|
+
(0, import_react12.useEffect)(() => {
|
|
1579
|
+
if (isOpen && inputRef.current) {
|
|
1580
|
+
const rect = inputRef.current.getBoundingClientRect();
|
|
1581
|
+
setCalendarPosition({
|
|
1582
|
+
top: rect.bottom + 8,
|
|
1583
|
+
left: rect.left
|
|
1584
|
+
});
|
|
1585
|
+
} else {
|
|
1586
|
+
setCalendarPosition(null);
|
|
1587
|
+
}
|
|
1588
|
+
}, [isOpen]);
|
|
1589
|
+
const year = viewDate.getFullYear();
|
|
1590
|
+
const month = viewDate.getMonth();
|
|
1591
|
+
const firstDayOfMonth = new Date(year, month, 1).getDay();
|
|
1592
|
+
const daysInMonth = new Date(year, month + 1, 0).getDate();
|
|
1593
|
+
const daysInPrevMonth = new Date(year, month, 0).getDate();
|
|
1594
|
+
const calendarDays = [];
|
|
1595
|
+
for (let i = firstDayOfMonth - 1; i >= 0; i--) {
|
|
1596
|
+
calendarDays.push(new Date(year, month - 1, daysInPrevMonth - i));
|
|
1540
1597
|
}
|
|
1541
|
-
)
|
|
1598
|
+
for (let i = 1; i <= daysInMonth; i++) {
|
|
1599
|
+
calendarDays.push(new Date(year, month, i));
|
|
1600
|
+
}
|
|
1601
|
+
const remainingDays = 42 - calendarDays.length;
|
|
1602
|
+
for (let i = 1; i <= remainingDays; i++) {
|
|
1603
|
+
calendarDays.push(new Date(year, month + 1, i));
|
|
1604
|
+
}
|
|
1605
|
+
const isSameDay = (date1, date2) => {
|
|
1606
|
+
return date1.getDate() === date2.getDate() && date1.getMonth() === date2.getMonth() && date1.getFullYear() === date2.getFullYear();
|
|
1607
|
+
};
|
|
1608
|
+
const isToday = (date) => {
|
|
1609
|
+
return isSameDay(date, /* @__PURE__ */ new Date());
|
|
1610
|
+
};
|
|
1611
|
+
const isSelected = (date) => {
|
|
1612
|
+
return value && isSameDay(date, value);
|
|
1613
|
+
};
|
|
1614
|
+
const isCurrentMonth = (date) => {
|
|
1615
|
+
return date.getMonth() === month;
|
|
1616
|
+
};
|
|
1617
|
+
const isDisabled = (date) => {
|
|
1618
|
+
if (minDate && date < minDate) return true;
|
|
1619
|
+
if (maxDate && date > maxDate) return true;
|
|
1620
|
+
return false;
|
|
1621
|
+
};
|
|
1622
|
+
const handleDateClick = (date) => {
|
|
1623
|
+
if (isDisabled(date)) return;
|
|
1624
|
+
onChange?.(date);
|
|
1625
|
+
setIsOpen(false);
|
|
1626
|
+
};
|
|
1627
|
+
const handlePrevMonth = () => {
|
|
1628
|
+
setViewDate(new Date(year, month - 1, 1));
|
|
1629
|
+
};
|
|
1630
|
+
const handleNextMonth = () => {
|
|
1631
|
+
setViewDate(new Date(year, month + 1, 1));
|
|
1632
|
+
};
|
|
1633
|
+
const handleToday = () => {
|
|
1634
|
+
const today = /* @__PURE__ */ new Date();
|
|
1635
|
+
setViewDate(today);
|
|
1636
|
+
onChange?.(today);
|
|
1637
|
+
setIsOpen(false);
|
|
1638
|
+
};
|
|
1639
|
+
const formatDate = (date) => {
|
|
1640
|
+
if (!date) return "";
|
|
1641
|
+
return date.toLocaleDateString("en-US", {
|
|
1642
|
+
month: "short",
|
|
1643
|
+
day: "numeric",
|
|
1644
|
+
year: "numeric"
|
|
1645
|
+
});
|
|
1646
|
+
};
|
|
1647
|
+
const baseStyles = "w-full appearance-none rounded-lg border border-gray-300 bg-white text-gray-900 px-4 py-2.5 text-base transition-all duration-150 focus:outline-none focus:ring-2 focus:ring-blue-500 focus:border-transparent shadow-sm hover:border-gray-400 dark:bg-gray-800 dark:border-gray-600 dark:text-gray-100 dark:hover:border-gray-500 cursor-pointer";
|
|
1648
|
+
const errorStyles = error ? "border-red-500 focus:ring-red-500 dark:border-red-500" : "";
|
|
1649
|
+
const disabledStyles = disabled ? "opacity-50 cursor-not-allowed bg-gray-50 dark:bg-gray-900" : "";
|
|
1650
|
+
const calendar = isOpen && mounted && calendarPosition ? /* @__PURE__ */ (0, import_jsx_runtime51.jsxs)(
|
|
1651
|
+
"div",
|
|
1652
|
+
{
|
|
1653
|
+
ref: calendarRef,
|
|
1654
|
+
className: "fixed z-[9999] bg-white dark:bg-gray-800 rounded-lg border border-gray-200 dark:border-gray-700 shadow-xl p-4",
|
|
1655
|
+
style: {
|
|
1656
|
+
top: `${calendarPosition.top}px`,
|
|
1657
|
+
left: `${calendarPosition.left}px`,
|
|
1658
|
+
minWidth: "320px"
|
|
1659
|
+
},
|
|
1660
|
+
children: [
|
|
1661
|
+
/* @__PURE__ */ (0, import_jsx_runtime51.jsxs)("div", { className: "flex items-center justify-between mb-4", children: [
|
|
1662
|
+
/* @__PURE__ */ (0, import_jsx_runtime51.jsx)(
|
|
1663
|
+
"button",
|
|
1664
|
+
{
|
|
1665
|
+
onClick: handlePrevMonth,
|
|
1666
|
+
className: "p-2 hover:bg-gray-100 dark:hover:bg-gray-700 rounded-lg transition-colors",
|
|
1667
|
+
"aria-label": "Previous month",
|
|
1668
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime51.jsx)("svg", { className: "w-5 h-5 text-gray-600 dark:text-gray-400", fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime51.jsx)("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M15 19l-7-7 7-7" }) })
|
|
1669
|
+
}
|
|
1670
|
+
),
|
|
1671
|
+
/* @__PURE__ */ (0, import_jsx_runtime51.jsxs)("div", { className: "flex items-center gap-2", children: [
|
|
1672
|
+
/* @__PURE__ */ (0, import_jsx_runtime51.jsxs)("h2", { className: "text-base font-semibold text-gray-900 dark:text-gray-100", children: [
|
|
1673
|
+
MONTHS[month],
|
|
1674
|
+
" ",
|
|
1675
|
+
year
|
|
1676
|
+
] }),
|
|
1677
|
+
/* @__PURE__ */ (0, import_jsx_runtime51.jsx)(
|
|
1678
|
+
"button",
|
|
1679
|
+
{
|
|
1680
|
+
onClick: handleToday,
|
|
1681
|
+
className: "px-2 py-1 text-xs bg-blue-600 text-white rounded hover:bg-blue-700 transition-colors",
|
|
1682
|
+
children: "Today"
|
|
1683
|
+
}
|
|
1684
|
+
)
|
|
1685
|
+
] }),
|
|
1686
|
+
/* @__PURE__ */ (0, import_jsx_runtime51.jsx)(
|
|
1687
|
+
"button",
|
|
1688
|
+
{
|
|
1689
|
+
onClick: handleNextMonth,
|
|
1690
|
+
className: "p-2 hover:bg-gray-100 dark:hover:bg-gray-700 rounded-lg transition-colors",
|
|
1691
|
+
"aria-label": "Next month",
|
|
1692
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime51.jsx)("svg", { className: "w-5 h-5 text-gray-600 dark:text-gray-400", fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime51.jsx)("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M9 5l7 7-7 7" }) })
|
|
1693
|
+
}
|
|
1694
|
+
)
|
|
1695
|
+
] }),
|
|
1696
|
+
/* @__PURE__ */ (0, import_jsx_runtime51.jsx)("div", { className: "grid grid-cols-7 gap-1 mb-2", children: DAYS.map((day) => /* @__PURE__ */ (0, import_jsx_runtime51.jsx)("div", { className: "text-center text-xs font-semibold text-gray-600 dark:text-gray-400 py-1", children: day }, day)) }),
|
|
1697
|
+
/* @__PURE__ */ (0, import_jsx_runtime51.jsx)("div", { className: "grid grid-cols-7 gap-1", children: calendarDays.map((date, index) => {
|
|
1698
|
+
const isCurrentMonthDay = isCurrentMonth(date);
|
|
1699
|
+
const isTodayDay = isToday(date);
|
|
1700
|
+
const isSelectedDay = isSelected(date);
|
|
1701
|
+
const isDisabledDay = isDisabled(date);
|
|
1702
|
+
return /* @__PURE__ */ (0, import_jsx_runtime51.jsx)(
|
|
1703
|
+
"button",
|
|
1704
|
+
{
|
|
1705
|
+
onClick: () => handleDateClick(date),
|
|
1706
|
+
disabled: isDisabledDay,
|
|
1707
|
+
className: `
|
|
1708
|
+
aspect-square p-1 rounded-lg text-sm font-medium transition-all
|
|
1709
|
+
${!isCurrentMonthDay ? "text-gray-400 dark:text-gray-600" : "text-gray-900 dark:text-gray-100"}
|
|
1710
|
+
${isTodayDay && !isSelectedDay ? "bg-blue-50 dark:bg-blue-900/20 text-blue-600 dark:text-blue-400 font-bold" : ""}
|
|
1711
|
+
${isSelectedDay ? "bg-blue-600 text-white hover:bg-blue-700" : ""}
|
|
1712
|
+
${!isSelectedDay && !isDisabledDay ? "hover:bg-gray-100 dark:hover:bg-gray-700" : ""}
|
|
1713
|
+
${isDisabledDay ? "opacity-30 cursor-not-allowed" : "cursor-pointer"}
|
|
1714
|
+
`,
|
|
1715
|
+
children: date.getDate()
|
|
1716
|
+
},
|
|
1717
|
+
index
|
|
1718
|
+
);
|
|
1719
|
+
}) })
|
|
1720
|
+
]
|
|
1721
|
+
}
|
|
1722
|
+
) : null;
|
|
1723
|
+
return /* @__PURE__ */ (0, import_jsx_runtime51.jsxs)("div", { className, children: [
|
|
1724
|
+
label && /* @__PURE__ */ (0, import_jsx_runtime51.jsx)("label", { className: "block text-sm font-medium text-gray-700 dark:text-gray-300 mb-1", children: label }),
|
|
1725
|
+
/* @__PURE__ */ (0, import_jsx_runtime51.jsxs)(
|
|
1726
|
+
"div",
|
|
1727
|
+
{
|
|
1728
|
+
ref: inputRef,
|
|
1729
|
+
onClick: () => !disabled && setIsOpen(!isOpen),
|
|
1730
|
+
className: `${baseStyles} ${errorStyles} ${disabledStyles} flex items-center justify-between`.trim(),
|
|
1731
|
+
children: [
|
|
1732
|
+
/* @__PURE__ */ (0, import_jsx_runtime51.jsx)("span", { className: !value ? "text-gray-500 dark:text-gray-400" : "", children: value ? formatDate(value) : placeholder }),
|
|
1733
|
+
/* @__PURE__ */ (0, import_jsx_runtime51.jsx)("svg", { className: "w-5 h-5 text-gray-400", fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime51.jsx)("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M8 7V3m8 4V3m-9 8h10M5 21h14a2 2 0 002-2V7a2 2 0 00-2-2H5a2 2 0 00-2 2v12a2 2 0 002 2z" }) })
|
|
1734
|
+
]
|
|
1735
|
+
}
|
|
1736
|
+
),
|
|
1737
|
+
error && /* @__PURE__ */ (0, import_jsx_runtime51.jsx)("p", { className: "mt-1 text-sm text-red-600 dark:text-red-400", children: error }),
|
|
1738
|
+
helperText && !error && /* @__PURE__ */ (0, import_jsx_runtime51.jsx)("p", { className: "mt-1 text-sm text-gray-500 dark:text-gray-400", children: helperText }),
|
|
1739
|
+
mounted && (0, import_react_dom2.createPortal)(calendar, document.body)
|
|
1740
|
+
] });
|
|
1741
|
+
};
|
|
1542
1742
|
DatePicker.displayName = "DatePicker";
|
|
1543
1743
|
|
|
1544
1744
|
// src/components/TimePicker.tsx
|
|
@@ -1571,35 +1771,502 @@ TimePicker.displayName = "TimePicker";
|
|
|
1571
1771
|
|
|
1572
1772
|
// src/components/DateTimePicker.tsx
|
|
1573
1773
|
var import_react14 = require("react");
|
|
1774
|
+
var import_react_dom3 = require("react-dom");
|
|
1574
1775
|
var import_jsx_runtime53 = require("react/jsx-runtime");
|
|
1575
|
-
var
|
|
1576
|
-
|
|
1577
|
-
|
|
1578
|
-
|
|
1579
|
-
|
|
1580
|
-
|
|
1581
|
-
|
|
1582
|
-
|
|
1583
|
-
|
|
1584
|
-
|
|
1776
|
+
var DAYS2 = ["Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat"];
|
|
1777
|
+
var MONTHS2 = [
|
|
1778
|
+
"January",
|
|
1779
|
+
"February",
|
|
1780
|
+
"March",
|
|
1781
|
+
"April",
|
|
1782
|
+
"May",
|
|
1783
|
+
"June",
|
|
1784
|
+
"July",
|
|
1785
|
+
"August",
|
|
1786
|
+
"September",
|
|
1787
|
+
"October",
|
|
1788
|
+
"November",
|
|
1789
|
+
"December"
|
|
1790
|
+
];
|
|
1791
|
+
var DateTimePicker = ({
|
|
1792
|
+
label,
|
|
1793
|
+
error,
|
|
1794
|
+
helperText,
|
|
1795
|
+
value,
|
|
1796
|
+
onChange,
|
|
1797
|
+
minDate,
|
|
1798
|
+
maxDate,
|
|
1799
|
+
disabled,
|
|
1800
|
+
className = "",
|
|
1801
|
+
placeholder = "Select date and time..."
|
|
1802
|
+
}) => {
|
|
1803
|
+
const { theme } = useTheme();
|
|
1804
|
+
const [isOpen, setIsOpen] = (0, import_react14.useState)(false);
|
|
1805
|
+
const [viewDate, setViewDate] = (0, import_react14.useState)(value || /* @__PURE__ */ new Date());
|
|
1806
|
+
const [selectedTime, setSelectedTime] = (0, import_react14.useState)(
|
|
1807
|
+
value ? { hours: value.getHours(), minutes: value.getMinutes() } : { hours: 12, minutes: 0 }
|
|
1808
|
+
);
|
|
1809
|
+
const [mounted, setMounted] = (0, import_react14.useState)(false);
|
|
1810
|
+
const [pickerPosition, setPickerPosition] = (0, import_react14.useState)(null);
|
|
1811
|
+
const inputRef = (0, import_react14.useRef)(null);
|
|
1812
|
+
const pickerRef = (0, import_react14.useRef)(null);
|
|
1813
|
+
(0, import_react14.useEffect)(() => {
|
|
1814
|
+
setMounted(true);
|
|
1815
|
+
}, []);
|
|
1816
|
+
(0, import_react14.useEffect)(() => {
|
|
1817
|
+
const handleClickOutside = (event) => {
|
|
1818
|
+
if (pickerRef.current && !pickerRef.current.contains(event.target) && inputRef.current && !inputRef.current.contains(event.target)) {
|
|
1819
|
+
setIsOpen(false);
|
|
1820
|
+
}
|
|
1821
|
+
};
|
|
1822
|
+
if (isOpen) {
|
|
1823
|
+
document.addEventListener("mousedown", handleClickOutside);
|
|
1824
|
+
return () => document.removeEventListener("mousedown", handleClickOutside);
|
|
1825
|
+
}
|
|
1826
|
+
}, [isOpen]);
|
|
1827
|
+
(0, import_react14.useEffect)(() => {
|
|
1828
|
+
if (isOpen && inputRef.current) {
|
|
1829
|
+
const rect = inputRef.current.getBoundingClientRect();
|
|
1830
|
+
setPickerPosition({
|
|
1831
|
+
top: rect.bottom + 8,
|
|
1832
|
+
left: rect.left
|
|
1833
|
+
});
|
|
1834
|
+
} else {
|
|
1835
|
+
setPickerPosition(null);
|
|
1836
|
+
}
|
|
1837
|
+
}, [isOpen]);
|
|
1838
|
+
const year = viewDate.getFullYear();
|
|
1839
|
+
const month = viewDate.getMonth();
|
|
1840
|
+
const firstDayOfMonth = new Date(year, month, 1).getDay();
|
|
1841
|
+
const daysInMonth = new Date(year, month + 1, 0).getDate();
|
|
1842
|
+
const daysInPrevMonth = new Date(year, month, 0).getDate();
|
|
1843
|
+
const calendarDays = [];
|
|
1844
|
+
for (let i = firstDayOfMonth - 1; i >= 0; i--) {
|
|
1845
|
+
calendarDays.push(new Date(year, month - 1, daysInPrevMonth - i));
|
|
1846
|
+
}
|
|
1847
|
+
for (let i = 1; i <= daysInMonth; i++) {
|
|
1848
|
+
calendarDays.push(new Date(year, month, i));
|
|
1849
|
+
}
|
|
1850
|
+
const remainingDays = 42 - calendarDays.length;
|
|
1851
|
+
for (let i = 1; i <= remainingDays; i++) {
|
|
1852
|
+
calendarDays.push(new Date(year, month + 1, i));
|
|
1853
|
+
}
|
|
1854
|
+
const isSameDay = (date1, date2) => {
|
|
1855
|
+
return date1.getDate() === date2.getDate() && date1.getMonth() === date2.getMonth() && date1.getFullYear() === date2.getFullYear();
|
|
1856
|
+
};
|
|
1857
|
+
const isToday = (date) => {
|
|
1858
|
+
return isSameDay(date, /* @__PURE__ */ new Date());
|
|
1859
|
+
};
|
|
1860
|
+
const isSelected = (date) => {
|
|
1861
|
+
return value && isSameDay(date, value);
|
|
1862
|
+
};
|
|
1863
|
+
const isCurrentMonth = (date) => {
|
|
1864
|
+
return date.getMonth() === month;
|
|
1865
|
+
};
|
|
1866
|
+
const isDisabled = (date) => {
|
|
1867
|
+
if (minDate && date < minDate) return true;
|
|
1868
|
+
if (maxDate && date > maxDate) return true;
|
|
1869
|
+
return false;
|
|
1870
|
+
};
|
|
1871
|
+
const handleDateClick = (date) => {
|
|
1872
|
+
if (isDisabled(date)) return;
|
|
1873
|
+
const newDateTime = new Date(
|
|
1874
|
+
date.getFullYear(),
|
|
1875
|
+
date.getMonth(),
|
|
1876
|
+
date.getDate(),
|
|
1877
|
+
selectedTime.hours,
|
|
1878
|
+
selectedTime.minutes
|
|
1879
|
+
);
|
|
1880
|
+
onChange?.(newDateTime);
|
|
1881
|
+
};
|
|
1882
|
+
const handleTimeChange = (hours, minutes) => {
|
|
1883
|
+
setSelectedTime({ hours, minutes });
|
|
1884
|
+
if (value) {
|
|
1885
|
+
const newDateTime = new Date(
|
|
1886
|
+
value.getFullYear(),
|
|
1887
|
+
value.getMonth(),
|
|
1888
|
+
value.getDate(),
|
|
1889
|
+
hours,
|
|
1890
|
+
minutes
|
|
1891
|
+
);
|
|
1892
|
+
onChange?.(newDateTime);
|
|
1893
|
+
}
|
|
1894
|
+
};
|
|
1895
|
+
const handleDone = () => {
|
|
1896
|
+
if (value) {
|
|
1897
|
+
setIsOpen(false);
|
|
1898
|
+
}
|
|
1899
|
+
};
|
|
1900
|
+
const handlePrevMonth = () => {
|
|
1901
|
+
setViewDate(new Date(year, month - 1, 1));
|
|
1902
|
+
};
|
|
1903
|
+
const handleNextMonth = () => {
|
|
1904
|
+
setViewDate(new Date(year, month + 1, 1));
|
|
1905
|
+
};
|
|
1906
|
+
const handleToday = () => {
|
|
1907
|
+
const now = /* @__PURE__ */ new Date();
|
|
1908
|
+
setViewDate(now);
|
|
1909
|
+
setSelectedTime({ hours: now.getHours(), minutes: now.getMinutes() });
|
|
1910
|
+
onChange?.(now);
|
|
1911
|
+
};
|
|
1912
|
+
const formatDateTime = (date) => {
|
|
1913
|
+
if (!date) return "";
|
|
1914
|
+
return date.toLocaleString("en-US", {
|
|
1915
|
+
month: "short",
|
|
1916
|
+
day: "numeric",
|
|
1917
|
+
year: "numeric",
|
|
1918
|
+
hour: "numeric",
|
|
1919
|
+
minute: "2-digit",
|
|
1920
|
+
hour12: true
|
|
1921
|
+
});
|
|
1922
|
+
};
|
|
1923
|
+
const formatTime = (hours, minutes) => {
|
|
1924
|
+
const period = hours >= 12 ? "PM" : "AM";
|
|
1925
|
+
const displayHours = hours % 12 || 12;
|
|
1926
|
+
const displayMinutes = minutes.toString().padStart(2, "0");
|
|
1927
|
+
return `${displayHours}:${displayMinutes} ${period}`;
|
|
1928
|
+
};
|
|
1929
|
+
const baseStyles = "w-full appearance-none rounded-lg border border-gray-300 bg-white text-gray-900 px-4 py-2.5 text-base transition-all duration-150 focus:outline-none focus:ring-2 focus:ring-blue-500 focus:border-transparent shadow-sm hover:border-gray-400 dark:bg-gray-800 dark:border-gray-600 dark:text-gray-100 dark:hover:border-gray-500 cursor-pointer";
|
|
1930
|
+
const errorStyles = error ? "border-red-500 focus:ring-red-500 dark:border-red-500" : "";
|
|
1931
|
+
const disabledStyles = disabled ? "opacity-50 cursor-not-allowed bg-gray-50 dark:bg-gray-900" : "";
|
|
1932
|
+
const picker = isOpen && mounted && pickerPosition ? /* @__PURE__ */ (0, import_jsx_runtime53.jsxs)(
|
|
1933
|
+
"div",
|
|
1934
|
+
{
|
|
1935
|
+
ref: pickerRef,
|
|
1936
|
+
className: "fixed z-[9999] bg-white dark:bg-gray-800 rounded-lg border border-gray-200 dark:border-gray-700 shadow-xl p-4",
|
|
1937
|
+
style: {
|
|
1938
|
+
top: `${pickerPosition.top}px`,
|
|
1939
|
+
left: `${pickerPosition.left}px`,
|
|
1940
|
+
minWidth: "360px"
|
|
1941
|
+
},
|
|
1942
|
+
children: [
|
|
1943
|
+
/* @__PURE__ */ (0, import_jsx_runtime53.jsxs)("div", { className: "flex items-center justify-between mb-4", children: [
|
|
1944
|
+
/* @__PURE__ */ (0, import_jsx_runtime53.jsx)(
|
|
1945
|
+
"button",
|
|
1946
|
+
{
|
|
1947
|
+
onClick: handlePrevMonth,
|
|
1948
|
+
className: "p-2 hover:bg-gray-100 dark:hover:bg-gray-700 rounded-lg transition-colors",
|
|
1949
|
+
"aria-label": "Previous month",
|
|
1950
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime53.jsx)("svg", { className: "w-5 h-5 text-gray-600 dark:text-gray-400", fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime53.jsx)("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M15 19l-7-7 7-7" }) })
|
|
1951
|
+
}
|
|
1952
|
+
),
|
|
1953
|
+
/* @__PURE__ */ (0, import_jsx_runtime53.jsxs)("div", { className: "flex items-center gap-2", children: [
|
|
1954
|
+
/* @__PURE__ */ (0, import_jsx_runtime53.jsxs)("h2", { className: "text-base font-semibold text-gray-900 dark:text-gray-100", children: [
|
|
1955
|
+
MONTHS2[month],
|
|
1956
|
+
" ",
|
|
1957
|
+
year
|
|
1958
|
+
] }),
|
|
1959
|
+
/* @__PURE__ */ (0, import_jsx_runtime53.jsx)(
|
|
1960
|
+
"button",
|
|
1961
|
+
{
|
|
1962
|
+
onClick: handleToday,
|
|
1963
|
+
className: "px-2 py-1 text-xs bg-blue-600 text-white rounded hover:bg-blue-700 transition-colors",
|
|
1964
|
+
children: "Now"
|
|
1965
|
+
}
|
|
1966
|
+
)
|
|
1967
|
+
] }),
|
|
1968
|
+
/* @__PURE__ */ (0, import_jsx_runtime53.jsx)(
|
|
1969
|
+
"button",
|
|
1970
|
+
{
|
|
1971
|
+
onClick: handleNextMonth,
|
|
1972
|
+
className: "p-2 hover:bg-gray-100 dark:hover:bg-gray-700 rounded-lg transition-colors",
|
|
1973
|
+
"aria-label": "Next month",
|
|
1974
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime53.jsx)("svg", { className: "w-5 h-5 text-gray-600 dark:text-gray-400", fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime53.jsx)("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M9 5l7 7-7 7" }) })
|
|
1975
|
+
}
|
|
1976
|
+
)
|
|
1977
|
+
] }),
|
|
1978
|
+
/* @__PURE__ */ (0, import_jsx_runtime53.jsx)("div", { className: "grid grid-cols-7 gap-1 mb-2", children: DAYS2.map((day) => /* @__PURE__ */ (0, import_jsx_runtime53.jsx)("div", { className: "text-center text-xs font-semibold text-gray-600 dark:text-gray-400 py-1", children: day }, day)) }),
|
|
1979
|
+
/* @__PURE__ */ (0, import_jsx_runtime53.jsx)("div", { className: "grid grid-cols-7 gap-1 mb-4", children: calendarDays.map((date, index) => {
|
|
1980
|
+
const isCurrentMonthDay = isCurrentMonth(date);
|
|
1981
|
+
const isTodayDay = isToday(date);
|
|
1982
|
+
const isSelectedDay = isSelected(date);
|
|
1983
|
+
const isDisabledDay = isDisabled(date);
|
|
1984
|
+
return /* @__PURE__ */ (0, import_jsx_runtime53.jsx)(
|
|
1985
|
+
"button",
|
|
1986
|
+
{
|
|
1987
|
+
onClick: () => handleDateClick(date),
|
|
1988
|
+
disabled: isDisabledDay,
|
|
1989
|
+
className: `
|
|
1990
|
+
aspect-square p-1 rounded-lg text-sm font-medium transition-all
|
|
1991
|
+
${!isCurrentMonthDay ? "text-gray-400 dark:text-gray-600" : "text-gray-900 dark:text-gray-100"}
|
|
1992
|
+
${isTodayDay && !isSelectedDay ? "bg-blue-50 dark:bg-blue-900/20 text-blue-600 dark:text-blue-400 font-bold" : ""}
|
|
1993
|
+
${isSelectedDay ? "bg-blue-600 text-white hover:bg-blue-700" : ""}
|
|
1994
|
+
${!isSelectedDay && !isDisabledDay ? "hover:bg-gray-100 dark:hover:bg-gray-700" : ""}
|
|
1995
|
+
${isDisabledDay ? "opacity-30 cursor-not-allowed" : "cursor-pointer"}
|
|
1996
|
+
`,
|
|
1997
|
+
children: date.getDate()
|
|
1998
|
+
},
|
|
1999
|
+
index
|
|
2000
|
+
);
|
|
2001
|
+
}) }),
|
|
2002
|
+
/* @__PURE__ */ (0, import_jsx_runtime53.jsxs)("div", { className: "border-t border-gray-200 dark:border-gray-700 pt-4", children: [
|
|
2003
|
+
/* @__PURE__ */ (0, import_jsx_runtime53.jsxs)("div", { className: "flex items-center justify-center gap-4 mb-4", children: [
|
|
2004
|
+
/* @__PURE__ */ (0, import_jsx_runtime53.jsxs)("div", { className: "flex flex-col items-center", children: [
|
|
2005
|
+
/* @__PURE__ */ (0, import_jsx_runtime53.jsx)("label", { className: "text-xs font-semibold text-gray-600 dark:text-gray-400 mb-2", children: "Hour" }),
|
|
2006
|
+
/* @__PURE__ */ (0, import_jsx_runtime53.jsxs)("div", { className: "flex flex-col items-center gap-1", children: [
|
|
2007
|
+
/* @__PURE__ */ (0, import_jsx_runtime53.jsx)(
|
|
2008
|
+
"button",
|
|
2009
|
+
{
|
|
2010
|
+
type: "button",
|
|
2011
|
+
onClick: () => handleTimeChange((selectedTime.hours + 1) % 24, selectedTime.minutes),
|
|
2012
|
+
className: "p-1 hover:bg-gray-100 dark:hover:bg-gray-700 rounded transition-colors",
|
|
2013
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime53.jsx)("svg", { className: "w-4 h-4 text-gray-600 dark:text-gray-400", fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime53.jsx)("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M5 15l7-7 7 7" }) })
|
|
2014
|
+
}
|
|
2015
|
+
),
|
|
2016
|
+
/* @__PURE__ */ (0, import_jsx_runtime53.jsx)(
|
|
2017
|
+
"input",
|
|
2018
|
+
{
|
|
2019
|
+
type: "number",
|
|
2020
|
+
min: "0",
|
|
2021
|
+
max: "23",
|
|
2022
|
+
value: selectedTime.hours,
|
|
2023
|
+
onChange: (e) => {
|
|
2024
|
+
const val = parseInt(e.target.value);
|
|
2025
|
+
if (!isNaN(val) && val >= 0 && val <= 23) {
|
|
2026
|
+
handleTimeChange(val, selectedTime.minutes);
|
|
2027
|
+
}
|
|
2028
|
+
},
|
|
2029
|
+
className: "w-16 px-2 py-2 text-center border border-gray-300 dark:border-gray-600 rounded-lg bg-white dark:bg-gray-700 text-gray-900 dark:text-gray-100 focus:outline-none focus:ring-2 focus:ring-blue-500 text-lg font-semibold [appearance:textfield] [&::-webkit-outer-spin-button]:appearance-none [&::-webkit-inner-spin-button]:appearance-none"
|
|
2030
|
+
}
|
|
2031
|
+
),
|
|
2032
|
+
/* @__PURE__ */ (0, import_jsx_runtime53.jsx)(
|
|
2033
|
+
"button",
|
|
2034
|
+
{
|
|
2035
|
+
type: "button",
|
|
2036
|
+
onClick: () => handleTimeChange((selectedTime.hours - 1 + 24) % 24, selectedTime.minutes),
|
|
2037
|
+
className: "p-1 hover:bg-gray-100 dark:hover:bg-gray-700 rounded transition-colors",
|
|
2038
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime53.jsx)("svg", { className: "w-4 h-4 text-gray-600 dark:text-gray-400", fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime53.jsx)("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M19 9l-7 7-7-7" }) })
|
|
2039
|
+
}
|
|
2040
|
+
)
|
|
2041
|
+
] })
|
|
2042
|
+
] }),
|
|
2043
|
+
/* @__PURE__ */ (0, import_jsx_runtime53.jsx)("span", { className: "text-2xl font-bold text-gray-600 dark:text-gray-400 mt-8", children: ":" }),
|
|
2044
|
+
/* @__PURE__ */ (0, import_jsx_runtime53.jsxs)("div", { className: "flex flex-col items-center", children: [
|
|
2045
|
+
/* @__PURE__ */ (0, import_jsx_runtime53.jsx)("label", { className: "text-xs font-semibold text-gray-600 dark:text-gray-400 mb-2", children: "Minute" }),
|
|
2046
|
+
/* @__PURE__ */ (0, import_jsx_runtime53.jsxs)("div", { className: "flex flex-col items-center gap-1", children: [
|
|
2047
|
+
/* @__PURE__ */ (0, import_jsx_runtime53.jsx)(
|
|
2048
|
+
"button",
|
|
2049
|
+
{
|
|
2050
|
+
type: "button",
|
|
2051
|
+
onClick: () => handleTimeChange(selectedTime.hours, (selectedTime.minutes + 1) % 60),
|
|
2052
|
+
className: "p-1 hover:bg-gray-100 dark:hover:bg-gray-700 rounded transition-colors",
|
|
2053
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime53.jsx)("svg", { className: "w-4 h-4 text-gray-600 dark:text-gray-400", fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime53.jsx)("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M5 15l7-7 7 7" }) })
|
|
2054
|
+
}
|
|
2055
|
+
),
|
|
2056
|
+
/* @__PURE__ */ (0, import_jsx_runtime53.jsx)(
|
|
2057
|
+
"input",
|
|
2058
|
+
{
|
|
2059
|
+
type: "number",
|
|
2060
|
+
min: "0",
|
|
2061
|
+
max: "59",
|
|
2062
|
+
value: selectedTime.minutes,
|
|
2063
|
+
onChange: (e) => {
|
|
2064
|
+
const val = parseInt(e.target.value);
|
|
2065
|
+
if (!isNaN(val) && val >= 0 && val <= 59) {
|
|
2066
|
+
handleTimeChange(selectedTime.hours, val);
|
|
2067
|
+
}
|
|
2068
|
+
},
|
|
2069
|
+
className: "w-16 px-2 py-2 text-center border border-gray-300 dark:border-gray-600 rounded-lg bg-white dark:bg-gray-700 text-gray-900 dark:text-gray-100 focus:outline-none focus:ring-2 focus:ring-blue-500 text-lg font-semibold [appearance:textfield] [&::-webkit-outer-spin-button]:appearance-none [&::-webkit-inner-spin-button]:appearance-none"
|
|
2070
|
+
}
|
|
2071
|
+
),
|
|
2072
|
+
/* @__PURE__ */ (0, import_jsx_runtime53.jsx)(
|
|
2073
|
+
"button",
|
|
2074
|
+
{
|
|
2075
|
+
type: "button",
|
|
2076
|
+
onClick: () => handleTimeChange(selectedTime.hours, (selectedTime.minutes - 1 + 60) % 60),
|
|
2077
|
+
className: "p-1 hover:bg-gray-100 dark:hover:bg-gray-700 rounded transition-colors",
|
|
2078
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime53.jsx)("svg", { className: "w-4 h-4 text-gray-600 dark:text-gray-400", fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime53.jsx)("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M19 9l-7 7-7-7" }) })
|
|
2079
|
+
}
|
|
2080
|
+
)
|
|
2081
|
+
] })
|
|
2082
|
+
] })
|
|
2083
|
+
] }),
|
|
2084
|
+
/* @__PURE__ */ (0, import_jsx_runtime53.jsx)("div", { className: "text-center text-sm text-gray-600 dark:text-gray-400 mb-4", children: formatTime(selectedTime.hours, selectedTime.minutes) }),
|
|
2085
|
+
/* @__PURE__ */ (0, import_jsx_runtime53.jsx)(
|
|
2086
|
+
"button",
|
|
2087
|
+
{
|
|
2088
|
+
onClick: handleDone,
|
|
2089
|
+
className: "w-full px-4 py-2 bg-blue-600 text-white rounded-lg hover:bg-blue-700 transition-colors font-medium",
|
|
2090
|
+
children: "Done"
|
|
2091
|
+
}
|
|
2092
|
+
)
|
|
2093
|
+
] })
|
|
2094
|
+
]
|
|
2095
|
+
}
|
|
2096
|
+
) : null;
|
|
2097
|
+
return /* @__PURE__ */ (0, import_jsx_runtime53.jsxs)("div", { className, children: [
|
|
2098
|
+
label && /* @__PURE__ */ (0, import_jsx_runtime53.jsx)("label", { className: "block text-sm font-medium text-gray-700 dark:text-gray-300 mb-1", children: label }),
|
|
2099
|
+
/* @__PURE__ */ (0, import_jsx_runtime53.jsxs)(
|
|
2100
|
+
"div",
|
|
2101
|
+
{
|
|
2102
|
+
ref: inputRef,
|
|
2103
|
+
onClick: () => !disabled && setIsOpen(!isOpen),
|
|
2104
|
+
className: `${baseStyles} ${errorStyles} ${disabledStyles} flex items-center justify-between`.trim(),
|
|
2105
|
+
children: [
|
|
2106
|
+
/* @__PURE__ */ (0, import_jsx_runtime53.jsx)("span", { className: !value ? "text-gray-500 dark:text-gray-400" : "", children: value ? formatDateTime(value) : placeholder }),
|
|
2107
|
+
/* @__PURE__ */ (0, import_jsx_runtime53.jsx)("svg", { className: "w-5 h-5 text-gray-400", fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime53.jsx)("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M8 7V3m8 4V3m-9 8h10M5 21h14a2 2 0 002-2V7a2 2 0 00-2-2H5a2 2 0 00-2 2v12a2 2 0 002 2z" }) })
|
|
2108
|
+
]
|
|
2109
|
+
}
|
|
2110
|
+
),
|
|
2111
|
+
error && /* @__PURE__ */ (0, import_jsx_runtime53.jsx)("p", { className: "mt-1 text-sm text-red-600 dark:text-red-400", children: error }),
|
|
2112
|
+
helperText && !error && /* @__PURE__ */ (0, import_jsx_runtime53.jsx)("p", { className: "mt-1 text-sm text-gray-500 dark:text-gray-400", children: helperText }),
|
|
2113
|
+
mounted && (0, import_react_dom3.createPortal)(picker, document.body)
|
|
2114
|
+
] });
|
|
2115
|
+
};
|
|
2116
|
+
DateTimePicker.displayName = "DateTimePicker";
|
|
2117
|
+
|
|
2118
|
+
// src/components/Calendar.tsx
|
|
2119
|
+
var import_react15 = require("react");
|
|
2120
|
+
var import_jsx_runtime54 = require("react/jsx-runtime");
|
|
2121
|
+
var DAYS3 = ["Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat"];
|
|
2122
|
+
var MONTHS3 = [
|
|
2123
|
+
"January",
|
|
2124
|
+
"February",
|
|
2125
|
+
"March",
|
|
2126
|
+
"April",
|
|
2127
|
+
"May",
|
|
2128
|
+
"June",
|
|
2129
|
+
"July",
|
|
2130
|
+
"August",
|
|
2131
|
+
"September",
|
|
2132
|
+
"October",
|
|
2133
|
+
"November",
|
|
2134
|
+
"December"
|
|
2135
|
+
];
|
|
2136
|
+
var Calendar = ({
|
|
2137
|
+
value,
|
|
2138
|
+
onChange,
|
|
2139
|
+
minDate,
|
|
2140
|
+
maxDate,
|
|
2141
|
+
className = ""
|
|
2142
|
+
}) => {
|
|
2143
|
+
const { theme } = useTheme();
|
|
2144
|
+
const [currentDate, setCurrentDate] = (0, import_react15.useState)(value || /* @__PURE__ */ new Date());
|
|
2145
|
+
const [viewDate, setViewDate] = (0, import_react15.useState)(value || /* @__PURE__ */ new Date());
|
|
2146
|
+
const year = viewDate.getFullYear();
|
|
2147
|
+
const month = viewDate.getMonth();
|
|
2148
|
+
const firstDayOfMonth = new Date(year, month, 1).getDay();
|
|
2149
|
+
const daysInMonth = new Date(year, month + 1, 0).getDate();
|
|
2150
|
+
const daysInPrevMonth = new Date(year, month, 0).getDate();
|
|
2151
|
+
const calendarDays = [];
|
|
2152
|
+
for (let i = firstDayOfMonth - 1; i >= 0; i--) {
|
|
2153
|
+
calendarDays.push(new Date(year, month - 1, daysInPrevMonth - i));
|
|
2154
|
+
}
|
|
2155
|
+
for (let i = 1; i <= daysInMonth; i++) {
|
|
2156
|
+
calendarDays.push(new Date(year, month, i));
|
|
2157
|
+
}
|
|
2158
|
+
const remainingDays = 42 - calendarDays.length;
|
|
2159
|
+
for (let i = 1; i <= remainingDays; i++) {
|
|
2160
|
+
calendarDays.push(new Date(year, month + 1, i));
|
|
2161
|
+
}
|
|
2162
|
+
const isSameDay = (date1, date2) => {
|
|
2163
|
+
return date1.getDate() === date2.getDate() && date1.getMonth() === date2.getMonth() && date1.getFullYear() === date2.getFullYear();
|
|
2164
|
+
};
|
|
2165
|
+
const isToday = (date) => {
|
|
2166
|
+
return isSameDay(date, /* @__PURE__ */ new Date());
|
|
2167
|
+
};
|
|
2168
|
+
const isSelected = (date) => {
|
|
2169
|
+
return value && isSameDay(date, value);
|
|
2170
|
+
};
|
|
2171
|
+
const isCurrentMonth = (date) => {
|
|
2172
|
+
return date.getMonth() === month;
|
|
2173
|
+
};
|
|
2174
|
+
const isDisabled = (date) => {
|
|
2175
|
+
if (minDate && date < minDate) return true;
|
|
2176
|
+
if (maxDate && date > maxDate) return true;
|
|
2177
|
+
return false;
|
|
2178
|
+
};
|
|
2179
|
+
const handleDateClick = (date) => {
|
|
2180
|
+
if (isDisabled(date)) return;
|
|
2181
|
+
setCurrentDate(date);
|
|
2182
|
+
onChange?.(date);
|
|
2183
|
+
};
|
|
2184
|
+
const handlePrevMonth = () => {
|
|
2185
|
+
setViewDate(new Date(year, month - 1, 1));
|
|
2186
|
+
};
|
|
2187
|
+
const handleNextMonth = () => {
|
|
2188
|
+
setViewDate(new Date(year, month + 1, 1));
|
|
2189
|
+
};
|
|
2190
|
+
const handleToday = () => {
|
|
2191
|
+
const today = /* @__PURE__ */ new Date();
|
|
2192
|
+
setViewDate(today);
|
|
2193
|
+
setCurrentDate(today);
|
|
2194
|
+
onChange?.(today);
|
|
2195
|
+
};
|
|
2196
|
+
return /* @__PURE__ */ (0, import_jsx_runtime54.jsxs)("div", { className: `bg-white dark:bg-gray-800 rounded-lg border border-gray-200 dark:border-gray-700 p-4 ${className}`, children: [
|
|
2197
|
+
/* @__PURE__ */ (0, import_jsx_runtime54.jsxs)("div", { className: "flex items-center justify-between mb-4", children: [
|
|
2198
|
+
/* @__PURE__ */ (0, import_jsx_runtime54.jsx)(
|
|
2199
|
+
"button",
|
|
1585
2200
|
{
|
|
1586
|
-
|
|
1587
|
-
|
|
1588
|
-
|
|
1589
|
-
className:
|
|
1590
|
-
...props
|
|
2201
|
+
onClick: handlePrevMonth,
|
|
2202
|
+
className: "p-2 hover:bg-gray-100 dark:hover:bg-gray-700 rounded-lg transition-colors",
|
|
2203
|
+
"aria-label": "Previous month",
|
|
2204
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime54.jsx)("svg", { className: "w-5 h-5 text-gray-600 dark:text-gray-400", fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime54.jsx)("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M15 19l-7-7 7-7" }) })
|
|
1591
2205
|
}
|
|
1592
2206
|
),
|
|
1593
|
-
|
|
1594
|
-
|
|
1595
|
-
|
|
1596
|
-
|
|
1597
|
-
|
|
1598
|
-
|
|
2207
|
+
/* @__PURE__ */ (0, import_jsx_runtime54.jsxs)("div", { className: "flex items-center gap-2", children: [
|
|
2208
|
+
/* @__PURE__ */ (0, import_jsx_runtime54.jsxs)("h2", { className: "text-lg font-semibold text-gray-900 dark:text-gray-100", children: [
|
|
2209
|
+
MONTHS3[month],
|
|
2210
|
+
" ",
|
|
2211
|
+
year
|
|
2212
|
+
] }),
|
|
2213
|
+
/* @__PURE__ */ (0, import_jsx_runtime54.jsx)(
|
|
2214
|
+
"button",
|
|
2215
|
+
{
|
|
2216
|
+
onClick: handleToday,
|
|
2217
|
+
className: "px-3 py-1 text-sm bg-blue-600 text-white rounded hover:bg-blue-700 transition-colors",
|
|
2218
|
+
children: "Today"
|
|
2219
|
+
}
|
|
2220
|
+
)
|
|
2221
|
+
] }),
|
|
2222
|
+
/* @__PURE__ */ (0, import_jsx_runtime54.jsx)(
|
|
2223
|
+
"button",
|
|
2224
|
+
{
|
|
2225
|
+
onClick: handleNextMonth,
|
|
2226
|
+
className: "p-2 hover:bg-gray-100 dark:hover:bg-gray-700 rounded-lg transition-colors",
|
|
2227
|
+
"aria-label": "Next month",
|
|
2228
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime54.jsx)("svg", { className: "w-5 h-5 text-gray-600 dark:text-gray-400", fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime54.jsx)("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M9 5l7 7-7 7" }) })
|
|
2229
|
+
}
|
|
2230
|
+
)
|
|
2231
|
+
] }),
|
|
2232
|
+
/* @__PURE__ */ (0, import_jsx_runtime54.jsx)("div", { className: "grid grid-cols-7 gap-1 mb-2", children: DAYS3.map((day) => /* @__PURE__ */ (0, import_jsx_runtime54.jsx)(
|
|
2233
|
+
"div",
|
|
2234
|
+
{
|
|
2235
|
+
className: "text-center text-xs font-semibold text-gray-600 dark:text-gray-400 py-2",
|
|
2236
|
+
children: day
|
|
2237
|
+
},
|
|
2238
|
+
day
|
|
2239
|
+
)) }),
|
|
2240
|
+
/* @__PURE__ */ (0, import_jsx_runtime54.jsx)("div", { className: "grid grid-cols-7 gap-1", children: calendarDays.map((date, index) => {
|
|
2241
|
+
if (!date) return /* @__PURE__ */ (0, import_jsx_runtime54.jsx)("div", {}, index);
|
|
2242
|
+
const isCurrentMonthDay = isCurrentMonth(date);
|
|
2243
|
+
const isTodayDay = isToday(date);
|
|
2244
|
+
const isSelectedDay = isSelected(date);
|
|
2245
|
+
const isDisabledDay = isDisabled(date);
|
|
2246
|
+
return /* @__PURE__ */ (0, import_jsx_runtime54.jsx)(
|
|
2247
|
+
"button",
|
|
2248
|
+
{
|
|
2249
|
+
onClick: () => handleDateClick(date),
|
|
2250
|
+
disabled: isDisabledDay,
|
|
2251
|
+
className: `
|
|
2252
|
+
aspect-square p-2 rounded-lg text-sm font-medium transition-all
|
|
2253
|
+
${!isCurrentMonthDay ? "text-gray-400 dark:text-gray-600" : "text-gray-900 dark:text-gray-100"}
|
|
2254
|
+
${isTodayDay && !isSelectedDay ? "bg-blue-50 dark:bg-blue-900/20 text-blue-600 dark:text-blue-400 font-bold" : ""}
|
|
2255
|
+
${isSelectedDay ? "bg-blue-600 text-white hover:bg-blue-700" : ""}
|
|
2256
|
+
${!isSelectedDay && !isDisabledDay ? "hover:bg-gray-100 dark:hover:bg-gray-700" : ""}
|
|
2257
|
+
${isDisabledDay ? "opacity-30 cursor-not-allowed" : "cursor-pointer"}
|
|
2258
|
+
`,
|
|
2259
|
+
children: date.getDate()
|
|
2260
|
+
},
|
|
2261
|
+
index
|
|
2262
|
+
);
|
|
2263
|
+
}) })
|
|
2264
|
+
] });
|
|
2265
|
+
};
|
|
1599
2266
|
|
|
1600
2267
|
// src/components/Radio.tsx
|
|
1601
|
-
var
|
|
1602
|
-
var
|
|
2268
|
+
var import_react16 = __toESM(require("react"));
|
|
2269
|
+
var import_jsx_runtime55 = require("react/jsx-runtime");
|
|
1603
2270
|
var Radio = ({
|
|
1604
2271
|
name,
|
|
1605
2272
|
options,
|
|
@@ -1610,7 +2277,7 @@ var Radio = ({
|
|
|
1610
2277
|
orientation = "vertical",
|
|
1611
2278
|
className = ""
|
|
1612
2279
|
}) => {
|
|
1613
|
-
const [internalValue, setInternalValue] =
|
|
2280
|
+
const [internalValue, setInternalValue] = import_react16.default.useState(defaultValue || "");
|
|
1614
2281
|
const value = controlledValue !== void 0 ? controlledValue : internalValue;
|
|
1615
2282
|
const handleChange = (optionValue) => {
|
|
1616
2283
|
if (disabled) return;
|
|
@@ -1618,17 +2285,17 @@ var Radio = ({
|
|
|
1618
2285
|
onChange?.(optionValue);
|
|
1619
2286
|
};
|
|
1620
2287
|
const containerClass = orientation === "horizontal" ? "flex flex-wrap gap-4" : "flex flex-col gap-2";
|
|
1621
|
-
return /* @__PURE__ */ (0,
|
|
2288
|
+
return /* @__PURE__ */ (0, import_jsx_runtime55.jsx)("div", { className: `${containerClass} ${className}`, role: "radiogroup", children: options.map((option) => {
|
|
1622
2289
|
const isDisabled = disabled || option.disabled;
|
|
1623
2290
|
const isChecked = value === option.value;
|
|
1624
2291
|
const id = `${name}-${option.value}`;
|
|
1625
|
-
return /* @__PURE__ */ (0,
|
|
2292
|
+
return /* @__PURE__ */ (0, import_jsx_runtime55.jsxs)(
|
|
1626
2293
|
"label",
|
|
1627
2294
|
{
|
|
1628
2295
|
htmlFor: id,
|
|
1629
2296
|
className: `flex items-center gap-2 cursor-pointer ${isDisabled ? "opacity-50 cursor-not-allowed" : ""}`,
|
|
1630
2297
|
children: [
|
|
1631
|
-
/* @__PURE__ */ (0,
|
|
2298
|
+
/* @__PURE__ */ (0, import_jsx_runtime55.jsx)(
|
|
1632
2299
|
"input",
|
|
1633
2300
|
{
|
|
1634
2301
|
type: "radio",
|
|
@@ -1641,7 +2308,7 @@ var Radio = ({
|
|
|
1641
2308
|
className: "w-4 h-4 text-blue-600 bg-gray-100 border-gray-300 focus:ring-blue-500 dark:focus:ring-blue-600 dark:ring-offset-gray-800 focus:ring-2 dark:bg-gray-700 dark:border-gray-600 cursor-pointer disabled:cursor-not-allowed"
|
|
1642
2309
|
}
|
|
1643
2310
|
),
|
|
1644
|
-
/* @__PURE__ */ (0,
|
|
2311
|
+
/* @__PURE__ */ (0, import_jsx_runtime55.jsx)("span", { className: "text-sm font-medium text-gray-900 dark:text-gray-300", children: option.label })
|
|
1645
2312
|
]
|
|
1646
2313
|
},
|
|
1647
2314
|
option.value
|
|
@@ -1650,7 +2317,7 @@ var Radio = ({
|
|
|
1650
2317
|
};
|
|
1651
2318
|
|
|
1652
2319
|
// src/components/ProgressBar.tsx
|
|
1653
|
-
var
|
|
2320
|
+
var import_jsx_runtime56 = require("react/jsx-runtime");
|
|
1654
2321
|
var ProgressBar = ({
|
|
1655
2322
|
value,
|
|
1656
2323
|
max = 100,
|
|
@@ -1672,15 +2339,15 @@ var ProgressBar = ({
|
|
|
1672
2339
|
warning: "bg-yellow-500 dark:bg-yellow-400",
|
|
1673
2340
|
danger: "bg-red-600 dark:bg-red-500"
|
|
1674
2341
|
};
|
|
1675
|
-
return /* @__PURE__ */ (0,
|
|
1676
|
-
(showLabel || label) && /* @__PURE__ */ (0,
|
|
1677
|
-
label && /* @__PURE__ */ (0,
|
|
1678
|
-
showLabel && /* @__PURE__ */ (0,
|
|
2342
|
+
return /* @__PURE__ */ (0, import_jsx_runtime56.jsxs)("div", { className: `w-full ${className}`, children: [
|
|
2343
|
+
(showLabel || label) && /* @__PURE__ */ (0, import_jsx_runtime56.jsxs)("div", { className: "flex justify-between items-center mb-1", children: [
|
|
2344
|
+
label && /* @__PURE__ */ (0, import_jsx_runtime56.jsx)("span", { className: "text-sm font-medium text-gray-700 dark:text-gray-300", children: label }),
|
|
2345
|
+
showLabel && /* @__PURE__ */ (0, import_jsx_runtime56.jsxs)("span", { className: "text-sm font-medium text-gray-700 dark:text-gray-300", children: [
|
|
1679
2346
|
Math.round(percentage),
|
|
1680
2347
|
"%"
|
|
1681
2348
|
] })
|
|
1682
2349
|
] }),
|
|
1683
|
-
/* @__PURE__ */ (0,
|
|
2350
|
+
/* @__PURE__ */ (0, import_jsx_runtime56.jsx)(
|
|
1684
2351
|
"div",
|
|
1685
2352
|
{
|
|
1686
2353
|
className: `w-full bg-gray-200 dark:bg-gray-700 rounded-full overflow-hidden ${sizeClasses6[size]}`,
|
|
@@ -1688,7 +2355,7 @@ var ProgressBar = ({
|
|
|
1688
2355
|
"aria-valuenow": value,
|
|
1689
2356
|
"aria-valuemin": 0,
|
|
1690
2357
|
"aria-valuemax": max,
|
|
1691
|
-
children: /* @__PURE__ */ (0,
|
|
2358
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime56.jsx)(
|
|
1692
2359
|
"div",
|
|
1693
2360
|
{
|
|
1694
2361
|
className: `${sizeClasses6[size]} ${variantClasses[variant]} rounded-full transition-all duration-300 ease-out`,
|
|
@@ -1701,8 +2368,8 @@ var ProgressBar = ({
|
|
|
1701
2368
|
};
|
|
1702
2369
|
|
|
1703
2370
|
// src/components/Slider.tsx
|
|
1704
|
-
var
|
|
1705
|
-
var
|
|
2371
|
+
var import_react17 = __toESM(require("react"));
|
|
2372
|
+
var import_jsx_runtime57 = require("react/jsx-runtime");
|
|
1706
2373
|
var Slider = ({
|
|
1707
2374
|
value: controlledValue,
|
|
1708
2375
|
defaultValue = 50,
|
|
@@ -1715,7 +2382,7 @@ var Slider = ({
|
|
|
1715
2382
|
label,
|
|
1716
2383
|
className = ""
|
|
1717
2384
|
}) => {
|
|
1718
|
-
const [internalValue, setInternalValue] =
|
|
2385
|
+
const [internalValue, setInternalValue] = import_react17.default.useState(defaultValue);
|
|
1719
2386
|
const value = controlledValue !== void 0 ? controlledValue : internalValue;
|
|
1720
2387
|
const handleChange = (e) => {
|
|
1721
2388
|
const newValue = Number(e.target.value);
|
|
@@ -1723,21 +2390,21 @@ var Slider = ({
|
|
|
1723
2390
|
onChange?.(newValue);
|
|
1724
2391
|
};
|
|
1725
2392
|
const percentage = (value - min) / (max - min) * 100;
|
|
1726
|
-
return /* @__PURE__ */ (0,
|
|
1727
|
-
(label || showValue) && /* @__PURE__ */ (0,
|
|
1728
|
-
label && /* @__PURE__ */ (0,
|
|
1729
|
-
showValue && /* @__PURE__ */ (0,
|
|
2393
|
+
return /* @__PURE__ */ (0, import_jsx_runtime57.jsxs)("div", { className: `w-full ${className}`, children: [
|
|
2394
|
+
(label || showValue) && /* @__PURE__ */ (0, import_jsx_runtime57.jsxs)("div", { className: "flex justify-between items-center mb-2", children: [
|
|
2395
|
+
label && /* @__PURE__ */ (0, import_jsx_runtime57.jsx)("label", { className: "text-sm font-medium text-gray-700 dark:text-gray-300", children: label }),
|
|
2396
|
+
showValue && /* @__PURE__ */ (0, import_jsx_runtime57.jsx)("span", { className: "text-sm font-medium text-gray-700 dark:text-gray-300", children: value })
|
|
1730
2397
|
] }),
|
|
1731
|
-
/* @__PURE__ */ (0,
|
|
1732
|
-
/* @__PURE__ */ (0,
|
|
1733
|
-
/* @__PURE__ */ (0,
|
|
2398
|
+
/* @__PURE__ */ (0, import_jsx_runtime57.jsxs)("div", { className: "relative", children: [
|
|
2399
|
+
/* @__PURE__ */ (0, import_jsx_runtime57.jsx)("div", { className: "absolute inset-0 h-2 bg-gray-200 dark:bg-gray-700 rounded-full top-1/2 -translate-y-1/2" }),
|
|
2400
|
+
/* @__PURE__ */ (0, import_jsx_runtime57.jsx)(
|
|
1734
2401
|
"div",
|
|
1735
2402
|
{
|
|
1736
2403
|
className: "absolute h-2 bg-blue-600 dark:bg-blue-500 rounded-full top-1/2 -translate-y-1/2 pointer-events-none",
|
|
1737
2404
|
style: { width: `${percentage}%` }
|
|
1738
2405
|
}
|
|
1739
2406
|
),
|
|
1740
|
-
/* @__PURE__ */ (0,
|
|
2407
|
+
/* @__PURE__ */ (0, import_jsx_runtime57.jsx)(
|
|
1741
2408
|
"input",
|
|
1742
2409
|
{
|
|
1743
2410
|
type: "range",
|
|
@@ -1759,8 +2426,8 @@ var Slider = ({
|
|
|
1759
2426
|
};
|
|
1760
2427
|
|
|
1761
2428
|
// src/components/Avatar.tsx
|
|
1762
|
-
var
|
|
1763
|
-
var
|
|
2429
|
+
var import_react18 = __toESM(require("react"));
|
|
2430
|
+
var import_jsx_runtime58 = require("react/jsx-runtime");
|
|
1764
2431
|
var Avatar = ({
|
|
1765
2432
|
src,
|
|
1766
2433
|
alt,
|
|
@@ -1770,7 +2437,7 @@ var Avatar = ({
|
|
|
1770
2437
|
className = "",
|
|
1771
2438
|
fallbackColor = "bg-blue-600"
|
|
1772
2439
|
}) => {
|
|
1773
|
-
const [imageError, setImageError] =
|
|
2440
|
+
const [imageError, setImageError] = import_react18.default.useState(false);
|
|
1774
2441
|
const sizeClasses6 = {
|
|
1775
2442
|
xs: "w-6 h-6 text-xs",
|
|
1776
2443
|
sm: "w-8 h-8 text-sm",
|
|
@@ -1788,11 +2455,11 @@ var Avatar = ({
|
|
|
1788
2455
|
};
|
|
1789
2456
|
const showImage = src && !imageError;
|
|
1790
2457
|
const showInitials = !showImage && name;
|
|
1791
|
-
return /* @__PURE__ */ (0,
|
|
2458
|
+
return /* @__PURE__ */ (0, import_jsx_runtime58.jsx)(
|
|
1792
2459
|
"div",
|
|
1793
2460
|
{
|
|
1794
2461
|
className: `${sizeClasses6[size]} ${shapeClass} flex items-center justify-center overflow-hidden ${showImage ? "bg-gray-200 dark:bg-gray-700" : `${fallbackColor} text-white`} ${className}`,
|
|
1795
|
-
children: showImage ? /* @__PURE__ */ (0,
|
|
2462
|
+
children: showImage ? /* @__PURE__ */ (0, import_jsx_runtime58.jsx)(
|
|
1796
2463
|
"img",
|
|
1797
2464
|
{
|
|
1798
2465
|
src,
|
|
@@ -1800,13 +2467,13 @@ var Avatar = ({
|
|
|
1800
2467
|
className: "w-full h-full object-cover",
|
|
1801
2468
|
onError: () => setImageError(true)
|
|
1802
2469
|
}
|
|
1803
|
-
) : showInitials ? /* @__PURE__ */ (0,
|
|
2470
|
+
) : showInitials ? /* @__PURE__ */ (0, import_jsx_runtime58.jsx)("span", { className: "font-semibold select-none", children: getInitials(name) }) : /* @__PURE__ */ (0, import_jsx_runtime58.jsx)(
|
|
1804
2471
|
"svg",
|
|
1805
2472
|
{
|
|
1806
2473
|
className: "w-full h-full text-gray-400 dark:text-gray-600",
|
|
1807
2474
|
fill: "currentColor",
|
|
1808
2475
|
viewBox: "0 0 24 24",
|
|
1809
|
-
children: /* @__PURE__ */ (0,
|
|
2476
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime58.jsx)("path", { d: "M12 12c2.21 0 4-1.79 4-4s-1.79-4-4-4-4 1.79-4 4 1.79 4 4 4zm0 2c-2.67 0-8 1.34-8 4v2h16v-2c0-2.66-5.33-4-8-4z" })
|
|
1810
2477
|
}
|
|
1811
2478
|
)
|
|
1812
2479
|
}
|
|
@@ -1814,7 +2481,7 @@ var Avatar = ({
|
|
|
1814
2481
|
};
|
|
1815
2482
|
|
|
1816
2483
|
// src/components/Textarea.tsx
|
|
1817
|
-
var
|
|
2484
|
+
var import_jsx_runtime59 = require("react/jsx-runtime");
|
|
1818
2485
|
var Textarea = ({
|
|
1819
2486
|
label,
|
|
1820
2487
|
error,
|
|
@@ -1841,9 +2508,9 @@ var Textarea = ({
|
|
|
1841
2508
|
bg-white dark:bg-gray-800 text-gray-900 dark:text-gray-100
|
|
1842
2509
|
placeholder:text-gray-500 dark:placeholder:text-gray-400
|
|
1843
2510
|
disabled:opacity-50 disabled:cursor-not-allowed disabled:bg-gray-50 dark:disabled:bg-gray-900`;
|
|
1844
|
-
return /* @__PURE__ */ (0,
|
|
1845
|
-
label && /* @__PURE__ */ (0,
|
|
1846
|
-
/* @__PURE__ */ (0,
|
|
2511
|
+
return /* @__PURE__ */ (0, import_jsx_runtime59.jsxs)("div", { className: `w-full ${className}`, children: [
|
|
2512
|
+
label && /* @__PURE__ */ (0, import_jsx_runtime59.jsx)("label", { className: "block text-sm font-medium text-gray-700 dark:text-gray-300 mb-1", children: label }),
|
|
2513
|
+
/* @__PURE__ */ (0, import_jsx_runtime59.jsx)(
|
|
1847
2514
|
"textarea",
|
|
1848
2515
|
{
|
|
1849
2516
|
className: `${baseClasses} ${sizeClasses6[size]} ${resizeClasses[resize]}`,
|
|
@@ -1851,25 +2518,25 @@ var Textarea = ({
|
|
|
1851
2518
|
...props
|
|
1852
2519
|
}
|
|
1853
2520
|
),
|
|
1854
|
-
error && /* @__PURE__ */ (0,
|
|
1855
|
-
helperText && !error && /* @__PURE__ */ (0,
|
|
2521
|
+
error && /* @__PURE__ */ (0, import_jsx_runtime59.jsx)("p", { className: "mt-1 text-sm text-red-600 dark:text-red-400", children: error }),
|
|
2522
|
+
helperText && !error && /* @__PURE__ */ (0, import_jsx_runtime59.jsx)("p", { className: "mt-1 text-sm text-gray-500 dark:text-gray-400", children: helperText })
|
|
1856
2523
|
] });
|
|
1857
2524
|
};
|
|
1858
2525
|
|
|
1859
2526
|
// src/components/Toast.tsx
|
|
1860
|
-
var
|
|
1861
|
-
var
|
|
1862
|
-
var ToastContext = (0,
|
|
2527
|
+
var import_react19 = require("react");
|
|
2528
|
+
var import_jsx_runtime60 = require("react/jsx-runtime");
|
|
2529
|
+
var ToastContext = (0, import_react19.createContext)(void 0);
|
|
1863
2530
|
var useToast = () => {
|
|
1864
|
-
const context = (0,
|
|
2531
|
+
const context = (0, import_react19.useContext)(ToastContext);
|
|
1865
2532
|
if (!context) {
|
|
1866
2533
|
throw new Error("useToast must be used within a ToastProvider");
|
|
1867
2534
|
}
|
|
1868
2535
|
return context;
|
|
1869
2536
|
};
|
|
1870
2537
|
var ToastProvider = ({ children, position = "top-right" }) => {
|
|
1871
|
-
const [toasts, setToasts] = (0,
|
|
1872
|
-
const addToast = (0,
|
|
2538
|
+
const [toasts, setToasts] = (0, import_react19.useState)([]);
|
|
2539
|
+
const addToast = (0, import_react19.useCallback)((toast2) => {
|
|
1873
2540
|
const id = Math.random().toString(36).substring(7);
|
|
1874
2541
|
const newToast = { ...toast2, id };
|
|
1875
2542
|
setToasts((prev) => [...prev, newToast]);
|
|
@@ -1878,7 +2545,7 @@ var ToastProvider = ({ children, position = "top-right" }) => {
|
|
|
1878
2545
|
removeToast(id);
|
|
1879
2546
|
}, duration);
|
|
1880
2547
|
}, []);
|
|
1881
|
-
const removeToast = (0,
|
|
2548
|
+
const removeToast = (0, import_react19.useCallback)((id) => {
|
|
1882
2549
|
setToasts((prev) => prev.filter((toast2) => toast2.id !== id));
|
|
1883
2550
|
}, []);
|
|
1884
2551
|
const positionClasses2 = {
|
|
@@ -1889,9 +2556,9 @@ var ToastProvider = ({ children, position = "top-right" }) => {
|
|
|
1889
2556
|
"top-center": "top-4 left-1/2 -translate-x-1/2",
|
|
1890
2557
|
"bottom-center": "bottom-4 left-1/2 -translate-x-1/2"
|
|
1891
2558
|
};
|
|
1892
|
-
return /* @__PURE__ */ (0,
|
|
2559
|
+
return /* @__PURE__ */ (0, import_jsx_runtime60.jsxs)(ToastContext.Provider, { value: { toasts, addToast, removeToast }, children: [
|
|
1893
2560
|
children,
|
|
1894
|
-
/* @__PURE__ */ (0,
|
|
2561
|
+
/* @__PURE__ */ (0, import_jsx_runtime60.jsx)("div", { className: `fixed ${positionClasses2[position]} z-50 flex flex-col gap-2 max-w-md`, children: toasts.map((toast2) => /* @__PURE__ */ (0, import_jsx_runtime60.jsx)(ToastItem, { toast: toast2, onClose: () => removeToast(toast2.id) }, toast2.id)) })
|
|
1895
2562
|
] });
|
|
1896
2563
|
};
|
|
1897
2564
|
var ToastItem = ({ toast: toast2, onClose }) => {
|
|
@@ -1902,27 +2569,27 @@ var ToastItem = ({ toast: toast2, onClose }) => {
|
|
|
1902
2569
|
info: "bg-blue-50 dark:bg-blue-900/30 border-blue-500 text-blue-800 dark:text-blue-200"
|
|
1903
2570
|
};
|
|
1904
2571
|
const typeIcons = {
|
|
1905
|
-
success: /* @__PURE__ */ (0,
|
|
1906
|
-
error: /* @__PURE__ */ (0,
|
|
1907
|
-
warning: /* @__PURE__ */ (0,
|
|
1908
|
-
info: /* @__PURE__ */ (0,
|
|
2572
|
+
success: /* @__PURE__ */ (0, import_jsx_runtime60.jsx)(CheckIcon, { size: "sm", className: "text-green-600 dark:text-green-400" }),
|
|
2573
|
+
error: /* @__PURE__ */ (0, import_jsx_runtime60.jsx)(CloseIcon, { size: "sm", className: "text-red-600 dark:text-red-400" }),
|
|
2574
|
+
warning: /* @__PURE__ */ (0, import_jsx_runtime60.jsx)("svg", { className: "w-4 h-4 text-yellow-600 dark:text-yellow-400", fill: "currentColor", viewBox: "0 0 20 20", children: /* @__PURE__ */ (0, import_jsx_runtime60.jsx)("path", { fillRule: "evenodd", d: "M8.257 3.099c.765-1.36 2.722-1.36 3.486 0l5.58 9.92c.75 1.334-.213 2.98-1.742 2.98H4.42c-1.53 0-2.493-1.646-1.743-2.98l5.58-9.92zM11 13a1 1 0 11-2 0 1 1 0 012 0zm-1-8a1 1 0 00-1 1v3a1 1 0 002 0V6a1 1 0 00-1-1z", clipRule: "evenodd" }) }),
|
|
2575
|
+
info: /* @__PURE__ */ (0, import_jsx_runtime60.jsx)("svg", { className: "w-4 h-4 text-blue-600 dark:text-blue-400", fill: "currentColor", viewBox: "0 0 20 20", children: /* @__PURE__ */ (0, import_jsx_runtime60.jsx)("path", { fillRule: "evenodd", d: "M18 10a8 8 0 11-16 0 8 8 0 0116 0zm-7-4a1 1 0 11-2 0 1 1 0 012 0zM9 9a1 1 0 000 2v3a1 1 0 001 1h1a1 1 0 100-2v-3a1 1 0 00-1-1H9z", clipRule: "evenodd" }) })
|
|
1909
2576
|
};
|
|
1910
2577
|
const type = toast2.type || "info";
|
|
1911
|
-
return /* @__PURE__ */ (0,
|
|
2578
|
+
return /* @__PURE__ */ (0, import_jsx_runtime60.jsxs)(
|
|
1912
2579
|
"div",
|
|
1913
2580
|
{
|
|
1914
2581
|
className: `flex items-start gap-3 p-4 rounded-lg border-l-4 shadow-lg backdrop-blur-sm ${typeStyles[type]} animate-slide-in`,
|
|
1915
2582
|
role: "alert",
|
|
1916
2583
|
children: [
|
|
1917
|
-
/* @__PURE__ */ (0,
|
|
1918
|
-
/* @__PURE__ */ (0,
|
|
1919
|
-
/* @__PURE__ */ (0,
|
|
2584
|
+
/* @__PURE__ */ (0, import_jsx_runtime60.jsx)("div", { className: "flex-shrink-0 mt-0.5", children: typeIcons[type] }),
|
|
2585
|
+
/* @__PURE__ */ (0, import_jsx_runtime60.jsx)("p", { className: "flex-1 text-sm font-medium", children: toast2.message }),
|
|
2586
|
+
/* @__PURE__ */ (0, import_jsx_runtime60.jsx)(
|
|
1920
2587
|
"button",
|
|
1921
2588
|
{
|
|
1922
2589
|
onClick: onClose,
|
|
1923
2590
|
className: "flex-shrink-0 text-gray-400 hover:text-gray-600 dark:hover:text-gray-200 transition-colors",
|
|
1924
2591
|
"aria-label": "Close",
|
|
1925
|
-
children: /* @__PURE__ */ (0,
|
|
2592
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime60.jsx)(CloseIcon, { size: "sm" })
|
|
1926
2593
|
}
|
|
1927
2594
|
)
|
|
1928
2595
|
]
|
|
@@ -1953,8 +2620,8 @@ var toast = {
|
|
|
1953
2620
|
};
|
|
1954
2621
|
|
|
1955
2622
|
// src/components/Stepper.tsx
|
|
1956
|
-
var
|
|
1957
|
-
var
|
|
2623
|
+
var import_react20 = __toESM(require("react"));
|
|
2624
|
+
var import_jsx_runtime61 = require("react/jsx-runtime");
|
|
1958
2625
|
var Stepper = ({
|
|
1959
2626
|
steps,
|
|
1960
2627
|
currentStep,
|
|
@@ -1962,18 +2629,18 @@ var Stepper = ({
|
|
|
1962
2629
|
className = ""
|
|
1963
2630
|
}) => {
|
|
1964
2631
|
const isHorizontal = orientation === "horizontal";
|
|
1965
|
-
return /* @__PURE__ */ (0,
|
|
2632
|
+
return /* @__PURE__ */ (0, import_jsx_runtime61.jsx)("div", { className: `${isHorizontal ? "flex items-center" : "flex flex-col"} ${className}`, children: steps.map((step, index) => {
|
|
1966
2633
|
const stepNumber = index + 1;
|
|
1967
2634
|
const isActive = stepNumber === currentStep;
|
|
1968
2635
|
const isCompleted = stepNumber < currentStep;
|
|
1969
2636
|
const isLast = index === steps.length - 1;
|
|
1970
|
-
return /* @__PURE__ */ (0,
|
|
1971
|
-
/* @__PURE__ */ (0,
|
|
1972
|
-
/* @__PURE__ */ (0,
|
|
2637
|
+
return /* @__PURE__ */ (0, import_jsx_runtime61.jsxs)(import_react20.default.Fragment, { children: [
|
|
2638
|
+
/* @__PURE__ */ (0, import_jsx_runtime61.jsxs)("div", { className: `flex ${isHorizontal ? "flex-col items-center" : "flex-row items-start"} ${isHorizontal ? "" : "flex-1"}`, children: [
|
|
2639
|
+
/* @__PURE__ */ (0, import_jsx_runtime61.jsx)("div", { className: "flex items-center", children: /* @__PURE__ */ (0, import_jsx_runtime61.jsx)(
|
|
1973
2640
|
"div",
|
|
1974
2641
|
{
|
|
1975
2642
|
className: `flex items-center justify-center w-10 h-10 rounded-full border-2 transition-all ${isCompleted ? "bg-blue-600 border-blue-600 dark:bg-blue-500 dark:border-blue-500" : isActive ? "border-blue-600 bg-white dark:border-blue-500 dark:bg-gray-800" : "border-gray-300 bg-white dark:border-gray-600 dark:bg-gray-800"}`,
|
|
1976
|
-
children: isCompleted ? /* @__PURE__ */ (0,
|
|
2643
|
+
children: isCompleted ? /* @__PURE__ */ (0, import_jsx_runtime61.jsx)(CheckIcon, { size: "sm", className: "text-white" }) : /* @__PURE__ */ (0, import_jsx_runtime61.jsx)(
|
|
1977
2644
|
"span",
|
|
1978
2645
|
{
|
|
1979
2646
|
className: `text-sm font-semibold ${isActive ? "text-blue-600 dark:text-blue-400" : "text-gray-500 dark:text-gray-400"}`,
|
|
@@ -1982,18 +2649,18 @@ var Stepper = ({
|
|
|
1982
2649
|
)
|
|
1983
2650
|
}
|
|
1984
2651
|
) }),
|
|
1985
|
-
/* @__PURE__ */ (0,
|
|
1986
|
-
/* @__PURE__ */ (0,
|
|
2652
|
+
/* @__PURE__ */ (0, import_jsx_runtime61.jsxs)("div", { className: `${isHorizontal ? "mt-2 text-center" : "ml-4 pb-8"} ${isLast && !isHorizontal ? "pb-0" : ""}`, children: [
|
|
2653
|
+
/* @__PURE__ */ (0, import_jsx_runtime61.jsx)(
|
|
1987
2654
|
"p",
|
|
1988
2655
|
{
|
|
1989
2656
|
className: `text-sm font-medium ${isActive || isCompleted ? "text-gray-900 dark:text-gray-100" : "text-gray-500 dark:text-gray-400"}`,
|
|
1990
2657
|
children: step.label
|
|
1991
2658
|
}
|
|
1992
2659
|
),
|
|
1993
|
-
step.description && /* @__PURE__ */ (0,
|
|
2660
|
+
step.description && /* @__PURE__ */ (0, import_jsx_runtime61.jsx)("p", { className: "text-xs text-gray-500 dark:text-gray-400 mt-1", children: step.description })
|
|
1994
2661
|
] })
|
|
1995
2662
|
] }),
|
|
1996
|
-
!isLast && /* @__PURE__ */ (0,
|
|
2663
|
+
!isLast && /* @__PURE__ */ (0, import_jsx_runtime61.jsx)(
|
|
1997
2664
|
"div",
|
|
1998
2665
|
{
|
|
1999
2666
|
className: `${isHorizontal ? "flex-1 h-0.5 mx-4" : "w-0.5 h-full ml-5 -mt-8"} ${isCompleted || isActive && stepNumber < currentStep ? "bg-blue-600 dark:bg-blue-500" : "bg-gray-300 dark:bg-gray-600"}`
|
|
@@ -2004,7 +2671,7 @@ var Stepper = ({
|
|
|
2004
2671
|
};
|
|
2005
2672
|
|
|
2006
2673
|
// src/components/Divider.tsx
|
|
2007
|
-
var
|
|
2674
|
+
var import_jsx_runtime62 = require("react/jsx-runtime");
|
|
2008
2675
|
var Divider = ({
|
|
2009
2676
|
orientation = "horizontal",
|
|
2010
2677
|
variant = "solid",
|
|
@@ -2023,14 +2690,14 @@ var Divider = ({
|
|
|
2023
2690
|
center: "justify-center",
|
|
2024
2691
|
right: "justify-end"
|
|
2025
2692
|
};
|
|
2026
|
-
return /* @__PURE__ */ (0,
|
|
2027
|
-
labelPosition !== "left" && /* @__PURE__ */ (0,
|
|
2028
|
-
/* @__PURE__ */ (0,
|
|
2029
|
-
labelPosition !== "right" && /* @__PURE__ */ (0,
|
|
2693
|
+
return /* @__PURE__ */ (0, import_jsx_runtime62.jsxs)("div", { className: `flex items-center ${alignmentClasses[labelPosition]} ${className}`, role: "separator", children: [
|
|
2694
|
+
labelPosition !== "left" && /* @__PURE__ */ (0, import_jsx_runtime62.jsx)("div", { className: `flex-1 border-t ${variantClasses[variant]} border-gray-300 dark:border-gray-600` }),
|
|
2695
|
+
/* @__PURE__ */ (0, import_jsx_runtime62.jsx)("span", { className: "px-4 text-sm text-gray-500 dark:text-gray-400", children: label }),
|
|
2696
|
+
labelPosition !== "right" && /* @__PURE__ */ (0, import_jsx_runtime62.jsx)("div", { className: `flex-1 border-t ${variantClasses[variant]} border-gray-300 dark:border-gray-600` })
|
|
2030
2697
|
] });
|
|
2031
2698
|
}
|
|
2032
2699
|
if (orientation === "vertical") {
|
|
2033
|
-
return /* @__PURE__ */ (0,
|
|
2700
|
+
return /* @__PURE__ */ (0, import_jsx_runtime62.jsx)(
|
|
2034
2701
|
"div",
|
|
2035
2702
|
{
|
|
2036
2703
|
className: `inline-block h-full border-l ${variantClasses[variant]} border-gray-300 dark:border-gray-600 ${className}`,
|
|
@@ -2039,7 +2706,7 @@ var Divider = ({
|
|
|
2039
2706
|
}
|
|
2040
2707
|
);
|
|
2041
2708
|
}
|
|
2042
|
-
return /* @__PURE__ */ (0,
|
|
2709
|
+
return /* @__PURE__ */ (0, import_jsx_runtime62.jsx)(
|
|
2043
2710
|
"hr",
|
|
2044
2711
|
{
|
|
2045
2712
|
className: `border-t ${variantClasses[variant]} border-gray-300 dark:border-gray-600 ${className}`,
|
|
@@ -2049,8 +2716,8 @@ var Divider = ({
|
|
|
2049
2716
|
};
|
|
2050
2717
|
|
|
2051
2718
|
// src/components/FileUpload.tsx
|
|
2052
|
-
var
|
|
2053
|
-
var
|
|
2719
|
+
var import_react21 = require("react");
|
|
2720
|
+
var import_jsx_runtime63 = require("react/jsx-runtime");
|
|
2054
2721
|
var FileUpload = ({
|
|
2055
2722
|
accept,
|
|
2056
2723
|
multiple = false,
|
|
@@ -2063,9 +2730,9 @@ var FileUpload = ({
|
|
|
2063
2730
|
label,
|
|
2064
2731
|
helperText
|
|
2065
2732
|
}) => {
|
|
2066
|
-
const [files, setFiles] = (0,
|
|
2067
|
-
const [isDragging, setIsDragging] = (0,
|
|
2068
|
-
const fileInputRef = (0,
|
|
2733
|
+
const [files, setFiles] = (0, import_react21.useState)([]);
|
|
2734
|
+
const [isDragging, setIsDragging] = (0, import_react21.useState)(false);
|
|
2735
|
+
const fileInputRef = (0, import_react21.useRef)(null);
|
|
2069
2736
|
const formatFileSize = (bytes) => {
|
|
2070
2737
|
if (bytes === 0) return "0 Bytes";
|
|
2071
2738
|
const k = 1024;
|
|
@@ -2123,9 +2790,9 @@ var FileUpload = ({
|
|
|
2123
2790
|
setFiles(newFiles);
|
|
2124
2791
|
onChange?.(newFiles);
|
|
2125
2792
|
};
|
|
2126
|
-
return /* @__PURE__ */ (0,
|
|
2127
|
-
label && /* @__PURE__ */ (0,
|
|
2128
|
-
/* @__PURE__ */ (0,
|
|
2793
|
+
return /* @__PURE__ */ (0, import_jsx_runtime63.jsxs)("div", { className: `w-full ${className}`, children: [
|
|
2794
|
+
label && /* @__PURE__ */ (0, import_jsx_runtime63.jsx)("label", { className: "block text-sm font-medium text-gray-700 dark:text-gray-300 mb-2", children: label }),
|
|
2795
|
+
/* @__PURE__ */ (0, import_jsx_runtime63.jsxs)(
|
|
2129
2796
|
"div",
|
|
2130
2797
|
{
|
|
2131
2798
|
onDrop: handleDrop,
|
|
@@ -2134,7 +2801,7 @@ var FileUpload = ({
|
|
|
2134
2801
|
onClick: handleClick,
|
|
2135
2802
|
className: `relative border-2 border-dashed rounded-lg p-8 text-center cursor-pointer transition-all ${isDragging ? "border-blue-500 bg-blue-50 dark:bg-blue-900/20" : "border-gray-300 dark:border-gray-600 hover:border-gray-400 dark:hover:border-gray-500"} ${disabled ? "opacity-50 cursor-not-allowed" : ""}`,
|
|
2136
2803
|
children: [
|
|
2137
|
-
/* @__PURE__ */ (0,
|
|
2804
|
+
/* @__PURE__ */ (0, import_jsx_runtime63.jsx)(
|
|
2138
2805
|
"input",
|
|
2139
2806
|
{
|
|
2140
2807
|
ref: fileInputRef,
|
|
@@ -2146,14 +2813,14 @@ var FileUpload = ({
|
|
|
2146
2813
|
className: "hidden"
|
|
2147
2814
|
}
|
|
2148
2815
|
),
|
|
2149
|
-
/* @__PURE__ */ (0,
|
|
2150
|
-
/* @__PURE__ */ (0,
|
|
2151
|
-
/* @__PURE__ */ (0,
|
|
2152
|
-
/* @__PURE__ */ (0,
|
|
2153
|
-
/* @__PURE__ */ (0,
|
|
2816
|
+
/* @__PURE__ */ (0, import_jsx_runtime63.jsxs)("div", { className: "flex flex-col items-center gap-2", children: [
|
|
2817
|
+
/* @__PURE__ */ (0, import_jsx_runtime63.jsx)("div", { className: "w-12 h-12 rounded-full bg-gray-100 dark:bg-gray-800 flex items-center justify-center", children: /* @__PURE__ */ (0, import_jsx_runtime63.jsx)(UploadIcon, { size: "lg", className: "text-gray-400 dark:text-gray-500" }) }),
|
|
2818
|
+
/* @__PURE__ */ (0, import_jsx_runtime63.jsxs)("div", { children: [
|
|
2819
|
+
/* @__PURE__ */ (0, import_jsx_runtime63.jsxs)("p", { className: "text-sm font-medium text-gray-700 dark:text-gray-300", children: [
|
|
2820
|
+
/* @__PURE__ */ (0, import_jsx_runtime63.jsx)("span", { className: "text-blue-600 dark:text-blue-400", children: "Click to upload" }),
|
|
2154
2821
|
" or drag and drop"
|
|
2155
2822
|
] }),
|
|
2156
|
-
/* @__PURE__ */ (0,
|
|
2823
|
+
/* @__PURE__ */ (0, import_jsx_runtime63.jsxs)("p", { className: "text-xs text-gray-500 dark:text-gray-400 mt-1", children: [
|
|
2157
2824
|
accept ? `Accepted: ${accept}` : "Any file type",
|
|
2158
2825
|
maxSize && ` \u2022 Max size: ${formatFileSize(maxSize)}`
|
|
2159
2826
|
] })
|
|
@@ -2162,17 +2829,17 @@ var FileUpload = ({
|
|
|
2162
2829
|
]
|
|
2163
2830
|
}
|
|
2164
2831
|
),
|
|
2165
|
-
helperText && /* @__PURE__ */ (0,
|
|
2166
|
-
files.length > 0 && /* @__PURE__ */ (0,
|
|
2832
|
+
helperText && /* @__PURE__ */ (0, import_jsx_runtime63.jsx)("p", { className: "mt-2 text-sm text-gray-500 dark:text-gray-400", children: helperText }),
|
|
2833
|
+
files.length > 0 && /* @__PURE__ */ (0, import_jsx_runtime63.jsx)("div", { className: "mt-4 space-y-2", children: files.map((file, index) => /* @__PURE__ */ (0, import_jsx_runtime63.jsxs)(
|
|
2167
2834
|
"div",
|
|
2168
2835
|
{
|
|
2169
2836
|
className: "flex items-center justify-between p-3 bg-gray-50 dark:bg-gray-800 rounded-lg border border-gray-200 dark:border-gray-700",
|
|
2170
2837
|
children: [
|
|
2171
|
-
/* @__PURE__ */ (0,
|
|
2172
|
-
/* @__PURE__ */ (0,
|
|
2173
|
-
/* @__PURE__ */ (0,
|
|
2838
|
+
/* @__PURE__ */ (0, import_jsx_runtime63.jsxs)("div", { className: "flex-1 min-w-0", children: [
|
|
2839
|
+
/* @__PURE__ */ (0, import_jsx_runtime63.jsx)("p", { className: "text-sm font-medium text-gray-900 dark:text-gray-100 truncate", children: file.name }),
|
|
2840
|
+
/* @__PURE__ */ (0, import_jsx_runtime63.jsx)("p", { className: "text-xs text-gray-500 dark:text-gray-400", children: formatFileSize(file.size) })
|
|
2174
2841
|
] }),
|
|
2175
|
-
/* @__PURE__ */ (0,
|
|
2842
|
+
/* @__PURE__ */ (0, import_jsx_runtime63.jsx)(
|
|
2176
2843
|
"button",
|
|
2177
2844
|
{
|
|
2178
2845
|
onClick: (e) => {
|
|
@@ -2181,7 +2848,7 @@ var FileUpload = ({
|
|
|
2181
2848
|
},
|
|
2182
2849
|
className: "ml-4 text-gray-400 hover:text-red-600 dark:hover:text-red-400 transition-colors",
|
|
2183
2850
|
"aria-label": "Remove file",
|
|
2184
|
-
children: /* @__PURE__ */ (0,
|
|
2851
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime63.jsx)(CloseIcon, { size: "sm" })
|
|
2185
2852
|
}
|
|
2186
2853
|
)
|
|
2187
2854
|
]
|
|
@@ -2233,6 +2900,7 @@ function getThemeScript() {
|
|
|
2233
2900
|
Badge,
|
|
2234
2901
|
BellIcon,
|
|
2235
2902
|
Button,
|
|
2903
|
+
Calendar,
|
|
2236
2904
|
CalendarIcon,
|
|
2237
2905
|
CameraIcon,
|
|
2238
2906
|
Card,
|