@j3m-quantum/ui 1.0.0 → 1.3.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/README.md +185 -30
- package/dist/index.cjs +3702 -306
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +654 -3
- package/dist/index.d.ts +654 -3
- package/dist/index.js +3596 -304
- package/dist/index.js.map +1 -1
- package/dist/styles/index.css +1381 -253
- package/package.json +3 -2
package/dist/index.cjs
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
'use strict';
|
|
2
2
|
|
|
3
|
-
var
|
|
3
|
+
var React14 = require('react');
|
|
4
4
|
var reactSlot = require('@radix-ui/react-slot');
|
|
5
5
|
var classVarianceAuthority = require('class-variance-authority');
|
|
6
6
|
var clsx = require('clsx');
|
|
@@ -18,6 +18,7 @@ var ToggleGroupPrimitive = require('@radix-ui/react-toggle-group');
|
|
|
18
18
|
var reactHookForm = require('react-hook-form');
|
|
19
19
|
var LabelPrimitive = require('@radix-ui/react-label');
|
|
20
20
|
var AvatarPrimitive = require('@radix-ui/react-avatar');
|
|
21
|
+
var DropdownMenuPrimitive = require('@radix-ui/react-dropdown-menu');
|
|
21
22
|
var AccordionPrimitive = require('@radix-ui/react-accordion');
|
|
22
23
|
var TabsPrimitive = require('@radix-ui/react-tabs');
|
|
23
24
|
var reactDayPicker = require('react-day-picker');
|
|
@@ -30,7 +31,6 @@ var TooltipPrimitive = require('@radix-ui/react-tooltip');
|
|
|
30
31
|
var sonner = require('sonner');
|
|
31
32
|
var cmdk = require('cmdk');
|
|
32
33
|
var DialogPrimitive = require('@radix-ui/react-dialog');
|
|
33
|
-
var DropdownMenuPrimitive = require('@radix-ui/react-dropdown-menu');
|
|
34
34
|
var MenubarPrimitive = require('@radix-ui/react-menubar');
|
|
35
35
|
var NavigationMenuPrimitive = require('@radix-ui/react-navigation-menu');
|
|
36
36
|
var ContextMenuPrimitive = require('@radix-ui/react-context-menu');
|
|
@@ -40,6 +40,7 @@ var HoverCardPrimitive = require('@radix-ui/react-hover-card');
|
|
|
40
40
|
var ScrollAreaPrimitive = require('@radix-ui/react-scroll-area');
|
|
41
41
|
var CollapsiblePrimitive = require('@radix-ui/react-collapsible');
|
|
42
42
|
var ResizablePrimitive = require('react-resizable-panels');
|
|
43
|
+
var dateFns = require('date-fns');
|
|
43
44
|
|
|
44
45
|
function _interopDefault (e) { return e && e.__esModule ? e : { default: e }; }
|
|
45
46
|
|
|
@@ -61,7 +62,7 @@ function _interopNamespace(e) {
|
|
|
61
62
|
return Object.freeze(n);
|
|
62
63
|
}
|
|
63
64
|
|
|
64
|
-
var
|
|
65
|
+
var React14__namespace = /*#__PURE__*/_interopNamespace(React14);
|
|
65
66
|
var SeparatorPrimitive__namespace = /*#__PURE__*/_interopNamespace(SeparatorPrimitive);
|
|
66
67
|
var CheckboxPrimitive__namespace = /*#__PURE__*/_interopNamespace(CheckboxPrimitive);
|
|
67
68
|
var RadioGroupPrimitive__namespace = /*#__PURE__*/_interopNamespace(RadioGroupPrimitive);
|
|
@@ -72,6 +73,7 @@ var TogglePrimitive__namespace = /*#__PURE__*/_interopNamespace(TogglePrimitive)
|
|
|
72
73
|
var ToggleGroupPrimitive__namespace = /*#__PURE__*/_interopNamespace(ToggleGroupPrimitive);
|
|
73
74
|
var LabelPrimitive__namespace = /*#__PURE__*/_interopNamespace(LabelPrimitive);
|
|
74
75
|
var AvatarPrimitive__namespace = /*#__PURE__*/_interopNamespace(AvatarPrimitive);
|
|
76
|
+
var DropdownMenuPrimitive__namespace = /*#__PURE__*/_interopNamespace(DropdownMenuPrimitive);
|
|
75
77
|
var AccordionPrimitive__namespace = /*#__PURE__*/_interopNamespace(AccordionPrimitive);
|
|
76
78
|
var TabsPrimitive__namespace = /*#__PURE__*/_interopNamespace(TabsPrimitive);
|
|
77
79
|
var useEmblaCarousel__default = /*#__PURE__*/_interopDefault(useEmblaCarousel);
|
|
@@ -81,7 +83,6 @@ var AlertDialogPrimitive__namespace = /*#__PURE__*/_interopNamespace(AlertDialog
|
|
|
81
83
|
var ProgressPrimitive__namespace = /*#__PURE__*/_interopNamespace(ProgressPrimitive);
|
|
82
84
|
var TooltipPrimitive__namespace = /*#__PURE__*/_interopNamespace(TooltipPrimitive);
|
|
83
85
|
var DialogPrimitive__namespace = /*#__PURE__*/_interopNamespace(DialogPrimitive);
|
|
84
|
-
var DropdownMenuPrimitive__namespace = /*#__PURE__*/_interopNamespace(DropdownMenuPrimitive);
|
|
85
86
|
var MenubarPrimitive__namespace = /*#__PURE__*/_interopNamespace(MenubarPrimitive);
|
|
86
87
|
var NavigationMenuPrimitive__namespace = /*#__PURE__*/_interopNamespace(NavigationMenuPrimitive);
|
|
87
88
|
var ContextMenuPrimitive__namespace = /*#__PURE__*/_interopNamespace(ContextMenuPrimitive);
|
|
@@ -94,8 +95,8 @@ var ResizablePrimitive__namespace = /*#__PURE__*/_interopNamespace(ResizablePrim
|
|
|
94
95
|
// src/hooks/use-mobile.ts
|
|
95
96
|
var MOBILE_BREAKPOINT = 768;
|
|
96
97
|
function useIsMobile() {
|
|
97
|
-
const [isMobile, setIsMobile] =
|
|
98
|
-
|
|
98
|
+
const [isMobile, setIsMobile] = React14__namespace.useState(void 0);
|
|
99
|
+
React14__namespace.useEffect(() => {
|
|
99
100
|
const mql = window.matchMedia(`(max-width: ${MOBILE_BREAKPOINT - 1}px)`);
|
|
100
101
|
const onChange = () => {
|
|
101
102
|
setIsMobile(window.innerWidth < MOBILE_BREAKPOINT);
|
|
@@ -114,10 +115,10 @@ var buttonVariants = classVarianceAuthority.cva(
|
|
|
114
115
|
{
|
|
115
116
|
variants: {
|
|
116
117
|
variant: {
|
|
117
|
-
default: "bg-primary text-primary-foreground
|
|
118
|
-
destructive: "bg-destructive text-destructive-foreground
|
|
119
|
-
outline: "border border-input bg-background
|
|
120
|
-
secondary: "bg-secondary text-secondary-foreground
|
|
118
|
+
default: "bg-primary text-primary-foreground hover:bg-primary/90",
|
|
119
|
+
destructive: "bg-destructive text-destructive-foreground hover:bg-destructive/90",
|
|
120
|
+
outline: "border border-input bg-background hover:bg-accent hover:text-accent-foreground",
|
|
121
|
+
secondary: "bg-secondary text-secondary-foreground border border-input hover:bg-secondary/80",
|
|
121
122
|
ghost: "hover:bg-accent hover:text-accent-foreground",
|
|
122
123
|
link: "text-primary underline-offset-4 hover:underline"
|
|
123
124
|
},
|
|
@@ -136,7 +137,7 @@ var buttonVariants = classVarianceAuthority.cva(
|
|
|
136
137
|
}
|
|
137
138
|
}
|
|
138
139
|
);
|
|
139
|
-
var Button =
|
|
140
|
+
var Button = React14__namespace.forwardRef(
|
|
140
141
|
({ className, variant, size, asChild = false, ...props }, ref) => {
|
|
141
142
|
const Comp = asChild ? reactSlot.Slot : "button";
|
|
142
143
|
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
@@ -500,7 +501,7 @@ function Slider({
|
|
|
500
501
|
max = 100,
|
|
501
502
|
...props
|
|
502
503
|
}) {
|
|
503
|
-
const _values =
|
|
504
|
+
const _values = React14__namespace.useMemo(
|
|
504
505
|
() => Array.isArray(value) ? value : Array.isArray(defaultValue) ? defaultValue : [min, max],
|
|
505
506
|
[value, defaultValue, min, max]
|
|
506
507
|
);
|
|
@@ -536,7 +537,7 @@ function Slider({
|
|
|
536
537
|
)
|
|
537
538
|
}
|
|
538
539
|
),
|
|
539
|
-
Array.from({ length: _values.length }, (
|
|
540
|
+
Array.from({ length: _values.length }, (_, index) => /* @__PURE__ */ jsxRuntime.jsx(
|
|
540
541
|
SliderPrimitive__namespace.Thumb,
|
|
541
542
|
{
|
|
542
543
|
"data-slot": "slider-thumb",
|
|
@@ -786,7 +787,7 @@ function Toggle({
|
|
|
786
787
|
}
|
|
787
788
|
);
|
|
788
789
|
}
|
|
789
|
-
var ToggleGroupContext =
|
|
790
|
+
var ToggleGroupContext = React14__namespace.createContext({
|
|
790
791
|
size: "default",
|
|
791
792
|
variant: "default",
|
|
792
793
|
spacing: 0
|
|
@@ -823,7 +824,7 @@ function ToggleGroupItem({
|
|
|
823
824
|
size,
|
|
824
825
|
...props
|
|
825
826
|
}) {
|
|
826
|
-
const context =
|
|
827
|
+
const context = React14__namespace.useContext(ToggleGroupContext);
|
|
827
828
|
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
828
829
|
ToggleGroupPrimitive__namespace.Item,
|
|
829
830
|
{
|
|
@@ -854,7 +855,7 @@ function ToolBarCanvas({
|
|
|
854
855
|
{
|
|
855
856
|
"data-slot": "toolbar-canvas",
|
|
856
857
|
className: cn(
|
|
857
|
-
"inline-flex items-center gap-1 rounded-full bg-
|
|
858
|
+
"inline-flex items-center gap-1 rounded-full bg-background border border-input p-1.5",
|
|
858
859
|
className
|
|
859
860
|
),
|
|
860
861
|
...props
|
|
@@ -949,7 +950,7 @@ function PlayerCanvasControls({
|
|
|
949
950
|
{
|
|
950
951
|
"data-slot": "player-canvas-controls",
|
|
951
952
|
className: cn(
|
|
952
|
-
"flex items-center gap-2 px-1.5 py-1.5 rounded-full bg-
|
|
953
|
+
"flex items-center gap-2 px-1.5 py-1.5 rounded-full bg-background border border-input",
|
|
953
954
|
className
|
|
954
955
|
),
|
|
955
956
|
...props
|
|
@@ -990,7 +991,7 @@ function PlayerCanvasPlayButton({
|
|
|
990
991
|
className
|
|
991
992
|
),
|
|
992
993
|
style: {
|
|
993
|
-
backgroundColor: "
|
|
994
|
+
backgroundColor: "var(--j3m-orange-8)",
|
|
994
995
|
...style
|
|
995
996
|
},
|
|
996
997
|
...props,
|
|
@@ -1130,7 +1131,7 @@ function PlayerCanvasProgress({
|
|
|
1130
1131
|
className: "absolute inset-y-0 left-0 rounded-full transition-all duration-200",
|
|
1131
1132
|
style: {
|
|
1132
1133
|
width: `${percentage}%`,
|
|
1133
|
-
backgroundColor: "
|
|
1134
|
+
backgroundColor: "var(--j3m-orange-8)"
|
|
1134
1135
|
}
|
|
1135
1136
|
}
|
|
1136
1137
|
)
|
|
@@ -1154,7 +1155,7 @@ function Label2({
|
|
|
1154
1155
|
);
|
|
1155
1156
|
}
|
|
1156
1157
|
var Form = reactHookForm.FormProvider;
|
|
1157
|
-
var FormFieldContext =
|
|
1158
|
+
var FormFieldContext = React14__namespace.createContext(
|
|
1158
1159
|
{}
|
|
1159
1160
|
);
|
|
1160
1161
|
var FormField = ({
|
|
@@ -1163,8 +1164,8 @@ var FormField = ({
|
|
|
1163
1164
|
return /* @__PURE__ */ jsxRuntime.jsx(FormFieldContext.Provider, { value: { name: props.name }, children: /* @__PURE__ */ jsxRuntime.jsx(reactHookForm.Controller, { ...props }) });
|
|
1164
1165
|
};
|
|
1165
1166
|
var useFormField = () => {
|
|
1166
|
-
const fieldContext =
|
|
1167
|
-
const itemContext =
|
|
1167
|
+
const fieldContext = React14__namespace.useContext(FormFieldContext);
|
|
1168
|
+
const itemContext = React14__namespace.useContext(FormItemContext);
|
|
1168
1169
|
const { getFieldState } = reactHookForm.useFormContext();
|
|
1169
1170
|
const formState = reactHookForm.useFormState({ name: fieldContext.name });
|
|
1170
1171
|
const fieldState = getFieldState(fieldContext.name, formState);
|
|
@@ -1181,11 +1182,11 @@ var useFormField = () => {
|
|
|
1181
1182
|
...fieldState
|
|
1182
1183
|
};
|
|
1183
1184
|
};
|
|
1184
|
-
var FormItemContext =
|
|
1185
|
+
var FormItemContext = React14__namespace.createContext(
|
|
1185
1186
|
{}
|
|
1186
1187
|
);
|
|
1187
1188
|
function FormItem({ className, ...props }) {
|
|
1188
|
-
const id =
|
|
1189
|
+
const id = React14__namespace.useId();
|
|
1189
1190
|
return /* @__PURE__ */ jsxRuntime.jsx(FormItemContext.Provider, { value: { id }, children: /* @__PURE__ */ jsxRuntime.jsx(
|
|
1190
1191
|
"div",
|
|
1191
1192
|
{
|
|
@@ -1433,7 +1434,7 @@ function FieldError({
|
|
|
1433
1434
|
errors,
|
|
1434
1435
|
...props
|
|
1435
1436
|
}) {
|
|
1436
|
-
const content =
|
|
1437
|
+
const content = React14.useMemo(() => {
|
|
1437
1438
|
if (children) {
|
|
1438
1439
|
return children;
|
|
1439
1440
|
}
|
|
@@ -1469,7 +1470,7 @@ var cardVariants = classVarianceAuthority.cva(
|
|
|
1469
1470
|
{
|
|
1470
1471
|
variants: {
|
|
1471
1472
|
variant: {
|
|
1472
|
-
default: "bg-card border
|
|
1473
|
+
default: "bg-card border",
|
|
1473
1474
|
glass: [
|
|
1474
1475
|
"glass-context",
|
|
1475
1476
|
// Enables glass semantic token overrides for children
|
|
@@ -1724,6 +1725,298 @@ function AvatarFallback({
|
|
|
1724
1725
|
}
|
|
1725
1726
|
);
|
|
1726
1727
|
}
|
|
1728
|
+
function DropdownMenu({
|
|
1729
|
+
...props
|
|
1730
|
+
}) {
|
|
1731
|
+
return /* @__PURE__ */ jsxRuntime.jsx(DropdownMenuPrimitive__namespace.Root, { "data-slot": "dropdown-menu", ...props });
|
|
1732
|
+
}
|
|
1733
|
+
function DropdownMenuPortal({
|
|
1734
|
+
...props
|
|
1735
|
+
}) {
|
|
1736
|
+
return /* @__PURE__ */ jsxRuntime.jsx(DropdownMenuPrimitive__namespace.Portal, { "data-slot": "dropdown-menu-portal", ...props });
|
|
1737
|
+
}
|
|
1738
|
+
function DropdownMenuTrigger({
|
|
1739
|
+
...props
|
|
1740
|
+
}) {
|
|
1741
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
1742
|
+
DropdownMenuPrimitive__namespace.Trigger,
|
|
1743
|
+
{
|
|
1744
|
+
"data-slot": "dropdown-menu-trigger",
|
|
1745
|
+
...props
|
|
1746
|
+
}
|
|
1747
|
+
);
|
|
1748
|
+
}
|
|
1749
|
+
function DropdownMenuContent({
|
|
1750
|
+
className,
|
|
1751
|
+
sideOffset = 4,
|
|
1752
|
+
...props
|
|
1753
|
+
}) {
|
|
1754
|
+
return /* @__PURE__ */ jsxRuntime.jsx(DropdownMenuPrimitive__namespace.Portal, { children: /* @__PURE__ */ jsxRuntime.jsx(
|
|
1755
|
+
DropdownMenuPrimitive__namespace.Content,
|
|
1756
|
+
{
|
|
1757
|
+
"data-slot": "dropdown-menu-content",
|
|
1758
|
+
sideOffset,
|
|
1759
|
+
className: cn(
|
|
1760
|
+
"bg-popover text-popover-foreground data-[state=open]:animate-in data-[state=closed]:animate-out data-[state=closed]:fade-out-0 data-[state=open]:fade-in-0 data-[state=closed]:zoom-out-95 data-[state=open]:zoom-in-95 data-[side=bottom]:slide-in-from-top-2 data-[side=left]:slide-in-from-right-2 data-[side=right]:slide-in-from-left-2 data-[side=top]:slide-in-from-bottom-2 z-50 max-h-(--radix-dropdown-menu-content-available-height) min-w-[8rem] origin-(--radix-dropdown-menu-content-transform-origin) overflow-x-hidden overflow-y-auto rounded-md border p-1 shadow-md",
|
|
1761
|
+
className
|
|
1762
|
+
),
|
|
1763
|
+
...props
|
|
1764
|
+
}
|
|
1765
|
+
) });
|
|
1766
|
+
}
|
|
1767
|
+
function DropdownMenuGroup({
|
|
1768
|
+
...props
|
|
1769
|
+
}) {
|
|
1770
|
+
return /* @__PURE__ */ jsxRuntime.jsx(DropdownMenuPrimitive__namespace.Group, { "data-slot": "dropdown-menu-group", ...props });
|
|
1771
|
+
}
|
|
1772
|
+
function DropdownMenuItem({
|
|
1773
|
+
className,
|
|
1774
|
+
inset,
|
|
1775
|
+
variant = "default",
|
|
1776
|
+
...props
|
|
1777
|
+
}) {
|
|
1778
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
1779
|
+
DropdownMenuPrimitive__namespace.Item,
|
|
1780
|
+
{
|
|
1781
|
+
"data-slot": "dropdown-menu-item",
|
|
1782
|
+
"data-inset": inset,
|
|
1783
|
+
"data-variant": variant,
|
|
1784
|
+
className: cn(
|
|
1785
|
+
"focus:bg-accent focus:text-accent-foreground data-[variant=destructive]:text-destructive data-[variant=destructive]:focus:bg-destructive/10 dark:data-[variant=destructive]:focus:bg-destructive/20 data-[variant=destructive]:focus:text-destructive data-[variant=destructive]:*:[svg]:!text-destructive [&_svg:not([class*='text-'])]:text-muted-foreground relative flex cursor-default items-center gap-2 rounded-sm px-2 py-1.5 text-sm outline-hidden select-none data-[disabled]:pointer-events-none data-[disabled]:opacity-50 data-[inset]:pl-8 [&_svg]:pointer-events-none [&_svg]:shrink-0 [&_svg:not([class*='size-'])]:size-4",
|
|
1786
|
+
className
|
|
1787
|
+
),
|
|
1788
|
+
...props
|
|
1789
|
+
}
|
|
1790
|
+
);
|
|
1791
|
+
}
|
|
1792
|
+
function DropdownMenuCheckboxItem({
|
|
1793
|
+
className,
|
|
1794
|
+
children,
|
|
1795
|
+
checked,
|
|
1796
|
+
...props
|
|
1797
|
+
}) {
|
|
1798
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(
|
|
1799
|
+
DropdownMenuPrimitive__namespace.CheckboxItem,
|
|
1800
|
+
{
|
|
1801
|
+
"data-slot": "dropdown-menu-checkbox-item",
|
|
1802
|
+
className: cn(
|
|
1803
|
+
"focus:bg-accent focus:text-accent-foreground relative flex cursor-default items-center gap-2 rounded-sm py-1.5 pr-2 pl-8 text-sm outline-hidden select-none data-[disabled]:pointer-events-none data-[disabled]:opacity-50 [&_svg]:pointer-events-none [&_svg]:shrink-0 [&_svg:not([class*='size-'])]:size-4",
|
|
1804
|
+
className
|
|
1805
|
+
),
|
|
1806
|
+
checked,
|
|
1807
|
+
...props,
|
|
1808
|
+
children: [
|
|
1809
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "pointer-events-none absolute left-2 flex size-3.5 items-center justify-center", children: /* @__PURE__ */ jsxRuntime.jsx(DropdownMenuPrimitive__namespace.ItemIndicator, { children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.CheckIcon, { className: "size-4" }) }) }),
|
|
1810
|
+
children
|
|
1811
|
+
]
|
|
1812
|
+
}
|
|
1813
|
+
);
|
|
1814
|
+
}
|
|
1815
|
+
function DropdownMenuRadioGroup({
|
|
1816
|
+
...props
|
|
1817
|
+
}) {
|
|
1818
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
1819
|
+
DropdownMenuPrimitive__namespace.RadioGroup,
|
|
1820
|
+
{
|
|
1821
|
+
"data-slot": "dropdown-menu-radio-group",
|
|
1822
|
+
...props
|
|
1823
|
+
}
|
|
1824
|
+
);
|
|
1825
|
+
}
|
|
1826
|
+
function DropdownMenuRadioItem({
|
|
1827
|
+
className,
|
|
1828
|
+
children,
|
|
1829
|
+
...props
|
|
1830
|
+
}) {
|
|
1831
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(
|
|
1832
|
+
DropdownMenuPrimitive__namespace.RadioItem,
|
|
1833
|
+
{
|
|
1834
|
+
"data-slot": "dropdown-menu-radio-item",
|
|
1835
|
+
className: cn(
|
|
1836
|
+
"focus:bg-accent focus:text-accent-foreground relative flex cursor-default items-center gap-2 rounded-sm py-1.5 pr-2 pl-8 text-sm outline-hidden select-none data-[disabled]:pointer-events-none data-[disabled]:opacity-50 [&_svg]:pointer-events-none [&_svg]:shrink-0 [&_svg:not([class*='size-'])]:size-4",
|
|
1837
|
+
className
|
|
1838
|
+
),
|
|
1839
|
+
...props,
|
|
1840
|
+
children: [
|
|
1841
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "pointer-events-none absolute left-2 flex size-3.5 items-center justify-center", children: /* @__PURE__ */ jsxRuntime.jsx(DropdownMenuPrimitive__namespace.ItemIndicator, { children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.CircleIcon, { className: "size-2 fill-current" }) }) }),
|
|
1842
|
+
children
|
|
1843
|
+
]
|
|
1844
|
+
}
|
|
1845
|
+
);
|
|
1846
|
+
}
|
|
1847
|
+
function DropdownMenuLabel({
|
|
1848
|
+
className,
|
|
1849
|
+
inset,
|
|
1850
|
+
...props
|
|
1851
|
+
}) {
|
|
1852
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
1853
|
+
DropdownMenuPrimitive__namespace.Label,
|
|
1854
|
+
{
|
|
1855
|
+
"data-slot": "dropdown-menu-label",
|
|
1856
|
+
"data-inset": inset,
|
|
1857
|
+
className: cn(
|
|
1858
|
+
"px-2 py-1.5 text-sm font-medium data-[inset]:pl-8",
|
|
1859
|
+
className
|
|
1860
|
+
),
|
|
1861
|
+
...props
|
|
1862
|
+
}
|
|
1863
|
+
);
|
|
1864
|
+
}
|
|
1865
|
+
function DropdownMenuSeparator({
|
|
1866
|
+
className,
|
|
1867
|
+
...props
|
|
1868
|
+
}) {
|
|
1869
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
1870
|
+
DropdownMenuPrimitive__namespace.Separator,
|
|
1871
|
+
{
|
|
1872
|
+
"data-slot": "dropdown-menu-separator",
|
|
1873
|
+
className: cn("bg-border -mx-1 my-1 h-px", className),
|
|
1874
|
+
...props
|
|
1875
|
+
}
|
|
1876
|
+
);
|
|
1877
|
+
}
|
|
1878
|
+
function DropdownMenuShortcut({
|
|
1879
|
+
className,
|
|
1880
|
+
...props
|
|
1881
|
+
}) {
|
|
1882
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
1883
|
+
"span",
|
|
1884
|
+
{
|
|
1885
|
+
"data-slot": "dropdown-menu-shortcut",
|
|
1886
|
+
className: cn(
|
|
1887
|
+
"text-muted-foreground ml-auto text-xs tracking-widest",
|
|
1888
|
+
className
|
|
1889
|
+
),
|
|
1890
|
+
...props
|
|
1891
|
+
}
|
|
1892
|
+
);
|
|
1893
|
+
}
|
|
1894
|
+
function DropdownMenuSub({
|
|
1895
|
+
...props
|
|
1896
|
+
}) {
|
|
1897
|
+
return /* @__PURE__ */ jsxRuntime.jsx(DropdownMenuPrimitive__namespace.Sub, { "data-slot": "dropdown-menu-sub", ...props });
|
|
1898
|
+
}
|
|
1899
|
+
function DropdownMenuSubTrigger({
|
|
1900
|
+
className,
|
|
1901
|
+
inset,
|
|
1902
|
+
children,
|
|
1903
|
+
...props
|
|
1904
|
+
}) {
|
|
1905
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(
|
|
1906
|
+
DropdownMenuPrimitive__namespace.SubTrigger,
|
|
1907
|
+
{
|
|
1908
|
+
"data-slot": "dropdown-menu-sub-trigger",
|
|
1909
|
+
"data-inset": inset,
|
|
1910
|
+
className: cn(
|
|
1911
|
+
"focus:bg-accent focus:text-accent-foreground data-[state=open]:bg-accent data-[state=open]:text-accent-foreground [&_svg:not([class*='text-'])]:text-muted-foreground flex cursor-default items-center gap-2 rounded-sm px-2 py-1.5 text-sm outline-hidden select-none data-[inset]:pl-8 [&_svg]:pointer-events-none [&_svg]:shrink-0 [&_svg:not([class*='size-'])]:size-4",
|
|
1912
|
+
className
|
|
1913
|
+
),
|
|
1914
|
+
...props,
|
|
1915
|
+
children: [
|
|
1916
|
+
children,
|
|
1917
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.ChevronRightIcon, { className: "ml-auto size-4" })
|
|
1918
|
+
]
|
|
1919
|
+
}
|
|
1920
|
+
);
|
|
1921
|
+
}
|
|
1922
|
+
function DropdownMenuSubContent({
|
|
1923
|
+
className,
|
|
1924
|
+
...props
|
|
1925
|
+
}) {
|
|
1926
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
1927
|
+
DropdownMenuPrimitive__namespace.SubContent,
|
|
1928
|
+
{
|
|
1929
|
+
"data-slot": "dropdown-menu-sub-content",
|
|
1930
|
+
className: cn(
|
|
1931
|
+
"bg-popover text-popover-foreground data-[state=open]:animate-in data-[state=closed]:animate-out data-[state=closed]:fade-out-0 data-[state=open]:fade-in-0 data-[state=closed]:zoom-out-95 data-[state=open]:zoom-in-95 data-[side=bottom]:slide-in-from-top-2 data-[side=left]:slide-in-from-right-2 data-[side=right]:slide-in-from-left-2 data-[side=top]:slide-in-from-bottom-2 z-50 min-w-[8rem] origin-(--radix-dropdown-menu-content-transform-origin) overflow-hidden rounded-md border p-1 shadow-lg",
|
|
1932
|
+
className
|
|
1933
|
+
),
|
|
1934
|
+
...props
|
|
1935
|
+
}
|
|
1936
|
+
);
|
|
1937
|
+
}
|
|
1938
|
+
function UserAvatarsDropdown({
|
|
1939
|
+
users,
|
|
1940
|
+
selectedUserId,
|
|
1941
|
+
onSelect,
|
|
1942
|
+
maxVisible = 2,
|
|
1943
|
+
label = "All",
|
|
1944
|
+
className
|
|
1945
|
+
}) {
|
|
1946
|
+
const visibleUsers = users.slice(0, maxVisible);
|
|
1947
|
+
const overflowCount = Math.max(0, users.length - maxVisible);
|
|
1948
|
+
const getInitials = (name) => {
|
|
1949
|
+
return name.split(" ").map((n) => n[0]).join("").toUpperCase().slice(0, 2);
|
|
1950
|
+
};
|
|
1951
|
+
const selectedUser = users.find((u) => u.id === selectedUserId);
|
|
1952
|
+
const displayLabel = selectedUserId ? selectedUser?.name || "User" : label;
|
|
1953
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(DropdownMenu, { children: [
|
|
1954
|
+
/* @__PURE__ */ jsxRuntime.jsx(DropdownMenuTrigger, { asChild: true, children: /* @__PURE__ */ jsxRuntime.jsxs(
|
|
1955
|
+
"button",
|
|
1956
|
+
{
|
|
1957
|
+
type: "button",
|
|
1958
|
+
className: cn(
|
|
1959
|
+
"flex items-center gap-2 rounded border border-border bg-background px-3 py-1.5 text-sm transition-colors",
|
|
1960
|
+
"hover:bg-muted focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring",
|
|
1961
|
+
className
|
|
1962
|
+
),
|
|
1963
|
+
children: [
|
|
1964
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex -space-x-2", children: [
|
|
1965
|
+
visibleUsers.map((user) => /* @__PURE__ */ jsxRuntime.jsxs(
|
|
1966
|
+
Avatar,
|
|
1967
|
+
{
|
|
1968
|
+
className: "size-6 border-2 border-background",
|
|
1969
|
+
children: [
|
|
1970
|
+
/* @__PURE__ */ jsxRuntime.jsx(AvatarImage, { src: user.image, alt: user.name }),
|
|
1971
|
+
/* @__PURE__ */ jsxRuntime.jsx(AvatarFallback, { className: "text-[10px]", children: getInitials(user.name) })
|
|
1972
|
+
]
|
|
1973
|
+
},
|
|
1974
|
+
user.id
|
|
1975
|
+
)),
|
|
1976
|
+
overflowCount > 0 && /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex size-6 items-center justify-center rounded-full border-2 border-background bg-muted text-[10px] font-medium", children: [
|
|
1977
|
+
"+",
|
|
1978
|
+
overflowCount
|
|
1979
|
+
] })
|
|
1980
|
+
] }),
|
|
1981
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "font-medium", children: displayLabel }),
|
|
1982
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.ChevronDownIcon, { className: "size-4 text-muted-foreground" })
|
|
1983
|
+
]
|
|
1984
|
+
}
|
|
1985
|
+
) }),
|
|
1986
|
+
/* @__PURE__ */ jsxRuntime.jsxs(DropdownMenuContent, { align: "end", className: "w-48", children: [
|
|
1987
|
+
/* @__PURE__ */ jsxRuntime.jsxs(
|
|
1988
|
+
DropdownMenuItem,
|
|
1989
|
+
{
|
|
1990
|
+
onClick: () => onSelect(null),
|
|
1991
|
+
className: "flex items-center justify-between",
|
|
1992
|
+
children: [
|
|
1993
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { children: "All users" }),
|
|
1994
|
+
selectedUserId === null && /* @__PURE__ */ jsxRuntime.jsx(lucideReact.CheckIcon, { className: "size-4" })
|
|
1995
|
+
]
|
|
1996
|
+
}
|
|
1997
|
+
),
|
|
1998
|
+
/* @__PURE__ */ jsxRuntime.jsx(DropdownMenuSeparator, {}),
|
|
1999
|
+
users.map((user) => /* @__PURE__ */ jsxRuntime.jsxs(
|
|
2000
|
+
DropdownMenuItem,
|
|
2001
|
+
{
|
|
2002
|
+
onClick: () => onSelect(user.id),
|
|
2003
|
+
className: "flex items-center justify-between",
|
|
2004
|
+
children: [
|
|
2005
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center gap-2", children: [
|
|
2006
|
+
/* @__PURE__ */ jsxRuntime.jsxs(Avatar, { className: "size-5", children: [
|
|
2007
|
+
/* @__PURE__ */ jsxRuntime.jsx(AvatarImage, { src: user.image, alt: user.name }),
|
|
2008
|
+
/* @__PURE__ */ jsxRuntime.jsx(AvatarFallback, { className: "text-[8px]", children: getInitials(user.name) })
|
|
2009
|
+
] }),
|
|
2010
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { children: user.name })
|
|
2011
|
+
] }),
|
|
2012
|
+
selectedUserId === user.id && /* @__PURE__ */ jsxRuntime.jsx(lucideReact.CheckIcon, { className: "size-4" })
|
|
2013
|
+
]
|
|
2014
|
+
},
|
|
2015
|
+
user.id
|
|
2016
|
+
))
|
|
2017
|
+
] })
|
|
2018
|
+
] });
|
|
2019
|
+
}
|
|
1727
2020
|
function Skeleton({ className, ...props }) {
|
|
1728
2021
|
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
1729
2022
|
"div",
|
|
@@ -1810,7 +2103,7 @@ function TabsList({
|
|
|
1810
2103
|
{
|
|
1811
2104
|
"data-slot": "tabs-list",
|
|
1812
2105
|
className: cn(
|
|
1813
|
-
"bg-muted text-muted-foreground inline-flex h-9 w-fit items-center justify-center rounded-lg p-[3px]",
|
|
2106
|
+
"bg-muted text-muted-foreground inline-flex h-9 w-fit items-center justify-center rounded-lg p-[3px] dark:bg-[#1a1a1a]",
|
|
1814
2107
|
className
|
|
1815
2108
|
),
|
|
1816
2109
|
...props
|
|
@@ -1826,7 +2119,7 @@ function TabsTrigger({
|
|
|
1826
2119
|
{
|
|
1827
2120
|
"data-slot": "tabs-trigger",
|
|
1828
2121
|
className: cn(
|
|
1829
|
-
"data-[state=active]:bg-background dark:data-[state=active]:text-foreground focus-visible:border-ring focus-visible:ring-ring/50 focus-visible:outline-ring dark:data-[state=active]:border-input dark:data-[state=active]:bg-input/30 text-foreground dark:text-muted-foreground inline-flex h-[calc(100%-1px)] flex-1 items-center justify-center gap-1.5 rounded-md border border-transparent px-2 py-1 text-sm font-medium whitespace-nowrap transition-[color,box-shadow] focus-visible:ring-[3px] focus-visible:outline-1 disabled:pointer-events-none disabled:opacity-50 data-[state=active]:
|
|
2122
|
+
"data-[state=active]:bg-background dark:data-[state=active]:text-foreground focus-visible:border-ring focus-visible:ring-ring/50 focus-visible:outline-ring dark:data-[state=active]:border-input dark:data-[state=active]:bg-input/30 text-foreground dark:text-muted-foreground inline-flex h-[calc(100%-1px)] flex-1 items-center justify-center gap-1.5 rounded-md border border-transparent px-2 py-1 text-sm font-medium whitespace-nowrap transition-[color,box-shadow] focus-visible:ring-[3px] focus-visible:outline-1 disabled:pointer-events-none disabled:opacity-50 data-[state=active]:border-input data-[state=inactive]:hover:bg-accent data-[state=inactive]:hover:text-accent-foreground [&_svg]:pointer-events-none [&_svg]:shrink-0 [&_svg:not([class*='size-'])]:size-4",
|
|
1830
2123
|
className
|
|
1831
2124
|
),
|
|
1832
2125
|
...props
|
|
@@ -1995,8 +2288,8 @@ function CalendarDayButton({
|
|
|
1995
2288
|
modifiers,
|
|
1996
2289
|
...props
|
|
1997
2290
|
}) {
|
|
1998
|
-
const ref =
|
|
1999
|
-
|
|
2291
|
+
const ref = React14__namespace.useRef(null);
|
|
2292
|
+
React14__namespace.useEffect(() => {
|
|
2000
2293
|
if (modifiers.focused) ref.current?.focus();
|
|
2001
2294
|
}, [modifiers.focused]);
|
|
2002
2295
|
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
@@ -2017,9 +2310,9 @@ function CalendarDayButton({
|
|
|
2017
2310
|
}
|
|
2018
2311
|
);
|
|
2019
2312
|
}
|
|
2020
|
-
var CarouselContext =
|
|
2313
|
+
var CarouselContext = React14__namespace.createContext(null);
|
|
2021
2314
|
function useCarousel() {
|
|
2022
|
-
const context =
|
|
2315
|
+
const context = React14__namespace.useContext(CarouselContext);
|
|
2023
2316
|
if (!context) {
|
|
2024
2317
|
throw new Error("useCarousel must be used within a <Carousel />");
|
|
2025
2318
|
}
|
|
@@ -2041,20 +2334,20 @@ function Carousel({
|
|
|
2041
2334
|
},
|
|
2042
2335
|
plugins
|
|
2043
2336
|
);
|
|
2044
|
-
const [canScrollPrev, setCanScrollPrev] =
|
|
2045
|
-
const [canScrollNext, setCanScrollNext] =
|
|
2046
|
-
const onSelect =
|
|
2337
|
+
const [canScrollPrev, setCanScrollPrev] = React14__namespace.useState(false);
|
|
2338
|
+
const [canScrollNext, setCanScrollNext] = React14__namespace.useState(false);
|
|
2339
|
+
const onSelect = React14__namespace.useCallback((api2) => {
|
|
2047
2340
|
if (!api2) return;
|
|
2048
2341
|
setCanScrollPrev(api2.canScrollPrev());
|
|
2049
2342
|
setCanScrollNext(api2.canScrollNext());
|
|
2050
2343
|
}, []);
|
|
2051
|
-
const scrollPrev =
|
|
2344
|
+
const scrollPrev = React14__namespace.useCallback(() => {
|
|
2052
2345
|
api?.scrollPrev();
|
|
2053
2346
|
}, [api]);
|
|
2054
|
-
const scrollNext =
|
|
2347
|
+
const scrollNext = React14__namespace.useCallback(() => {
|
|
2055
2348
|
api?.scrollNext();
|
|
2056
2349
|
}, [api]);
|
|
2057
|
-
const handleKeyDown =
|
|
2350
|
+
const handleKeyDown = React14__namespace.useCallback(
|
|
2058
2351
|
(event) => {
|
|
2059
2352
|
if (event.key === "ArrowLeft") {
|
|
2060
2353
|
event.preventDefault();
|
|
@@ -2066,11 +2359,11 @@ function Carousel({
|
|
|
2066
2359
|
},
|
|
2067
2360
|
[scrollPrev, scrollNext]
|
|
2068
2361
|
);
|
|
2069
|
-
|
|
2362
|
+
React14__namespace.useEffect(() => {
|
|
2070
2363
|
if (!api || !setApi) return;
|
|
2071
2364
|
setApi(api);
|
|
2072
2365
|
}, [api, setApi]);
|
|
2073
|
-
|
|
2366
|
+
React14__namespace.useEffect(() => {
|
|
2074
2367
|
if (!api) return;
|
|
2075
2368
|
onSelect(api);
|
|
2076
2369
|
api.on("reInit", onSelect);
|
|
@@ -2203,9 +2496,9 @@ function CarouselNext({
|
|
|
2203
2496
|
);
|
|
2204
2497
|
}
|
|
2205
2498
|
var THEMES = { light: "", dark: ".dark" };
|
|
2206
|
-
var ChartContext =
|
|
2499
|
+
var ChartContext = React14__namespace.createContext(null);
|
|
2207
2500
|
function useChart() {
|
|
2208
|
-
const context =
|
|
2501
|
+
const context = React14__namespace.useContext(ChartContext);
|
|
2209
2502
|
if (!context) {
|
|
2210
2503
|
throw new Error("useChart must be used within a <ChartContainer />");
|
|
2211
2504
|
}
|
|
@@ -2218,7 +2511,7 @@ function ChartContainer({
|
|
|
2218
2511
|
config,
|
|
2219
2512
|
...props
|
|
2220
2513
|
}) {
|
|
2221
|
-
const uniqueId =
|
|
2514
|
+
const uniqueId = React14__namespace.useId();
|
|
2222
2515
|
const chartId = `chart-${id || uniqueId.replace(/:/g, "")}`;
|
|
2223
2516
|
return /* @__PURE__ */ jsxRuntime.jsx(ChartContext.Provider, { value: { config }, children: /* @__PURE__ */ jsxRuntime.jsxs(
|
|
2224
2517
|
"div",
|
|
@@ -2279,7 +2572,7 @@ function ChartTooltipContent({
|
|
|
2279
2572
|
labelKey
|
|
2280
2573
|
}) {
|
|
2281
2574
|
const { config } = useChart();
|
|
2282
|
-
const tooltipLabel =
|
|
2575
|
+
const tooltipLabel = React14__namespace.useMemo(() => {
|
|
2283
2576
|
if (hideLabel || !payload?.length) {
|
|
2284
2577
|
return null;
|
|
2285
2578
|
}
|
|
@@ -2573,7 +2866,7 @@ var itemVariants = classVarianceAuthority.cva(
|
|
|
2573
2866
|
}
|
|
2574
2867
|
}
|
|
2575
2868
|
);
|
|
2576
|
-
function
|
|
2869
|
+
function Item6({
|
|
2577
2870
|
className,
|
|
2578
2871
|
variant = "default",
|
|
2579
2872
|
size = "default",
|
|
@@ -2981,40 +3274,27 @@ function TooltipContent({
|
|
|
2981
3274
|
}
|
|
2982
3275
|
) });
|
|
2983
3276
|
}
|
|
2984
|
-
|
|
2985
|
-
|
|
2986
|
-
|
|
2987
|
-
|
|
2988
|
-
|
|
2989
|
-
|
|
2990
|
-
|
|
2991
|
-
|
|
2992
|
-
|
|
2993
|
-
|
|
2994
|
-
|
|
2995
|
-
|
|
2996
|
-
|
|
2997
|
-
|
|
2998
|
-
|
|
2999
|
-
|
|
3000
|
-
|
|
3001
|
-
|
|
3002
|
-
|
|
3003
|
-
|
|
3004
|
-
|
|
3005
|
-
var x = React7__namespace.createContext(void 0);
|
|
3006
|
-
var U = { setTheme: (e) => {
|
|
3007
|
-
}, themes: [] };
|
|
3008
|
-
var z = () => {
|
|
3009
|
-
var e;
|
|
3010
|
-
return (e = React7__namespace.useContext(x)) != null ? e : U;
|
|
3011
|
-
};
|
|
3012
|
-
React7__namespace.memo(({ forcedTheme: e, storageKey: i, attribute: s, enableSystem: u, enableColorScheme: m, defaultTheme: a, value: l, themes: h, nonce: d, scriptProps: w }) => {
|
|
3013
|
-
let p = JSON.stringify([s, i, a, e, h, l, u, m]).slice(1, -1);
|
|
3014
|
-
return React7__namespace.createElement("script", { ...w, suppressHydrationWarning: true, nonce: typeof window == "undefined" ? d : "", dangerouslySetInnerHTML: { __html: `(${M.toString()})(${p})` } });
|
|
3015
|
-
});
|
|
3016
|
-
var Toaster = ({ ...props }) => {
|
|
3017
|
-
const { theme = "system" } = z();
|
|
3277
|
+
function useDetectTheme() {
|
|
3278
|
+
const [theme, setTheme] = React14__namespace.useState("light");
|
|
3279
|
+
React14__namespace.useEffect(() => {
|
|
3280
|
+
const isDark = document.documentElement.classList.contains("dark");
|
|
3281
|
+
setTheme(isDark ? "dark" : "light");
|
|
3282
|
+
const observer = new MutationObserver((mutations) => {
|
|
3283
|
+
mutations.forEach((mutation) => {
|
|
3284
|
+
if (mutation.attributeName === "class") {
|
|
3285
|
+
const isDark2 = document.documentElement.classList.contains("dark");
|
|
3286
|
+
setTheme(isDark2 ? "dark" : "light");
|
|
3287
|
+
}
|
|
3288
|
+
});
|
|
3289
|
+
});
|
|
3290
|
+
observer.observe(document.documentElement, { attributes: true });
|
|
3291
|
+
return () => observer.disconnect();
|
|
3292
|
+
}, []);
|
|
3293
|
+
return theme;
|
|
3294
|
+
}
|
|
3295
|
+
var Toaster = ({ theme: themeProp, ...props }) => {
|
|
3296
|
+
const detectedTheme = useDetectTheme();
|
|
3297
|
+
const theme = themeProp ?? detectedTheme;
|
|
3018
3298
|
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
3019
3299
|
sonner.Toaster,
|
|
3020
3300
|
{
|
|
@@ -3517,215 +3797,52 @@ function CommandShortcut({
|
|
|
3517
3797
|
}
|
|
3518
3798
|
);
|
|
3519
3799
|
}
|
|
3520
|
-
|
|
3521
|
-
|
|
3522
|
-
|
|
3523
|
-
|
|
3524
|
-
|
|
3525
|
-
|
|
3526
|
-
|
|
3527
|
-
|
|
3528
|
-
|
|
3529
|
-
|
|
3530
|
-
|
|
3531
|
-
|
|
3532
|
-
|
|
3533
|
-
|
|
3534
|
-
|
|
3535
|
-
|
|
3536
|
-
|
|
3537
|
-
|
|
3538
|
-
|
|
3539
|
-
|
|
3540
|
-
|
|
3541
|
-
|
|
3542
|
-
|
|
3543
|
-
|
|
3544
|
-
|
|
3545
|
-
|
|
3546
|
-
|
|
3547
|
-
|
|
3548
|
-
|
|
3549
|
-
|
|
3550
|
-
|
|
3551
|
-
|
|
3552
|
-
|
|
3553
|
-
|
|
3554
|
-
|
|
3555
|
-
|
|
3556
|
-
|
|
3557
|
-
|
|
3558
|
-
|
|
3559
|
-
|
|
3560
|
-
|
|
3561
|
-
}
|
|
3562
|
-
|
|
3563
|
-
|
|
3564
|
-
|
|
3565
|
-
|
|
3566
|
-
inset,
|
|
3567
|
-
variant = "default",
|
|
3568
|
-
...props
|
|
3569
|
-
}) {
|
|
3570
|
-
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
3571
|
-
DropdownMenuPrimitive__namespace.Item,
|
|
3572
|
-
{
|
|
3573
|
-
"data-slot": "dropdown-menu-item",
|
|
3574
|
-
"data-inset": inset,
|
|
3575
|
-
"data-variant": variant,
|
|
3576
|
-
className: cn(
|
|
3577
|
-
"focus:bg-accent focus:text-accent-foreground data-[variant=destructive]:text-destructive data-[variant=destructive]:focus:bg-destructive/10 dark:data-[variant=destructive]:focus:bg-destructive/20 data-[variant=destructive]:focus:text-destructive data-[variant=destructive]:*:[svg]:!text-destructive [&_svg:not([class*='text-'])]:text-muted-foreground relative flex cursor-default items-center gap-2 rounded-sm px-2 py-1.5 text-sm outline-hidden select-none data-[disabled]:pointer-events-none data-[disabled]:opacity-50 data-[inset]:pl-8 [&_svg]:pointer-events-none [&_svg]:shrink-0 [&_svg:not([class*='size-'])]:size-4",
|
|
3578
|
-
className
|
|
3579
|
-
),
|
|
3580
|
-
...props
|
|
3581
|
-
}
|
|
3582
|
-
);
|
|
3583
|
-
}
|
|
3584
|
-
function DropdownMenuCheckboxItem({
|
|
3585
|
-
className,
|
|
3586
|
-
children,
|
|
3587
|
-
checked,
|
|
3588
|
-
...props
|
|
3589
|
-
}) {
|
|
3590
|
-
return /* @__PURE__ */ jsxRuntime.jsxs(
|
|
3591
|
-
DropdownMenuPrimitive__namespace.CheckboxItem,
|
|
3592
|
-
{
|
|
3593
|
-
"data-slot": "dropdown-menu-checkbox-item",
|
|
3594
|
-
className: cn(
|
|
3595
|
-
"focus:bg-accent focus:text-accent-foreground relative flex cursor-default items-center gap-2 rounded-sm py-1.5 pr-2 pl-8 text-sm outline-hidden select-none data-[disabled]:pointer-events-none data-[disabled]:opacity-50 [&_svg]:pointer-events-none [&_svg]:shrink-0 [&_svg:not([class*='size-'])]:size-4",
|
|
3596
|
-
className
|
|
3597
|
-
),
|
|
3598
|
-
checked,
|
|
3599
|
-
...props,
|
|
3600
|
-
children: [
|
|
3601
|
-
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "pointer-events-none absolute left-2 flex size-3.5 items-center justify-center", children: /* @__PURE__ */ jsxRuntime.jsx(DropdownMenuPrimitive__namespace.ItemIndicator, { children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.CheckIcon, { className: "size-4" }) }) }),
|
|
3602
|
-
children
|
|
3603
|
-
]
|
|
3604
|
-
}
|
|
3605
|
-
);
|
|
3606
|
-
}
|
|
3607
|
-
function DropdownMenuRadioGroup({
|
|
3608
|
-
...props
|
|
3609
|
-
}) {
|
|
3610
|
-
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
3611
|
-
DropdownMenuPrimitive__namespace.RadioGroup,
|
|
3612
|
-
{
|
|
3613
|
-
"data-slot": "dropdown-menu-radio-group",
|
|
3614
|
-
...props
|
|
3615
|
-
}
|
|
3616
|
-
);
|
|
3617
|
-
}
|
|
3618
|
-
function DropdownMenuRadioItem({
|
|
3619
|
-
className,
|
|
3620
|
-
children,
|
|
3621
|
-
...props
|
|
3622
|
-
}) {
|
|
3623
|
-
return /* @__PURE__ */ jsxRuntime.jsxs(
|
|
3624
|
-
DropdownMenuPrimitive__namespace.RadioItem,
|
|
3625
|
-
{
|
|
3626
|
-
"data-slot": "dropdown-menu-radio-item",
|
|
3627
|
-
className: cn(
|
|
3628
|
-
"focus:bg-accent focus:text-accent-foreground relative flex cursor-default items-center gap-2 rounded-sm py-1.5 pr-2 pl-8 text-sm outline-hidden select-none data-[disabled]:pointer-events-none data-[disabled]:opacity-50 [&_svg]:pointer-events-none [&_svg]:shrink-0 [&_svg:not([class*='size-'])]:size-4",
|
|
3629
|
-
className
|
|
3630
|
-
),
|
|
3631
|
-
...props,
|
|
3632
|
-
children: [
|
|
3633
|
-
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "pointer-events-none absolute left-2 flex size-3.5 items-center justify-center", children: /* @__PURE__ */ jsxRuntime.jsx(DropdownMenuPrimitive__namespace.ItemIndicator, { children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.CircleIcon, { className: "size-2 fill-current" }) }) }),
|
|
3634
|
-
children
|
|
3635
|
-
]
|
|
3636
|
-
}
|
|
3637
|
-
);
|
|
3638
|
-
}
|
|
3639
|
-
function DropdownMenuLabel({
|
|
3640
|
-
className,
|
|
3641
|
-
inset,
|
|
3642
|
-
...props
|
|
3643
|
-
}) {
|
|
3644
|
-
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
3645
|
-
DropdownMenuPrimitive__namespace.Label,
|
|
3646
|
-
{
|
|
3647
|
-
"data-slot": "dropdown-menu-label",
|
|
3648
|
-
"data-inset": inset,
|
|
3649
|
-
className: cn(
|
|
3650
|
-
"px-2 py-1.5 text-sm font-medium data-[inset]:pl-8",
|
|
3651
|
-
className
|
|
3652
|
-
),
|
|
3653
|
-
...props
|
|
3654
|
-
}
|
|
3655
|
-
);
|
|
3656
|
-
}
|
|
3657
|
-
function DropdownMenuSeparator({
|
|
3658
|
-
className,
|
|
3659
|
-
...props
|
|
3660
|
-
}) {
|
|
3661
|
-
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
3662
|
-
DropdownMenuPrimitive__namespace.Separator,
|
|
3663
|
-
{
|
|
3664
|
-
"data-slot": "dropdown-menu-separator",
|
|
3665
|
-
className: cn("bg-border -mx-1 my-1 h-px", className),
|
|
3666
|
-
...props
|
|
3667
|
-
}
|
|
3668
|
-
);
|
|
3669
|
-
}
|
|
3670
|
-
function DropdownMenuShortcut({
|
|
3671
|
-
className,
|
|
3672
|
-
...props
|
|
3673
|
-
}) {
|
|
3674
|
-
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
3675
|
-
"span",
|
|
3676
|
-
{
|
|
3677
|
-
"data-slot": "dropdown-menu-shortcut",
|
|
3678
|
-
className: cn(
|
|
3679
|
-
"text-muted-foreground ml-auto text-xs tracking-widest",
|
|
3680
|
-
className
|
|
3681
|
-
),
|
|
3682
|
-
...props
|
|
3683
|
-
}
|
|
3684
|
-
);
|
|
3685
|
-
}
|
|
3686
|
-
function DropdownMenuSub({
|
|
3687
|
-
...props
|
|
3688
|
-
}) {
|
|
3689
|
-
return /* @__PURE__ */ jsxRuntime.jsx(DropdownMenuPrimitive__namespace.Sub, { "data-slot": "dropdown-menu-sub", ...props });
|
|
3690
|
-
}
|
|
3691
|
-
function DropdownMenuSubTrigger({
|
|
3692
|
-
className,
|
|
3693
|
-
inset,
|
|
3694
|
-
children,
|
|
3695
|
-
...props
|
|
3696
|
-
}) {
|
|
3697
|
-
return /* @__PURE__ */ jsxRuntime.jsxs(
|
|
3698
|
-
DropdownMenuPrimitive__namespace.SubTrigger,
|
|
3699
|
-
{
|
|
3700
|
-
"data-slot": "dropdown-menu-sub-trigger",
|
|
3701
|
-
"data-inset": inset,
|
|
3702
|
-
className: cn(
|
|
3703
|
-
"focus:bg-accent focus:text-accent-foreground data-[state=open]:bg-accent data-[state=open]:text-accent-foreground [&_svg:not([class*='text-'])]:text-muted-foreground flex cursor-default items-center gap-2 rounded-sm px-2 py-1.5 text-sm outline-hidden select-none data-[inset]:pl-8 [&_svg]:pointer-events-none [&_svg]:shrink-0 [&_svg:not([class*='size-'])]:size-4",
|
|
3704
|
-
className
|
|
3705
|
-
),
|
|
3706
|
-
...props,
|
|
3707
|
-
children: [
|
|
3708
|
-
children,
|
|
3709
|
-
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.ChevronRightIcon, { className: "ml-auto size-4" })
|
|
3710
|
-
]
|
|
3711
|
-
}
|
|
3712
|
-
);
|
|
3713
|
-
}
|
|
3714
|
-
function DropdownMenuSubContent({
|
|
3715
|
-
className,
|
|
3716
|
-
...props
|
|
3717
|
-
}) {
|
|
3718
|
-
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
3719
|
-
DropdownMenuPrimitive__namespace.SubContent,
|
|
3720
|
-
{
|
|
3721
|
-
"data-slot": "dropdown-menu-sub-content",
|
|
3722
|
-
className: cn(
|
|
3723
|
-
"bg-popover text-popover-foreground data-[state=open]:animate-in data-[state=closed]:animate-out data-[state=closed]:fade-out-0 data-[state=open]:fade-in-0 data-[state=closed]:zoom-out-95 data-[state=open]:zoom-in-95 data-[side=bottom]:slide-in-from-top-2 data-[side=left]:slide-in-from-right-2 data-[side=right]:slide-in-from-left-2 data-[side=top]:slide-in-from-bottom-2 z-50 min-w-[8rem] origin-(--radix-dropdown-menu-content-transform-origin) overflow-hidden rounded-md border p-1 shadow-lg",
|
|
3724
|
-
className
|
|
3725
|
-
),
|
|
3726
|
-
...props
|
|
3727
|
-
}
|
|
3728
|
-
);
|
|
3800
|
+
var SearchTrigger = React14__namespace.forwardRef(
|
|
3801
|
+
({
|
|
3802
|
+
className,
|
|
3803
|
+
placeholder = "Search...",
|
|
3804
|
+
showShortcut = true,
|
|
3805
|
+
shortcutKey = "K",
|
|
3806
|
+
shortcutModifier = "\u2318",
|
|
3807
|
+
...props
|
|
3808
|
+
}, ref) => {
|
|
3809
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(
|
|
3810
|
+
Button,
|
|
3811
|
+
{
|
|
3812
|
+
ref,
|
|
3813
|
+
variant: "outline",
|
|
3814
|
+
"data-slot": "search-trigger",
|
|
3815
|
+
className: cn(
|
|
3816
|
+
"relative h-9 w-full justify-start rounded-full bg-background text-sm text-muted-foreground",
|
|
3817
|
+
"sm:w-64 sm:max-w-[280px]",
|
|
3818
|
+
className
|
|
3819
|
+
),
|
|
3820
|
+
...props,
|
|
3821
|
+
children: [
|
|
3822
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.SearchIcon, { className: "mr-2 h-4 w-4 shrink-0" }),
|
|
3823
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "hidden truncate sm:inline-flex", children: placeholder }),
|
|
3824
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "truncate sm:hidden", children: "Search" }),
|
|
3825
|
+
showShortcut && /* @__PURE__ */ jsxRuntime.jsxs(Kbd, { className: "pointer-events-none absolute right-2 hidden h-5 select-none items-center gap-0.5 rounded border bg-muted px-1.5 font-mono text-[10px] font-medium sm:flex", children: [
|
|
3826
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "text-xs", children: shortcutModifier }),
|
|
3827
|
+
shortcutKey
|
|
3828
|
+
] })
|
|
3829
|
+
]
|
|
3830
|
+
}
|
|
3831
|
+
);
|
|
3832
|
+
}
|
|
3833
|
+
);
|
|
3834
|
+
SearchTrigger.displayName = "SearchTrigger";
|
|
3835
|
+
function useSearchShortcut(onOpen, key = "k") {
|
|
3836
|
+
React14__namespace.useEffect(() => {
|
|
3837
|
+
const down = (e) => {
|
|
3838
|
+
if (e.key.toLowerCase() === key.toLowerCase() && (e.metaKey || e.ctrlKey)) {
|
|
3839
|
+
e.preventDefault();
|
|
3840
|
+
onOpen();
|
|
3841
|
+
}
|
|
3842
|
+
};
|
|
3843
|
+
document.addEventListener("keydown", down);
|
|
3844
|
+
return () => document.removeEventListener("keydown", down);
|
|
3845
|
+
}, [onOpen, key]);
|
|
3729
3846
|
}
|
|
3730
3847
|
function Menubar({
|
|
3731
3848
|
className,
|
|
@@ -4744,9 +4861,9 @@ var SIDEBAR_WIDTH = "16rem";
|
|
|
4744
4861
|
var SIDEBAR_WIDTH_MOBILE = "18rem";
|
|
4745
4862
|
var SIDEBAR_WIDTH_ICON = "3rem";
|
|
4746
4863
|
var SIDEBAR_KEYBOARD_SHORTCUT = "b";
|
|
4747
|
-
var SidebarContext =
|
|
4864
|
+
var SidebarContext = React14__namespace.createContext(null);
|
|
4748
4865
|
function useSidebar() {
|
|
4749
|
-
const context =
|
|
4866
|
+
const context = React14__namespace.useContext(SidebarContext);
|
|
4750
4867
|
if (!context) {
|
|
4751
4868
|
throw new Error("useSidebar must be used within a SidebarProvider.");
|
|
4752
4869
|
}
|
|
@@ -4762,10 +4879,10 @@ function SidebarProvider({
|
|
|
4762
4879
|
...props
|
|
4763
4880
|
}) {
|
|
4764
4881
|
const isMobile = useIsMobile();
|
|
4765
|
-
const [openMobile, setOpenMobile] =
|
|
4766
|
-
const [_open, _setOpen] =
|
|
4882
|
+
const [openMobile, setOpenMobile] = React14__namespace.useState(false);
|
|
4883
|
+
const [_open, _setOpen] = React14__namespace.useState(defaultOpen);
|
|
4767
4884
|
const open = openProp ?? _open;
|
|
4768
|
-
const setOpen =
|
|
4885
|
+
const setOpen = React14__namespace.useCallback(
|
|
4769
4886
|
(value) => {
|
|
4770
4887
|
const openState = typeof value === "function" ? value(open) : value;
|
|
4771
4888
|
if (setOpenProp) {
|
|
@@ -4777,10 +4894,10 @@ function SidebarProvider({
|
|
|
4777
4894
|
},
|
|
4778
4895
|
[setOpenProp, open]
|
|
4779
4896
|
);
|
|
4780
|
-
const toggleSidebar =
|
|
4897
|
+
const toggleSidebar = React14__namespace.useCallback(() => {
|
|
4781
4898
|
return isMobile ? setOpenMobile((open2) => !open2) : setOpen((open2) => !open2);
|
|
4782
4899
|
}, [isMobile, setOpen, setOpenMobile]);
|
|
4783
|
-
|
|
4900
|
+
React14__namespace.useEffect(() => {
|
|
4784
4901
|
const handleKeyDown = (event) => {
|
|
4785
4902
|
if (event.key === SIDEBAR_KEYBOARD_SHORTCUT && (event.metaKey || event.ctrlKey)) {
|
|
4786
4903
|
event.preventDefault();
|
|
@@ -4791,7 +4908,7 @@ function SidebarProvider({
|
|
|
4791
4908
|
return () => window.removeEventListener("keydown", handleKeyDown);
|
|
4792
4909
|
}, [toggleSidebar]);
|
|
4793
4910
|
const state = open ? "expanded" : "collapsed";
|
|
4794
|
-
const contextValue =
|
|
4911
|
+
const contextValue = React14__namespace.useMemo(
|
|
4795
4912
|
() => ({
|
|
4796
4913
|
state,
|
|
4797
4914
|
open,
|
|
@@ -5249,7 +5366,7 @@ function SidebarMenuSkeleton({
|
|
|
5249
5366
|
showIcon = false,
|
|
5250
5367
|
...props
|
|
5251
5368
|
}) {
|
|
5252
|
-
const width =
|
|
5369
|
+
const width = React14__namespace.useMemo(() => {
|
|
5253
5370
|
return `${Math.floor(Math.random() * 40) + 50}%`;
|
|
5254
5371
|
}, []);
|
|
5255
5372
|
return /* @__PURE__ */ jsxRuntime.jsxs(
|
|
@@ -5347,8 +5464,7 @@ var sectionVariants = classVarianceAuthority.cva(
|
|
|
5347
5464
|
default: [
|
|
5348
5465
|
"bg-[var(--color-bg-surface)]",
|
|
5349
5466
|
"border border-[var(--color-border-subtle)]",
|
|
5350
|
-
"text-[var(--color-text-main)]"
|
|
5351
|
-
"shadow-sm"
|
|
5467
|
+
"text-[var(--color-text-main)]"
|
|
5352
5468
|
].join(" "),
|
|
5353
5469
|
// Glass Light - frosted glass for dark or image backgrounds
|
|
5354
5470
|
"glass-light": [
|
|
@@ -5393,7 +5509,7 @@ var sectionVariants = classVarianceAuthority.cva(
|
|
|
5393
5509
|
}
|
|
5394
5510
|
);
|
|
5395
5511
|
var isGlassVariant = (variant) => variant?.startsWith("glass-") ?? false;
|
|
5396
|
-
var Section =
|
|
5512
|
+
var Section = React14__namespace.forwardRef(
|
|
5397
5513
|
({ className, variant, ...props }, ref) => /* @__PURE__ */ jsxRuntime.jsx(
|
|
5398
5514
|
"section",
|
|
5399
5515
|
{
|
|
@@ -5405,7 +5521,7 @@ var Section = React7__namespace.forwardRef(
|
|
|
5405
5521
|
)
|
|
5406
5522
|
);
|
|
5407
5523
|
Section.displayName = "Section";
|
|
5408
|
-
var SectionHeader =
|
|
5524
|
+
var SectionHeader = React14__namespace.forwardRef(
|
|
5409
5525
|
({ className, ...props }, ref) => /* @__PURE__ */ jsxRuntime.jsx(
|
|
5410
5526
|
"div",
|
|
5411
5527
|
{
|
|
@@ -5420,7 +5536,7 @@ var SectionHeader = React7__namespace.forwardRef(
|
|
|
5420
5536
|
)
|
|
5421
5537
|
);
|
|
5422
5538
|
SectionHeader.displayName = "SectionHeader";
|
|
5423
|
-
var SectionTitle =
|
|
5539
|
+
var SectionTitle = React14__namespace.forwardRef(
|
|
5424
5540
|
({ className, ...props }, ref) => /* @__PURE__ */ jsxRuntime.jsx(
|
|
5425
5541
|
"h2",
|
|
5426
5542
|
{
|
|
@@ -5434,7 +5550,7 @@ var SectionTitle = React7__namespace.forwardRef(
|
|
|
5434
5550
|
)
|
|
5435
5551
|
);
|
|
5436
5552
|
SectionTitle.displayName = "SectionTitle";
|
|
5437
|
-
var SectionDescription =
|
|
5553
|
+
var SectionDescription = React14__namespace.forwardRef(
|
|
5438
5554
|
({ className, ...props }, ref) => /* @__PURE__ */ jsxRuntime.jsx(
|
|
5439
5555
|
"p",
|
|
5440
5556
|
{
|
|
@@ -5448,7 +5564,7 @@ var SectionDescription = React7__namespace.forwardRef(
|
|
|
5448
5564
|
)
|
|
5449
5565
|
);
|
|
5450
5566
|
SectionDescription.displayName = "SectionDescription";
|
|
5451
|
-
var SectionContent =
|
|
5567
|
+
var SectionContent = React14__namespace.forwardRef(
|
|
5452
5568
|
({ className, ...props }, ref) => /* @__PURE__ */ jsxRuntime.jsx(
|
|
5453
5569
|
"div",
|
|
5454
5570
|
{
|
|
@@ -5462,7 +5578,7 @@ var SectionContent = React7__namespace.forwardRef(
|
|
|
5462
5578
|
)
|
|
5463
5579
|
);
|
|
5464
5580
|
SectionContent.displayName = "SectionContent";
|
|
5465
|
-
var SectionFooter =
|
|
5581
|
+
var SectionFooter = React14__namespace.forwardRef(
|
|
5466
5582
|
({ className, ...props }, ref) => /* @__PURE__ */ jsxRuntime.jsx(
|
|
5467
5583
|
"div",
|
|
5468
5584
|
{
|
|
@@ -5478,11 +5594,3215 @@ var SectionFooter = React7__namespace.forwardRef(
|
|
|
5478
5594
|
)
|
|
5479
5595
|
);
|
|
5480
5596
|
SectionFooter.displayName = "SectionFooter";
|
|
5597
|
+
function SearchForm({ ...props }) {
|
|
5598
|
+
return /* @__PURE__ */ jsxRuntime.jsx("form", { ...props, children: /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "relative", children: [
|
|
5599
|
+
/* @__PURE__ */ jsxRuntime.jsx(Label2, { htmlFor: "search", className: "sr-only", children: "Search" }),
|
|
5600
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
5601
|
+
SidebarInput,
|
|
5602
|
+
{
|
|
5603
|
+
id: "search",
|
|
5604
|
+
placeholder: "Type to search...",
|
|
5605
|
+
className: "h-8 pl-7"
|
|
5606
|
+
}
|
|
5607
|
+
),
|
|
5608
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.SearchIcon, { className: "pointer-events-none absolute top-1/2 left-2 size-4 -translate-y-1/2 opacity-50 select-none" })
|
|
5609
|
+
] }) });
|
|
5610
|
+
}
|
|
5611
|
+
function SiteHeader({
|
|
5612
|
+
trigger,
|
|
5613
|
+
breadcrumbs = [
|
|
5614
|
+
{ label: "Building Your Application", href: "#" },
|
|
5615
|
+
{ label: "Data Fetching" }
|
|
5616
|
+
],
|
|
5617
|
+
showSearch = true,
|
|
5618
|
+
className,
|
|
5619
|
+
children
|
|
5620
|
+
}) {
|
|
5621
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
5622
|
+
"header",
|
|
5623
|
+
{
|
|
5624
|
+
"data-slot": "site-header",
|
|
5625
|
+
className: cn(
|
|
5626
|
+
"bg-sidebar text-sidebar-foreground sticky top-0 z-50 flex w-full items-center border-b border-sidebar-border",
|
|
5627
|
+
className
|
|
5628
|
+
),
|
|
5629
|
+
children: /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex h-[var(--header-height,3.5rem)] w-full items-center gap-[var(--j3m-spacing-s)] px-[var(--j3m-spacing-m)]", children: [
|
|
5630
|
+
trigger,
|
|
5631
|
+
trigger && /* @__PURE__ */ jsxRuntime.jsx(Separator, { orientation: "vertical", className: "mr-[var(--j3m-spacing-s)] h-4" }),
|
|
5632
|
+
/* @__PURE__ */ jsxRuntime.jsx(Breadcrumb, { className: "hidden sm:block", children: /* @__PURE__ */ jsxRuntime.jsx(BreadcrumbList, { children: breadcrumbs.map((item, index) => /* @__PURE__ */ jsxRuntime.jsxs(React14__namespace.Fragment, { children: [
|
|
5633
|
+
index > 0 && /* @__PURE__ */ jsxRuntime.jsx(BreadcrumbSeparator, {}),
|
|
5634
|
+
/* @__PURE__ */ jsxRuntime.jsx(BreadcrumbItem, { children: item.href ? /* @__PURE__ */ jsxRuntime.jsx(BreadcrumbLink, { href: item.href, children: item.label }) : /* @__PURE__ */ jsxRuntime.jsx(BreadcrumbPage, { children: item.label }) })
|
|
5635
|
+
] }, index)) }) }),
|
|
5636
|
+
showSearch && /* @__PURE__ */ jsxRuntime.jsx(SearchForm, { className: "w-full sm:ml-auto sm:w-auto" }),
|
|
5637
|
+
children
|
|
5638
|
+
] })
|
|
5639
|
+
}
|
|
5640
|
+
);
|
|
5641
|
+
}
|
|
5642
|
+
function NavMain({ items, label = "Platform" }) {
|
|
5643
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(SidebarGroup, { children: [
|
|
5644
|
+
/* @__PURE__ */ jsxRuntime.jsx(SidebarGroupLabel, { children: label }),
|
|
5645
|
+
/* @__PURE__ */ jsxRuntime.jsx(SidebarMenu, { children: items.map((item) => /* @__PURE__ */ jsxRuntime.jsx(Collapsible, { asChild: true, defaultOpen: item.isActive, children: /* @__PURE__ */ jsxRuntime.jsxs(SidebarMenuItem, { children: [
|
|
5646
|
+
/* @__PURE__ */ jsxRuntime.jsx(SidebarMenuButton, { asChild: true, tooltip: item.title, children: /* @__PURE__ */ jsxRuntime.jsxs("a", { href: item.url, children: [
|
|
5647
|
+
item.icon && /* @__PURE__ */ jsxRuntime.jsx(item.icon, {}),
|
|
5648
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { children: item.title })
|
|
5649
|
+
] }) }),
|
|
5650
|
+
item.items?.length ? /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
|
|
5651
|
+
/* @__PURE__ */ jsxRuntime.jsx(CollapsibleTrigger2, { asChild: true, children: /* @__PURE__ */ jsxRuntime.jsxs(SidebarMenuAction, { className: "data-[state=open]:rotate-90", children: [
|
|
5652
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.ChevronRightIcon, {}),
|
|
5653
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "sr-only", children: "Toggle" })
|
|
5654
|
+
] }) }),
|
|
5655
|
+
/* @__PURE__ */ jsxRuntime.jsx(CollapsibleContent2, { children: /* @__PURE__ */ jsxRuntime.jsx(SidebarMenuSub, { children: item.items?.map((subItem) => /* @__PURE__ */ jsxRuntime.jsx(SidebarMenuSubItem, { children: /* @__PURE__ */ jsxRuntime.jsx(SidebarMenuSubButton, { asChild: true, children: /* @__PURE__ */ jsxRuntime.jsx("a", { href: subItem.url, children: /* @__PURE__ */ jsxRuntime.jsx("span", { children: subItem.title }) }) }) }, subItem.title)) }) })
|
|
5656
|
+
] }) : null
|
|
5657
|
+
] }) }, item.title)) })
|
|
5658
|
+
] });
|
|
5659
|
+
}
|
|
5660
|
+
function NavProjects({ projects, label = "Projects" }) {
|
|
5661
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(SidebarGroup, { className: "group-data-[collapsible=icon]:hidden", children: [
|
|
5662
|
+
/* @__PURE__ */ jsxRuntime.jsx(SidebarGroupLabel, { children: label }),
|
|
5663
|
+
/* @__PURE__ */ jsxRuntime.jsxs(SidebarMenu, { children: [
|
|
5664
|
+
projects.map((item) => /* @__PURE__ */ jsxRuntime.jsxs(SidebarMenuItem, { children: [
|
|
5665
|
+
/* @__PURE__ */ jsxRuntime.jsx(SidebarMenuButton, { asChild: true, children: /* @__PURE__ */ jsxRuntime.jsxs("a", { href: item.url, children: [
|
|
5666
|
+
/* @__PURE__ */ jsxRuntime.jsx(item.icon, {}),
|
|
5667
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { children: item.name })
|
|
5668
|
+
] }) }),
|
|
5669
|
+
/* @__PURE__ */ jsxRuntime.jsxs(DropdownMenu, { children: [
|
|
5670
|
+
/* @__PURE__ */ jsxRuntime.jsx(DropdownMenuTrigger, { asChild: true, children: /* @__PURE__ */ jsxRuntime.jsxs(SidebarMenuAction, { showOnHover: true, children: [
|
|
5671
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.MoreHorizontalIcon, {}),
|
|
5672
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "sr-only", children: "More" })
|
|
5673
|
+
] }) }),
|
|
5674
|
+
/* @__PURE__ */ jsxRuntime.jsxs(
|
|
5675
|
+
DropdownMenuContent,
|
|
5676
|
+
{
|
|
5677
|
+
className: "w-48 rounded-[var(--j3m-radius-m)]",
|
|
5678
|
+
side: "right",
|
|
5679
|
+
align: "start",
|
|
5680
|
+
sideOffset: 8,
|
|
5681
|
+
children: [
|
|
5682
|
+
/* @__PURE__ */ jsxRuntime.jsxs(DropdownMenuItem, { children: [
|
|
5683
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.FolderIcon, { className: "text-muted-foreground" }),
|
|
5684
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { children: "View Project" })
|
|
5685
|
+
] }),
|
|
5686
|
+
/* @__PURE__ */ jsxRuntime.jsxs(DropdownMenuItem, { children: [
|
|
5687
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.ShareIcon, { className: "text-muted-foreground" }),
|
|
5688
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { children: "Share Project" })
|
|
5689
|
+
] }),
|
|
5690
|
+
/* @__PURE__ */ jsxRuntime.jsx(DropdownMenuSeparator, {}),
|
|
5691
|
+
/* @__PURE__ */ jsxRuntime.jsxs(DropdownMenuItem, { children: [
|
|
5692
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.TrashIcon, { className: "text-muted-foreground" }),
|
|
5693
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { children: "Delete Project" })
|
|
5694
|
+
] })
|
|
5695
|
+
]
|
|
5696
|
+
}
|
|
5697
|
+
)
|
|
5698
|
+
] })
|
|
5699
|
+
] }, item.name)),
|
|
5700
|
+
/* @__PURE__ */ jsxRuntime.jsx(SidebarMenuItem, { children: /* @__PURE__ */ jsxRuntime.jsxs(SidebarMenuButton, { className: "text-sidebar-foreground/70", children: [
|
|
5701
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.MoreHorizontalIcon, { className: "text-sidebar-foreground/70" }),
|
|
5702
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { children: "More" })
|
|
5703
|
+
] }) })
|
|
5704
|
+
] })
|
|
5705
|
+
] });
|
|
5706
|
+
}
|
|
5707
|
+
function NavSecondary({ items, ...props }) {
|
|
5708
|
+
return /* @__PURE__ */ jsxRuntime.jsx(SidebarGroup, { ...props, children: /* @__PURE__ */ jsxRuntime.jsx(SidebarGroupContent, { children: /* @__PURE__ */ jsxRuntime.jsx(SidebarMenu, { children: items.map((item) => /* @__PURE__ */ jsxRuntime.jsx(SidebarMenuItem, { children: /* @__PURE__ */ jsxRuntime.jsx(SidebarMenuButton, { asChild: true, size: "sm", children: /* @__PURE__ */ jsxRuntime.jsxs("a", { href: item.url, children: [
|
|
5709
|
+
/* @__PURE__ */ jsxRuntime.jsx(item.icon, {}),
|
|
5710
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { children: item.title })
|
|
5711
|
+
] }) }) }, item.title)) }) }) });
|
|
5712
|
+
}
|
|
5713
|
+
function NavUser({ user }) {
|
|
5714
|
+
return /* @__PURE__ */ jsxRuntime.jsx(SidebarMenu, { children: /* @__PURE__ */ jsxRuntime.jsx(SidebarMenuItem, { children: /* @__PURE__ */ jsxRuntime.jsxs(DropdownMenu, { children: [
|
|
5715
|
+
/* @__PURE__ */ jsxRuntime.jsx(DropdownMenuTrigger, { asChild: true, children: /* @__PURE__ */ jsxRuntime.jsxs(
|
|
5716
|
+
SidebarMenuButton,
|
|
5717
|
+
{
|
|
5718
|
+
size: "lg",
|
|
5719
|
+
className: "data-[state=open]:bg-sidebar-accent data-[state=open]:text-sidebar-accent-foreground",
|
|
5720
|
+
children: [
|
|
5721
|
+
/* @__PURE__ */ jsxRuntime.jsxs(Avatar, { className: "h-8 w-8 rounded-lg", children: [
|
|
5722
|
+
/* @__PURE__ */ jsxRuntime.jsx(AvatarImage, { src: user.avatar, alt: user.name }),
|
|
5723
|
+
/* @__PURE__ */ jsxRuntime.jsx(AvatarFallback, { className: "rounded-lg", children: user.name.slice(0, 2).toUpperCase() })
|
|
5724
|
+
] }),
|
|
5725
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "grid flex-1 text-left text-sm leading-tight", children: [
|
|
5726
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "truncate font-semibold", children: user.name }),
|
|
5727
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "truncate text-xs", children: user.email })
|
|
5728
|
+
] }),
|
|
5729
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.ChevronsUpDownIcon, { className: "ml-auto size-4" })
|
|
5730
|
+
]
|
|
5731
|
+
}
|
|
5732
|
+
) }),
|
|
5733
|
+
/* @__PURE__ */ jsxRuntime.jsxs(
|
|
5734
|
+
DropdownMenuContent,
|
|
5735
|
+
{
|
|
5736
|
+
className: "w-[--radix-dropdown-menu-trigger-width] min-w-56 rounded-[var(--j3m-radius-m)]",
|
|
5737
|
+
side: "right",
|
|
5738
|
+
align: "end",
|
|
5739
|
+
sideOffset: 8,
|
|
5740
|
+
children: [
|
|
5741
|
+
/* @__PURE__ */ jsxRuntime.jsx(DropdownMenuLabel, { className: "p-0 font-normal", children: /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center gap-2 px-1 py-1.5 text-left text-sm", children: [
|
|
5742
|
+
/* @__PURE__ */ jsxRuntime.jsxs(Avatar, { className: "h-8 w-8 rounded-lg", children: [
|
|
5743
|
+
/* @__PURE__ */ jsxRuntime.jsx(AvatarImage, { src: user.avatar, alt: user.name }),
|
|
5744
|
+
/* @__PURE__ */ jsxRuntime.jsx(AvatarFallback, { className: "rounded-lg", children: user.name.slice(0, 2).toUpperCase() })
|
|
5745
|
+
] }),
|
|
5746
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "grid flex-1 text-left text-sm leading-tight", children: [
|
|
5747
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "truncate font-semibold", children: user.name }),
|
|
5748
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "truncate text-xs", children: user.email })
|
|
5749
|
+
] })
|
|
5750
|
+
] }) }),
|
|
5751
|
+
/* @__PURE__ */ jsxRuntime.jsx(DropdownMenuSeparator, {}),
|
|
5752
|
+
/* @__PURE__ */ jsxRuntime.jsx(DropdownMenuGroup, { children: /* @__PURE__ */ jsxRuntime.jsxs(DropdownMenuItem, { children: [
|
|
5753
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.SparklesIcon, {}),
|
|
5754
|
+
"Upgrade to Pro"
|
|
5755
|
+
] }) }),
|
|
5756
|
+
/* @__PURE__ */ jsxRuntime.jsx(DropdownMenuSeparator, {}),
|
|
5757
|
+
/* @__PURE__ */ jsxRuntime.jsxs(DropdownMenuGroup, { children: [
|
|
5758
|
+
/* @__PURE__ */ jsxRuntime.jsxs(DropdownMenuItem, { children: [
|
|
5759
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.BadgeCheckIcon, {}),
|
|
5760
|
+
"Account"
|
|
5761
|
+
] }),
|
|
5762
|
+
/* @__PURE__ */ jsxRuntime.jsxs(DropdownMenuItem, { children: [
|
|
5763
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.CreditCardIcon, {}),
|
|
5764
|
+
"Billing"
|
|
5765
|
+
] }),
|
|
5766
|
+
/* @__PURE__ */ jsxRuntime.jsxs(DropdownMenuItem, { children: [
|
|
5767
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.BellIcon, {}),
|
|
5768
|
+
"Notifications"
|
|
5769
|
+
] })
|
|
5770
|
+
] }),
|
|
5771
|
+
/* @__PURE__ */ jsxRuntime.jsx(DropdownMenuSeparator, {}),
|
|
5772
|
+
/* @__PURE__ */ jsxRuntime.jsxs(DropdownMenuItem, { children: [
|
|
5773
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.LogOutIcon, {}),
|
|
5774
|
+
"Log out"
|
|
5775
|
+
] })
|
|
5776
|
+
]
|
|
5777
|
+
}
|
|
5778
|
+
)
|
|
5779
|
+
] }) }) });
|
|
5780
|
+
}
|
|
5481
5781
|
|
|
5782
|
+
// src/components/event-calendar/types.ts
|
|
5783
|
+
var DEFAULT_WORKING_HOURS = {
|
|
5784
|
+
0: { from: 0, to: 0 },
|
|
5785
|
+
// Sunday - closed
|
|
5786
|
+
1: { from: 9, to: 17 },
|
|
5787
|
+
// Monday
|
|
5788
|
+
2: { from: 9, to: 17 },
|
|
5789
|
+
// Tuesday
|
|
5790
|
+
3: { from: 9, to: 17 },
|
|
5791
|
+
// Wednesday
|
|
5792
|
+
4: { from: 9, to: 17 },
|
|
5793
|
+
// Thursday
|
|
5794
|
+
5: { from: 9, to: 17 },
|
|
5795
|
+
// Friday
|
|
5796
|
+
6: { from: 0, to: 0 }
|
|
5797
|
+
// Saturday - closed
|
|
5798
|
+
};
|
|
5799
|
+
var DEFAULT_VISIBLE_HOURS = { from: 0, to: 24 };
|
|
5800
|
+
var EVENT_COLORS = {
|
|
5801
|
+
blue: {
|
|
5802
|
+
bg: "bg-blue-500/20",
|
|
5803
|
+
text: "text-blue-700 dark:text-blue-300",
|
|
5804
|
+
border: "border-blue-500"
|
|
5805
|
+
},
|
|
5806
|
+
green: {
|
|
5807
|
+
bg: "bg-green-500/20",
|
|
5808
|
+
text: "text-green-700 dark:text-green-300",
|
|
5809
|
+
border: "border-green-500"
|
|
5810
|
+
},
|
|
5811
|
+
red: {
|
|
5812
|
+
bg: "bg-red-500/20",
|
|
5813
|
+
text: "text-red-700 dark:text-red-300",
|
|
5814
|
+
border: "border-red-500"
|
|
5815
|
+
},
|
|
5816
|
+
yellow: {
|
|
5817
|
+
bg: "bg-yellow-500/20",
|
|
5818
|
+
text: "text-yellow-700 dark:text-yellow-300",
|
|
5819
|
+
border: "border-yellow-500"
|
|
5820
|
+
},
|
|
5821
|
+
purple: {
|
|
5822
|
+
bg: "bg-purple-500/20",
|
|
5823
|
+
text: "text-purple-700 dark:text-purple-300",
|
|
5824
|
+
border: "border-purple-500"
|
|
5825
|
+
},
|
|
5826
|
+
orange: {
|
|
5827
|
+
bg: "bg-primary/20",
|
|
5828
|
+
text: "text-primary dark:text-orange-300",
|
|
5829
|
+
border: "border-primary"
|
|
5830
|
+
}
|
|
5831
|
+
};
|
|
5832
|
+
var VIEW_LABELS = {
|
|
5833
|
+
month: "Month",
|
|
5834
|
+
week: "Week",
|
|
5835
|
+
day: "Day",
|
|
5836
|
+
year: "Year",
|
|
5837
|
+
agenda: "Agenda"
|
|
5838
|
+
};
|
|
5839
|
+
var BADGE_VARIANT_LABELS = {
|
|
5840
|
+
dot: "Dot",
|
|
5841
|
+
colored: "Colored",
|
|
5842
|
+
mixed: "Mixed"
|
|
5843
|
+
};
|
|
5844
|
+
var CalendarContext = React14__namespace.createContext(null);
|
|
5845
|
+
function EventCalendarProvider({
|
|
5846
|
+
children,
|
|
5847
|
+
events: initialEvents = [],
|
|
5848
|
+
users: initialUsers = [],
|
|
5849
|
+
defaultDate = /* @__PURE__ */ new Date(),
|
|
5850
|
+
defaultView = "month",
|
|
5851
|
+
defaultBadgeVariant = "colored",
|
|
5852
|
+
defaultUserId = null,
|
|
5853
|
+
defaultWorkingHours = DEFAULT_WORKING_HOURS,
|
|
5854
|
+
defaultVisibleHours = DEFAULT_VISIBLE_HOURS,
|
|
5855
|
+
onEventAdd,
|
|
5856
|
+
onEventUpdate,
|
|
5857
|
+
onEventDelete
|
|
5858
|
+
}) {
|
|
5859
|
+
const [selectedDate, setSelectedDate] = React14__namespace.useState(defaultDate);
|
|
5860
|
+
const [selectedUserId, setSelectedUserId] = React14__namespace.useState(defaultUserId);
|
|
5861
|
+
const [events, setEventsState] = React14__namespace.useState(initialEvents);
|
|
5862
|
+
const [users] = React14__namespace.useState(initialUsers);
|
|
5863
|
+
const [badgeVariant, setBadgeVariant] = React14__namespace.useState(defaultBadgeVariant);
|
|
5864
|
+
const [view, setView] = React14__namespace.useState(defaultView);
|
|
5865
|
+
const [workingHours, setWorkingHours] = React14__namespace.useState(defaultWorkingHours);
|
|
5866
|
+
const [visibleHours, setVisibleHours] = React14__namespace.useState(defaultVisibleHours);
|
|
5867
|
+
React14__namespace.useEffect(() => {
|
|
5868
|
+
setEventsState(initialEvents);
|
|
5869
|
+
}, [initialEvents]);
|
|
5870
|
+
const setEvents = React14__namespace.useCallback((newEvents) => {
|
|
5871
|
+
setEventsState(newEvents);
|
|
5872
|
+
}, []);
|
|
5873
|
+
const addEvent = React14__namespace.useCallback((event) => {
|
|
5874
|
+
setEventsState((prev) => [...prev, event]);
|
|
5875
|
+
onEventAdd?.(event);
|
|
5876
|
+
}, [onEventAdd]);
|
|
5877
|
+
const updateEvent = React14__namespace.useCallback((event) => {
|
|
5878
|
+
setEventsState(
|
|
5879
|
+
(prev) => prev.map((e) => e.id === event.id ? event : e)
|
|
5880
|
+
);
|
|
5881
|
+
onEventUpdate?.(event);
|
|
5882
|
+
}, [onEventUpdate]);
|
|
5883
|
+
const deleteEvent = React14__namespace.useCallback((eventId) => {
|
|
5884
|
+
setEventsState((prev) => prev.filter((e) => e.id !== eventId));
|
|
5885
|
+
onEventDelete?.(eventId);
|
|
5886
|
+
}, [onEventDelete]);
|
|
5887
|
+
const goToToday = React14__namespace.useCallback(() => {
|
|
5888
|
+
setSelectedDate(/* @__PURE__ */ new Date());
|
|
5889
|
+
}, []);
|
|
5890
|
+
const goToPrevious = React14__namespace.useCallback(() => {
|
|
5891
|
+
setSelectedDate((current) => {
|
|
5892
|
+
switch (view) {
|
|
5893
|
+
case "day":
|
|
5894
|
+
return dateFns.subDays(current, 1);
|
|
5895
|
+
case "week":
|
|
5896
|
+
return dateFns.subWeeks(current, 1);
|
|
5897
|
+
case "month":
|
|
5898
|
+
return dateFns.subMonths(current, 1);
|
|
5899
|
+
case "year":
|
|
5900
|
+
return dateFns.subYears(current, 1);
|
|
5901
|
+
case "agenda":
|
|
5902
|
+
return dateFns.subMonths(current, 1);
|
|
5903
|
+
default:
|
|
5904
|
+
return current;
|
|
5905
|
+
}
|
|
5906
|
+
});
|
|
5907
|
+
}, [view]);
|
|
5908
|
+
const goToNext = React14__namespace.useCallback(() => {
|
|
5909
|
+
setSelectedDate((current) => {
|
|
5910
|
+
switch (view) {
|
|
5911
|
+
case "day":
|
|
5912
|
+
return dateFns.addDays(current, 1);
|
|
5913
|
+
case "week":
|
|
5914
|
+
return dateFns.addWeeks(current, 1);
|
|
5915
|
+
case "month":
|
|
5916
|
+
return dateFns.addMonths(current, 1);
|
|
5917
|
+
case "year":
|
|
5918
|
+
return dateFns.addYears(current, 1);
|
|
5919
|
+
case "agenda":
|
|
5920
|
+
return dateFns.addMonths(current, 1);
|
|
5921
|
+
default:
|
|
5922
|
+
return current;
|
|
5923
|
+
}
|
|
5924
|
+
});
|
|
5925
|
+
}, [view]);
|
|
5926
|
+
const contextValue = React14__namespace.useMemo(
|
|
5927
|
+
() => ({
|
|
5928
|
+
// State
|
|
5929
|
+
selectedDate,
|
|
5930
|
+
selectedUserId,
|
|
5931
|
+
events,
|
|
5932
|
+
users,
|
|
5933
|
+
badgeVariant,
|
|
5934
|
+
view,
|
|
5935
|
+
workingHours,
|
|
5936
|
+
visibleHours,
|
|
5937
|
+
// Actions
|
|
5938
|
+
setSelectedDate,
|
|
5939
|
+
setSelectedUserId,
|
|
5940
|
+
setEvents,
|
|
5941
|
+
addEvent,
|
|
5942
|
+
updateEvent,
|
|
5943
|
+
deleteEvent,
|
|
5944
|
+
setBadgeVariant,
|
|
5945
|
+
setView,
|
|
5946
|
+
setWorkingHours,
|
|
5947
|
+
setVisibleHours,
|
|
5948
|
+
goToToday,
|
|
5949
|
+
goToPrevious,
|
|
5950
|
+
goToNext
|
|
5951
|
+
}),
|
|
5952
|
+
[
|
|
5953
|
+
selectedDate,
|
|
5954
|
+
selectedUserId,
|
|
5955
|
+
events,
|
|
5956
|
+
users,
|
|
5957
|
+
badgeVariant,
|
|
5958
|
+
view,
|
|
5959
|
+
workingHours,
|
|
5960
|
+
visibleHours,
|
|
5961
|
+
setEvents,
|
|
5962
|
+
addEvent,
|
|
5963
|
+
updateEvent,
|
|
5964
|
+
deleteEvent,
|
|
5965
|
+
goToToday,
|
|
5966
|
+
goToPrevious,
|
|
5967
|
+
goToNext
|
|
5968
|
+
]
|
|
5969
|
+
);
|
|
5970
|
+
return /* @__PURE__ */ jsxRuntime.jsx(CalendarContext.Provider, { value: contextValue, children });
|
|
5971
|
+
}
|
|
5972
|
+
function useEventCalendar() {
|
|
5973
|
+
const context = React14__namespace.useContext(CalendarContext);
|
|
5974
|
+
if (!context) {
|
|
5975
|
+
throw new Error("useEventCalendar must be used within an EventCalendarProvider");
|
|
5976
|
+
}
|
|
5977
|
+
return context;
|
|
5978
|
+
}
|
|
5979
|
+
function useFilteredEvents() {
|
|
5980
|
+
const { events, selectedUserId } = useEventCalendar();
|
|
5981
|
+
return React14__namespace.useMemo(() => {
|
|
5982
|
+
if (!selectedUserId) return events;
|
|
5983
|
+
return events.filter((event) => event.user.id === selectedUserId);
|
|
5984
|
+
}, [events, selectedUserId]);
|
|
5985
|
+
}
|
|
5986
|
+
function useEventsInRange(startDate, endDate) {
|
|
5987
|
+
const filteredEvents = useFilteredEvents();
|
|
5988
|
+
return React14__namespace.useMemo(() => {
|
|
5989
|
+
return filteredEvents.filter((event) => {
|
|
5990
|
+
const eventStart = new Date(event.startDate);
|
|
5991
|
+
const eventEnd = new Date(event.endDate);
|
|
5992
|
+
return eventStart <= endDate && eventEnd >= startDate;
|
|
5993
|
+
});
|
|
5994
|
+
}, [filteredEvents, startDate, endDate]);
|
|
5995
|
+
}
|
|
5996
|
+
function rangeText(view, date) {
|
|
5997
|
+
const formatString = "MMM d, yyyy";
|
|
5998
|
+
let start;
|
|
5999
|
+
let end;
|
|
6000
|
+
switch (view) {
|
|
6001
|
+
case "agenda":
|
|
6002
|
+
start = dateFns.startOfMonth(date);
|
|
6003
|
+
end = dateFns.endOfMonth(date);
|
|
6004
|
+
break;
|
|
6005
|
+
case "year":
|
|
6006
|
+
start = dateFns.startOfYear(date);
|
|
6007
|
+
end = dateFns.endOfYear(date);
|
|
6008
|
+
break;
|
|
6009
|
+
case "month":
|
|
6010
|
+
start = dateFns.startOfMonth(date);
|
|
6011
|
+
end = dateFns.endOfMonth(date);
|
|
6012
|
+
break;
|
|
6013
|
+
case "week":
|
|
6014
|
+
start = dateFns.startOfWeek(date);
|
|
6015
|
+
end = dateFns.endOfWeek(date);
|
|
6016
|
+
break;
|
|
6017
|
+
case "day":
|
|
6018
|
+
return dateFns.format(date, formatString);
|
|
6019
|
+
default:
|
|
6020
|
+
return "Error while formatting";
|
|
6021
|
+
}
|
|
6022
|
+
return `${dateFns.format(start, formatString)} - ${dateFns.format(end, formatString)}`;
|
|
6023
|
+
}
|
|
6024
|
+
function navigateDate(date, view, direction) {
|
|
6025
|
+
const operations = {
|
|
6026
|
+
agenda: direction === "next" ? dateFns.addMonths : dateFns.subMonths,
|
|
6027
|
+
year: direction === "next" ? dateFns.addYears : dateFns.subYears,
|
|
6028
|
+
month: direction === "next" ? dateFns.addMonths : dateFns.subMonths,
|
|
6029
|
+
week: direction === "next" ? dateFns.addWeeks : dateFns.subWeeks,
|
|
6030
|
+
day: direction === "next" ? dateFns.addDays : dateFns.subDays
|
|
6031
|
+
};
|
|
6032
|
+
return operations[view](date, 1);
|
|
6033
|
+
}
|
|
6034
|
+
function getEventsCount(events, date, view) {
|
|
6035
|
+
const compareFns = {
|
|
6036
|
+
agenda: dateFns.isSameMonth,
|
|
6037
|
+
year: dateFns.isSameYear,
|
|
6038
|
+
day: dateFns.isSameDay,
|
|
6039
|
+
week: dateFns.isSameWeek,
|
|
6040
|
+
month: dateFns.isSameMonth
|
|
6041
|
+
};
|
|
6042
|
+
return events.filter(
|
|
6043
|
+
(event) => compareFns[view](new Date(event.startDate), date)
|
|
6044
|
+
).length;
|
|
6045
|
+
}
|
|
6046
|
+
function getCurrentEvents(events) {
|
|
6047
|
+
const now = /* @__PURE__ */ new Date();
|
|
6048
|
+
return events.filter(
|
|
6049
|
+
(event) => dateFns.isWithinInterval(now, {
|
|
6050
|
+
start: dateFns.parseISO(event.startDate),
|
|
6051
|
+
end: dateFns.parseISO(event.endDate)
|
|
6052
|
+
})
|
|
6053
|
+
) || [];
|
|
6054
|
+
}
|
|
6055
|
+
function groupEvents(dayEvents) {
|
|
6056
|
+
const sortedEvents = dayEvents.sort(
|
|
6057
|
+
(a, b) => dateFns.parseISO(a.startDate).getTime() - dateFns.parseISO(b.startDate).getTime()
|
|
6058
|
+
);
|
|
6059
|
+
const groups = [];
|
|
6060
|
+
for (const event of sortedEvents) {
|
|
6061
|
+
const eventStart = dateFns.parseISO(event.startDate);
|
|
6062
|
+
let placed = false;
|
|
6063
|
+
for (const group of groups) {
|
|
6064
|
+
const lastEventInGroup = group[group.length - 1];
|
|
6065
|
+
const lastEventEnd = dateFns.parseISO(lastEventInGroup.endDate);
|
|
6066
|
+
if (eventStart >= lastEventEnd) {
|
|
6067
|
+
group.push(event);
|
|
6068
|
+
placed = true;
|
|
6069
|
+
break;
|
|
6070
|
+
}
|
|
6071
|
+
}
|
|
6072
|
+
if (!placed) groups.push([event]);
|
|
6073
|
+
}
|
|
6074
|
+
return groups;
|
|
6075
|
+
}
|
|
6076
|
+
function getEventBlockStyle(event, day, groupIndex, groupSize, visibleHoursRange, hourHeight = 96) {
|
|
6077
|
+
const startDate = dateFns.parseISO(event.startDate);
|
|
6078
|
+
const endDate = dateFns.parseISO(event.endDate);
|
|
6079
|
+
const dayStart = new Date(day);
|
|
6080
|
+
dayStart.setHours(0, 0, 0, 0);
|
|
6081
|
+
const eventStart = startDate < dayStart ? dayStart : startDate;
|
|
6082
|
+
const startMinutes = dateFns.differenceInMinutes(eventStart, dayStart);
|
|
6083
|
+
const durationMinutes = dateFns.differenceInMinutes(endDate, eventStart);
|
|
6084
|
+
const visibleStartMinutes = (visibleHoursRange?.from ?? 0) * 60;
|
|
6085
|
+
const topMinutes = startMinutes - visibleStartMinutes;
|
|
6086
|
+
const topPx = topMinutes / 60 * hourHeight;
|
|
6087
|
+
const heightPx = Math.max(durationMinutes / 60 * hourHeight, hourHeight / 4);
|
|
6088
|
+
const width = 100 / groupSize;
|
|
6089
|
+
const left = groupIndex * width;
|
|
6090
|
+
return {
|
|
6091
|
+
top: `${topPx}px`,
|
|
6092
|
+
height: `${heightPx}px`,
|
|
6093
|
+
width: `${width}%`,
|
|
6094
|
+
left: `${left}%`
|
|
6095
|
+
};
|
|
6096
|
+
}
|
|
6097
|
+
function isWorkingHour(day, hour, workingHours) {
|
|
6098
|
+
const dayIndex = day.getDay();
|
|
6099
|
+
const dayHours = workingHours[dayIndex];
|
|
6100
|
+
return hour >= dayHours.from && hour < dayHours.to;
|
|
6101
|
+
}
|
|
6102
|
+
function getVisibleHours(visibleHours, singleDayEvents) {
|
|
6103
|
+
let earliestEventHour = visibleHours.from;
|
|
6104
|
+
let latestEventHour = visibleHours.to;
|
|
6105
|
+
singleDayEvents.forEach((event) => {
|
|
6106
|
+
const startHour = dateFns.parseISO(event.startDate).getHours();
|
|
6107
|
+
const endTime = dateFns.parseISO(event.endDate);
|
|
6108
|
+
const endHour = endTime.getHours() + (endTime.getMinutes() > 0 ? 1 : 0);
|
|
6109
|
+
if (startHour < earliestEventHour) earliestEventHour = startHour;
|
|
6110
|
+
if (endHour > latestEventHour) latestEventHour = endHour;
|
|
6111
|
+
});
|
|
6112
|
+
latestEventHour = Math.min(latestEventHour, 24);
|
|
6113
|
+
const hours = Array.from(
|
|
6114
|
+
{ length: latestEventHour - earliestEventHour },
|
|
6115
|
+
(_, i) => i + earliestEventHour
|
|
6116
|
+
);
|
|
6117
|
+
return { hours, earliestEventHour, latestEventHour };
|
|
6118
|
+
}
|
|
6119
|
+
function getCalendarCells(selectedDate) {
|
|
6120
|
+
const currentYear = selectedDate.getFullYear();
|
|
6121
|
+
const currentMonth = selectedDate.getMonth();
|
|
6122
|
+
const getDaysInMonth = (year, month) => new Date(year, month + 1, 0).getDate();
|
|
6123
|
+
const getFirstDayOfMonth = (year, month) => new Date(year, month, 1).getDay();
|
|
6124
|
+
const daysInMonth = getDaysInMonth(currentYear, currentMonth);
|
|
6125
|
+
const firstDayOfMonth = getFirstDayOfMonth(currentYear, currentMonth);
|
|
6126
|
+
const daysInPrevMonth = getDaysInMonth(currentYear, currentMonth - 1);
|
|
6127
|
+
const totalDays = firstDayOfMonth + daysInMonth;
|
|
6128
|
+
const prevMonthCells = Array.from({ length: firstDayOfMonth }, (_, i) => ({
|
|
6129
|
+
day: daysInPrevMonth - firstDayOfMonth + i + 1,
|
|
6130
|
+
currentMonth: false,
|
|
6131
|
+
date: new Date(
|
|
6132
|
+
currentYear,
|
|
6133
|
+
currentMonth - 1,
|
|
6134
|
+
daysInPrevMonth - firstDayOfMonth + i + 1
|
|
6135
|
+
)
|
|
6136
|
+
}));
|
|
6137
|
+
const currentMonthCells = Array.from({ length: daysInMonth }, (_, i) => ({
|
|
6138
|
+
day: i + 1,
|
|
6139
|
+
currentMonth: true,
|
|
6140
|
+
date: new Date(currentYear, currentMonth, i + 1)
|
|
6141
|
+
}));
|
|
6142
|
+
const nextMonthCells = Array.from(
|
|
6143
|
+
{ length: (7 - totalDays % 7) % 7 },
|
|
6144
|
+
(_, i) => ({
|
|
6145
|
+
day: i + 1,
|
|
6146
|
+
currentMonth: false,
|
|
6147
|
+
date: new Date(currentYear, currentMonth + 1, i + 1)
|
|
6148
|
+
})
|
|
6149
|
+
);
|
|
6150
|
+
return [...prevMonthCells, ...currentMonthCells, ...nextMonthCells];
|
|
6151
|
+
}
|
|
6152
|
+
function calculateMonthEventPositions(multiDayEvents, singleDayEvents, selectedDate) {
|
|
6153
|
+
const monthStart = dateFns.startOfMonth(selectedDate);
|
|
6154
|
+
const monthEnd = dateFns.endOfMonth(selectedDate);
|
|
6155
|
+
const eventPositions = {};
|
|
6156
|
+
const occupiedPositions = {};
|
|
6157
|
+
dateFns.eachDayOfInterval({ start: monthStart, end: monthEnd }).forEach((day) => {
|
|
6158
|
+
occupiedPositions[day.toISOString()] = [false, false, false];
|
|
6159
|
+
});
|
|
6160
|
+
const sortedEvents = [
|
|
6161
|
+
...multiDayEvents.sort((a, b) => {
|
|
6162
|
+
const aDuration = dateFns.differenceInDays(
|
|
6163
|
+
dateFns.parseISO(a.endDate),
|
|
6164
|
+
dateFns.parseISO(a.startDate)
|
|
6165
|
+
);
|
|
6166
|
+
const bDuration = dateFns.differenceInDays(
|
|
6167
|
+
dateFns.parseISO(b.endDate),
|
|
6168
|
+
dateFns.parseISO(b.startDate)
|
|
6169
|
+
);
|
|
6170
|
+
return bDuration - aDuration || dateFns.parseISO(a.startDate).getTime() - dateFns.parseISO(b.startDate).getTime();
|
|
6171
|
+
}),
|
|
6172
|
+
...singleDayEvents.sort(
|
|
6173
|
+
(a, b) => dateFns.parseISO(a.startDate).getTime() - dateFns.parseISO(b.startDate).getTime()
|
|
6174
|
+
)
|
|
6175
|
+
];
|
|
6176
|
+
sortedEvents.forEach((event) => {
|
|
6177
|
+
const eventStart = dateFns.parseISO(event.startDate);
|
|
6178
|
+
const eventEnd = dateFns.parseISO(event.endDate);
|
|
6179
|
+
const eventDays = dateFns.eachDayOfInterval({
|
|
6180
|
+
start: eventStart < monthStart ? monthStart : eventStart,
|
|
6181
|
+
end: eventEnd > monthEnd ? monthEnd : eventEnd
|
|
6182
|
+
});
|
|
6183
|
+
let position = -1;
|
|
6184
|
+
for (let i = 0; i < 3; i++) {
|
|
6185
|
+
if (eventDays.every((day) => {
|
|
6186
|
+
const dayPositions = occupiedPositions[dateFns.startOfDay(day).toISOString()];
|
|
6187
|
+
return dayPositions && !dayPositions[i];
|
|
6188
|
+
})) {
|
|
6189
|
+
position = i;
|
|
6190
|
+
break;
|
|
6191
|
+
}
|
|
6192
|
+
}
|
|
6193
|
+
if (position !== -1) {
|
|
6194
|
+
eventDays.forEach((day) => {
|
|
6195
|
+
const dayKey = dateFns.startOfDay(day).toISOString();
|
|
6196
|
+
occupiedPositions[dayKey][position] = true;
|
|
6197
|
+
});
|
|
6198
|
+
eventPositions[event.id] = position;
|
|
6199
|
+
}
|
|
6200
|
+
});
|
|
6201
|
+
return eventPositions;
|
|
6202
|
+
}
|
|
6203
|
+
function getMonthCellEvents(date, events, eventPositions) {
|
|
6204
|
+
const eventsForDate = events.filter((event) => {
|
|
6205
|
+
const eventStart = dateFns.parseISO(event.startDate);
|
|
6206
|
+
const eventEnd = dateFns.parseISO(event.endDate);
|
|
6207
|
+
return date >= eventStart && date <= eventEnd || dateFns.isSameDay(date, eventStart) || dateFns.isSameDay(date, eventEnd);
|
|
6208
|
+
});
|
|
6209
|
+
return eventsForDate.map((event) => ({
|
|
6210
|
+
...event,
|
|
6211
|
+
position: eventPositions[event.id] ?? -1,
|
|
6212
|
+
isMultiDay: event.startDate !== event.endDate
|
|
6213
|
+
})).sort((a, b) => {
|
|
6214
|
+
if (a.isMultiDay && !b.isMultiDay) return -1;
|
|
6215
|
+
if (!a.isMultiDay && b.isMultiDay) return 1;
|
|
6216
|
+
return a.position - b.position;
|
|
6217
|
+
});
|
|
6218
|
+
}
|
|
6219
|
+
function getMonthDays(date, weekStartsOn = 0) {
|
|
6220
|
+
const start = dateFns.startOfWeek(dateFns.startOfMonth(date), { weekStartsOn });
|
|
6221
|
+
const end = dateFns.endOfWeek(dateFns.endOfMonth(date), { weekStartsOn });
|
|
6222
|
+
return dateFns.eachDayOfInterval({ start, end });
|
|
6223
|
+
}
|
|
6224
|
+
function getWeekDays(date, weekStartsOn = 0) {
|
|
6225
|
+
const start = dateFns.startOfWeek(date, { weekStartsOn });
|
|
6226
|
+
const end = dateFns.endOfWeek(date, { weekStartsOn });
|
|
6227
|
+
return dateFns.eachDayOfInterval({ start, end });
|
|
6228
|
+
}
|
|
6229
|
+
function getDayHours(date, start = 0, end = 24) {
|
|
6230
|
+
const dayStart = dateFns.setMinutes(dateFns.setHours(date, start), 0);
|
|
6231
|
+
const dayEnd = dateFns.setMinutes(dateFns.setHours(date, end - 1), 59);
|
|
6232
|
+
return dateFns.eachHourOfInterval({ start: dayStart, end: dayEnd });
|
|
6233
|
+
}
|
|
6234
|
+
function getYearMonths(date) {
|
|
6235
|
+
const start = dateFns.startOfYear(date);
|
|
6236
|
+
const months = [];
|
|
6237
|
+
for (let i = 0; i < 12; i++) {
|
|
6238
|
+
months.push(new Date(start.getFullYear(), i, 1));
|
|
6239
|
+
}
|
|
6240
|
+
return months;
|
|
6241
|
+
}
|
|
6242
|
+
function getEventsForDate(events, date) {
|
|
6243
|
+
return events.filter((event) => {
|
|
6244
|
+
const eventStart = dateFns.parseISO(event.startDate);
|
|
6245
|
+
const eventEnd = dateFns.parseISO(event.endDate);
|
|
6246
|
+
return dateFns.isWithinInterval(date, {
|
|
6247
|
+
start: dateFns.startOfDay(eventStart),
|
|
6248
|
+
end: dateFns.endOfDay(eventEnd)
|
|
6249
|
+
}) || dateFns.isSameDay(eventStart, date) || dateFns.isSameDay(eventEnd, date);
|
|
6250
|
+
});
|
|
6251
|
+
}
|
|
6252
|
+
function getEventsInRange(events, start, end) {
|
|
6253
|
+
return events.filter((event) => {
|
|
6254
|
+
const eventStart = dateFns.parseISO(event.startDate);
|
|
6255
|
+
const eventEnd = dateFns.parseISO(event.endDate);
|
|
6256
|
+
return eventStart >= start && eventStart <= end || eventEnd >= start && eventEnd <= end || eventStart <= start && eventEnd >= end;
|
|
6257
|
+
});
|
|
6258
|
+
}
|
|
6259
|
+
function splitEventsByDuration(events) {
|
|
6260
|
+
const singleDayEvents = [];
|
|
6261
|
+
const multiDayEvents = [];
|
|
6262
|
+
events.forEach((event) => {
|
|
6263
|
+
const start = dateFns.parseISO(event.startDate);
|
|
6264
|
+
const end = dateFns.parseISO(event.endDate);
|
|
6265
|
+
if (dateFns.isSameDay(start, end)) {
|
|
6266
|
+
singleDayEvents.push(event);
|
|
6267
|
+
} else {
|
|
6268
|
+
multiDayEvents.push(event);
|
|
6269
|
+
}
|
|
6270
|
+
});
|
|
6271
|
+
return { singleDayEvents, multiDayEvents };
|
|
6272
|
+
}
|
|
6273
|
+
function isMultiDayEvent(event) {
|
|
6274
|
+
const start = dateFns.parseISO(event.startDate);
|
|
6275
|
+
const end = dateFns.parseISO(event.endDate);
|
|
6276
|
+
return !dateFns.isSameDay(start, end);
|
|
6277
|
+
}
|
|
6278
|
+
function getEventDuration(event) {
|
|
6279
|
+
const start = dateFns.parseISO(event.startDate);
|
|
6280
|
+
const end = dateFns.parseISO(event.endDate);
|
|
6281
|
+
return dateFns.differenceInDays(end, start) + 1;
|
|
6282
|
+
}
|
|
6283
|
+
function getEventDurationMinutes(event) {
|
|
6284
|
+
const start = dateFns.parseISO(event.startDate);
|
|
6285
|
+
const end = dateFns.parseISO(event.endDate);
|
|
6286
|
+
return dateFns.differenceInMinutes(end, start);
|
|
6287
|
+
}
|
|
6288
|
+
function sortEvents(events) {
|
|
6289
|
+
return [...events].sort((a, b) => {
|
|
6290
|
+
const startDiff = dateFns.parseISO(a.startDate).getTime() - dateFns.parseISO(b.startDate).getTime();
|
|
6291
|
+
if (startDiff !== 0) return startDiff;
|
|
6292
|
+
return getEventDuration(b) - getEventDuration(a);
|
|
6293
|
+
});
|
|
6294
|
+
}
|
|
6295
|
+
function getTimePosition(event, visibleHoursRange) {
|
|
6296
|
+
const start = dateFns.parseISO(event.startDate);
|
|
6297
|
+
const hours = dateFns.getHours(start);
|
|
6298
|
+
const minutes = dateFns.getMinutes(start);
|
|
6299
|
+
const startHour = visibleHoursRange?.from ?? 0;
|
|
6300
|
+
const totalMinutes = (hours - startHour) * 60 + minutes;
|
|
6301
|
+
const totalDayMinutes = ((visibleHoursRange?.to ?? 24) - startHour) * 60;
|
|
6302
|
+
return totalMinutes / totalDayMinutes * 100;
|
|
6303
|
+
}
|
|
6304
|
+
function getTimeHeight(event, visibleHoursRange) {
|
|
6305
|
+
const duration = getEventDurationMinutes(event);
|
|
6306
|
+
const totalDayMinutes = ((visibleHoursRange?.to ?? 24) - (visibleHoursRange?.from ?? 0)) * 60;
|
|
6307
|
+
return Math.min(duration / totalDayMinutes * 100, 100);
|
|
6308
|
+
}
|
|
6309
|
+
function formatTime(date, use24h = false) {
|
|
6310
|
+
return dateFns.format(date, use24h ? "HH:mm" : "h:mm a");
|
|
6311
|
+
}
|
|
6312
|
+
function getWeekDayNames(weekStartsOn = 0, shortNames = true) {
|
|
6313
|
+
const days = [
|
|
6314
|
+
"Sunday",
|
|
6315
|
+
"Monday",
|
|
6316
|
+
"Tuesday",
|
|
6317
|
+
"Wednesday",
|
|
6318
|
+
"Thursday",
|
|
6319
|
+
"Friday",
|
|
6320
|
+
"Saturday"
|
|
6321
|
+
];
|
|
6322
|
+
const rotated = [...days.slice(weekStartsOn), ...days.slice(0, weekStartsOn)];
|
|
6323
|
+
return shortNames ? rotated.map((d) => d.slice(0, 3)) : rotated;
|
|
6324
|
+
}
|
|
6325
|
+
function getHeaderLabel(date, view) {
|
|
6326
|
+
switch (view) {
|
|
6327
|
+
case "day":
|
|
6328
|
+
return dateFns.format(date, "EEEE, MMMM d, yyyy");
|
|
6329
|
+
case "week":
|
|
6330
|
+
const weekStart = dateFns.startOfWeek(date);
|
|
6331
|
+
const weekEnd = dateFns.endOfWeek(date);
|
|
6332
|
+
if (weekStart.getMonth() === weekEnd.getMonth()) {
|
|
6333
|
+
return dateFns.format(weekStart, "MMMM d") + " - " + dateFns.format(weekEnd, "d, yyyy");
|
|
6334
|
+
}
|
|
6335
|
+
return dateFns.format(weekStart, "MMM d") + " - " + dateFns.format(weekEnd, "MMM d, yyyy");
|
|
6336
|
+
case "month":
|
|
6337
|
+
return dateFns.format(date, "MMMM yyyy");
|
|
6338
|
+
case "year":
|
|
6339
|
+
return dateFns.format(date, "yyyy");
|
|
6340
|
+
case "agenda":
|
|
6341
|
+
return dateFns.format(date, "MMMM yyyy");
|
|
6342
|
+
default:
|
|
6343
|
+
return dateFns.format(date, "MMMM yyyy");
|
|
6344
|
+
}
|
|
6345
|
+
}
|
|
6346
|
+
function getViewDateRange(date, view) {
|
|
6347
|
+
switch (view) {
|
|
6348
|
+
case "day":
|
|
6349
|
+
return { start: dateFns.startOfDay(date), end: dateFns.endOfDay(date) };
|
|
6350
|
+
case "week":
|
|
6351
|
+
return { start: dateFns.startOfWeek(date), end: dateFns.endOfWeek(date) };
|
|
6352
|
+
case "month":
|
|
6353
|
+
return { start: dateFns.startOfMonth(date), end: dateFns.endOfMonth(date) };
|
|
6354
|
+
case "year":
|
|
6355
|
+
return { start: dateFns.startOfYear(date), end: dateFns.endOfYear(date) };
|
|
6356
|
+
case "agenda":
|
|
6357
|
+
return { start: dateFns.startOfMonth(date), end: dateFns.endOfMonth(date) };
|
|
6358
|
+
default:
|
|
6359
|
+
return { start: dateFns.startOfMonth(date), end: dateFns.endOfMonth(date) };
|
|
6360
|
+
}
|
|
6361
|
+
}
|
|
6362
|
+
function formatDateRange(start, end) {
|
|
6363
|
+
if (dateFns.isSameDay(start, end)) {
|
|
6364
|
+
return dateFns.format(start, "MMM d, yyyy");
|
|
6365
|
+
}
|
|
6366
|
+
if (start.getFullYear() === end.getFullYear()) {
|
|
6367
|
+
if (start.getMonth() === end.getMonth()) {
|
|
6368
|
+
return dateFns.format(start, "MMM d") + " - " + dateFns.format(end, "d, yyyy");
|
|
6369
|
+
}
|
|
6370
|
+
return dateFns.format(start, "MMM d") + " - " + dateFns.format(end, "MMM d, yyyy");
|
|
6371
|
+
}
|
|
6372
|
+
return dateFns.format(start, "MMM d, yyyy") + " - " + dateFns.format(end, "MMM d, yyyy");
|
|
6373
|
+
}
|
|
6374
|
+
function createDefaultEvent(startDate, duration = 60) {
|
|
6375
|
+
return {
|
|
6376
|
+
title: "",
|
|
6377
|
+
description: "",
|
|
6378
|
+
startDate: startDate.toISOString(),
|
|
6379
|
+
endDate: dateFns.addMinutes(startDate, duration).toISOString(),
|
|
6380
|
+
color: "blue",
|
|
6381
|
+
user: {
|
|
6382
|
+
id: "",
|
|
6383
|
+
name: ""
|
|
6384
|
+
}
|
|
6385
|
+
};
|
|
6386
|
+
}
|
|
6387
|
+
function generateEventId() {
|
|
6388
|
+
return `event_${Date.now()}_${Math.random().toString(36).substring(2, 9)}`;
|
|
6389
|
+
}
|
|
6390
|
+
function calculateDropDates(event, newStartDate) {
|
|
6391
|
+
const originalStart = dateFns.parseISO(event.startDate);
|
|
6392
|
+
const originalEnd = dateFns.parseISO(event.endDate);
|
|
6393
|
+
const duration = dateFns.differenceInMinutes(originalEnd, originalStart);
|
|
6394
|
+
const newStart = newStartDate;
|
|
6395
|
+
const newEnd = dateFns.addMinutes(newStart, duration);
|
|
6396
|
+
return {
|
|
6397
|
+
startDate: newStart.toISOString(),
|
|
6398
|
+
endDate: newEnd.toISOString()
|
|
6399
|
+
};
|
|
6400
|
+
}
|
|
6401
|
+
function snapToInterval(date, intervalMinutes = 15) {
|
|
6402
|
+
const minutes = dateFns.getMinutes(date);
|
|
6403
|
+
const snappedMinutes = Math.round(minutes / intervalMinutes) * intervalMinutes;
|
|
6404
|
+
return dateFns.setMinutes(date, snappedMinutes);
|
|
6405
|
+
}
|
|
6406
|
+
var colorClasses = {
|
|
6407
|
+
blue: {
|
|
6408
|
+
dot: "bg-blue-500",
|
|
6409
|
+
bg: "bg-blue-50 dark:bg-blue-950/50",
|
|
6410
|
+
text: "text-blue-600 dark:text-blue-400",
|
|
6411
|
+
border: "border-l-blue-500",
|
|
6412
|
+
solid: "bg-blue-500"
|
|
6413
|
+
},
|
|
6414
|
+
green: {
|
|
6415
|
+
dot: "bg-green-500",
|
|
6416
|
+
bg: "bg-green-50 dark:bg-green-950/50",
|
|
6417
|
+
text: "text-green-600 dark:text-green-400",
|
|
6418
|
+
border: "border-l-green-500",
|
|
6419
|
+
solid: "bg-green-500"
|
|
6420
|
+
},
|
|
6421
|
+
red: {
|
|
6422
|
+
dot: "bg-red-500",
|
|
6423
|
+
bg: "bg-red-50 dark:bg-red-950/50",
|
|
6424
|
+
text: "text-red-600 dark:text-red-400",
|
|
6425
|
+
border: "border-l-red-500",
|
|
6426
|
+
solid: "bg-red-500"
|
|
6427
|
+
},
|
|
6428
|
+
yellow: {
|
|
6429
|
+
dot: "bg-yellow-500",
|
|
6430
|
+
bg: "bg-yellow-50 dark:bg-yellow-950/50",
|
|
6431
|
+
text: "text-yellow-600 dark:text-yellow-400",
|
|
6432
|
+
border: "border-l-yellow-500",
|
|
6433
|
+
solid: "bg-yellow-500"
|
|
6434
|
+
},
|
|
6435
|
+
purple: {
|
|
6436
|
+
dot: "bg-purple-500",
|
|
6437
|
+
bg: "bg-purple-50 dark:bg-purple-950/50",
|
|
6438
|
+
text: "text-purple-600 dark:text-purple-400",
|
|
6439
|
+
border: "border-l-purple-500",
|
|
6440
|
+
solid: "bg-purple-500"
|
|
6441
|
+
},
|
|
6442
|
+
orange: {
|
|
6443
|
+
dot: "bg-primary",
|
|
6444
|
+
bg: "bg-orange-50 dark:bg-orange-950/50",
|
|
6445
|
+
text: "text-primary dark:text-orange-400",
|
|
6446
|
+
border: "border-l-primary",
|
|
6447
|
+
solid: "bg-primary"
|
|
6448
|
+
}
|
|
6449
|
+
};
|
|
6450
|
+
function EventBadge({
|
|
6451
|
+
event,
|
|
6452
|
+
variant = "colored",
|
|
6453
|
+
className,
|
|
6454
|
+
showTime = false,
|
|
6455
|
+
compact = false,
|
|
6456
|
+
isDragging = false,
|
|
6457
|
+
onClick
|
|
6458
|
+
}) {
|
|
6459
|
+
const colors = colorClasses[event.color];
|
|
6460
|
+
const startTime = dateFns.format(dateFns.parseISO(event.startDate), "h:mm a");
|
|
6461
|
+
const handleClick = (e) => {
|
|
6462
|
+
e.stopPropagation();
|
|
6463
|
+
onClick?.(event, e);
|
|
6464
|
+
};
|
|
6465
|
+
if (variant === "dot") {
|
|
6466
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(
|
|
6467
|
+
"button",
|
|
6468
|
+
{
|
|
6469
|
+
type: "button",
|
|
6470
|
+
onClick: handleClick,
|
|
6471
|
+
className: cn(
|
|
6472
|
+
"flex items-center gap-1.5 rounded-sm px-1.5 py-0.5 text-left text-xs transition-colors",
|
|
6473
|
+
"hover:bg-muted/50 focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring",
|
|
6474
|
+
isDragging && "opacity-50",
|
|
6475
|
+
className
|
|
6476
|
+
),
|
|
6477
|
+
children: [
|
|
6478
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { className: cn("size-2 shrink-0 rounded-full", colors.dot) }),
|
|
6479
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "truncate text-foreground", children: event.title }),
|
|
6480
|
+
showTime && /* @__PURE__ */ jsxRuntime.jsx("span", { className: "shrink-0 text-muted-foreground", children: startTime })
|
|
6481
|
+
]
|
|
6482
|
+
}
|
|
6483
|
+
);
|
|
6484
|
+
}
|
|
6485
|
+
if (variant === "mixed") {
|
|
6486
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(
|
|
6487
|
+
"button",
|
|
6488
|
+
{
|
|
6489
|
+
type: "button",
|
|
6490
|
+
onClick: handleClick,
|
|
6491
|
+
className: cn(
|
|
6492
|
+
"flex items-center gap-1.5 rounded-sm border-l-2 px-1.5 py-0.5 text-left text-xs transition-colors",
|
|
6493
|
+
"hover:bg-muted/50 focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring",
|
|
6494
|
+
colors.border,
|
|
6495
|
+
isDragging && "opacity-50",
|
|
6496
|
+
className
|
|
6497
|
+
),
|
|
6498
|
+
children: [
|
|
6499
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "truncate text-foreground", children: event.title }),
|
|
6500
|
+
showTime && /* @__PURE__ */ jsxRuntime.jsx("span", { className: "shrink-0 text-muted-foreground", children: startTime })
|
|
6501
|
+
]
|
|
6502
|
+
}
|
|
6503
|
+
);
|
|
6504
|
+
}
|
|
6505
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(
|
|
6506
|
+
"button",
|
|
6507
|
+
{
|
|
6508
|
+
type: "button",
|
|
6509
|
+
onClick: handleClick,
|
|
6510
|
+
className: cn(
|
|
6511
|
+
"flex flex-col items-start rounded-sm border-l-[3px] text-left text-xs transition-colors",
|
|
6512
|
+
"hover:opacity-80 focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring",
|
|
6513
|
+
colors.border,
|
|
6514
|
+
colors.bg,
|
|
6515
|
+
colors.text,
|
|
6516
|
+
compact ? "px-1.5 py-0.5" : "px-2 py-1",
|
|
6517
|
+
isDragging && "opacity-50 shadow-lg",
|
|
6518
|
+
className
|
|
6519
|
+
),
|
|
6520
|
+
children: [
|
|
6521
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "truncate font-medium max-w-full", children: event.title }),
|
|
6522
|
+
showTime && /* @__PURE__ */ jsxRuntime.jsx("span", { className: "shrink-0 text-muted-foreground", children: startTime })
|
|
6523
|
+
]
|
|
6524
|
+
}
|
|
6525
|
+
);
|
|
6526
|
+
}
|
|
6527
|
+
function MoreEvents({ count, onClick, className }) {
|
|
6528
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(
|
|
6529
|
+
"button",
|
|
6530
|
+
{
|
|
6531
|
+
type: "button",
|
|
6532
|
+
onClick,
|
|
6533
|
+
className: cn(
|
|
6534
|
+
"w-full rounded-sm px-2 py-0.5 text-left text-xs text-muted-foreground transition-colors",
|
|
6535
|
+
"hover:bg-muted hover:text-foreground",
|
|
6536
|
+
className
|
|
6537
|
+
),
|
|
6538
|
+
children: [
|
|
6539
|
+
count,
|
|
6540
|
+
" more..."
|
|
6541
|
+
]
|
|
6542
|
+
}
|
|
6543
|
+
);
|
|
6544
|
+
}
|
|
6545
|
+
function TimeIndicator({ className }) {
|
|
6546
|
+
const [now, setNow] = React14__namespace.useState(/* @__PURE__ */ new Date());
|
|
6547
|
+
React14__namespace.useEffect(() => {
|
|
6548
|
+
const interval = setInterval(() => setNow(/* @__PURE__ */ new Date()), 6e4);
|
|
6549
|
+
return () => clearInterval(interval);
|
|
6550
|
+
}, []);
|
|
6551
|
+
const hours = now.getHours();
|
|
6552
|
+
const minutes = now.getMinutes();
|
|
6553
|
+
const topPercent = (hours * 60 + minutes) / (24 * 60) * 100;
|
|
6554
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(
|
|
6555
|
+
"div",
|
|
6556
|
+
{
|
|
6557
|
+
className: cn(
|
|
6558
|
+
"pointer-events-none absolute left-0 right-0 z-20 flex items-center",
|
|
6559
|
+
className
|
|
6560
|
+
),
|
|
6561
|
+
style: { top: `${topPercent}%` },
|
|
6562
|
+
children: [
|
|
6563
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "size-2.5 -translate-x-1/2 rounded-full bg-red-500" }),
|
|
6564
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "h-0.5 flex-1 bg-red-500" })
|
|
6565
|
+
]
|
|
6566
|
+
}
|
|
6567
|
+
);
|
|
6568
|
+
}
|
|
6569
|
+
function DateBadge({ date, className }) {
|
|
6570
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(
|
|
6571
|
+
"div",
|
|
6572
|
+
{
|
|
6573
|
+
className: cn(
|
|
6574
|
+
"flex flex-col w-14 overflow-hidden border border-border rounded-md",
|
|
6575
|
+
className
|
|
6576
|
+
),
|
|
6577
|
+
children: [
|
|
6578
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "bg-foreground text-background text-[10px] font-bold text-center py-1.5 uppercase tracking-wider", children: dateFns.format(date, "MMM") }),
|
|
6579
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "bg-background text-foreground text-2xl font-bold text-center py-2.5", children: dateFns.format(date, "d") })
|
|
6580
|
+
]
|
|
6581
|
+
}
|
|
6582
|
+
);
|
|
6583
|
+
}
|
|
6584
|
+
var DragContext = React14__namespace.createContext(null);
|
|
6585
|
+
function DragProvider({
|
|
6586
|
+
children,
|
|
6587
|
+
snapMinutes = 15,
|
|
6588
|
+
onDragStart,
|
|
6589
|
+
onDragEnd
|
|
6590
|
+
}) {
|
|
6591
|
+
const [draggedEvent, setDraggedEventState] = React14__namespace.useState(null);
|
|
6592
|
+
const [isDragging, setIsDragging] = React14__namespace.useState(false);
|
|
6593
|
+
const { updateEvent } = useEventCalendar();
|
|
6594
|
+
const setDraggedEvent = React14__namespace.useCallback((event) => {
|
|
6595
|
+
setDraggedEventState(event);
|
|
6596
|
+
setIsDragging(!!event);
|
|
6597
|
+
if (event) {
|
|
6598
|
+
onDragStart?.(event);
|
|
6599
|
+
}
|
|
6600
|
+
}, [onDragStart]);
|
|
6601
|
+
const handleDrop = React14__namespace.useCallback((newStartDate) => {
|
|
6602
|
+
if (!draggedEvent) return;
|
|
6603
|
+
const snappedDate = snapToInterval(newStartDate, snapMinutes);
|
|
6604
|
+
const { startDate, endDate } = calculateDropDates(draggedEvent, snappedDate);
|
|
6605
|
+
const updatedEvent = {
|
|
6606
|
+
...draggedEvent,
|
|
6607
|
+
startDate,
|
|
6608
|
+
endDate
|
|
6609
|
+
};
|
|
6610
|
+
updateEvent(updatedEvent);
|
|
6611
|
+
onDragEnd?.(updatedEvent, new Date(startDate), new Date(endDate));
|
|
6612
|
+
setDraggedEvent(null);
|
|
6613
|
+
}, [draggedEvent, snapMinutes, updateEvent, onDragEnd, setDraggedEvent]);
|
|
6614
|
+
const contextValue = React14__namespace.useMemo(
|
|
6615
|
+
() => ({
|
|
6616
|
+
draggedEvent,
|
|
6617
|
+
setDraggedEvent,
|
|
6618
|
+
isDragging
|
|
6619
|
+
}),
|
|
6620
|
+
[draggedEvent, setDraggedEvent, isDragging]
|
|
6621
|
+
);
|
|
6622
|
+
return /* @__PURE__ */ jsxRuntime.jsx(DragContext.Provider, { value: contextValue, children: /* @__PURE__ */ jsxRuntime.jsx(DragDropHandler, { onDrop: handleDrop, children }) });
|
|
6623
|
+
}
|
|
6624
|
+
function useDrag() {
|
|
6625
|
+
const context = React14__namespace.useContext(DragContext);
|
|
6626
|
+
if (!context) {
|
|
6627
|
+
throw new Error("useDrag must be used within a DragProvider");
|
|
6628
|
+
}
|
|
6629
|
+
return context;
|
|
6630
|
+
}
|
|
6631
|
+
function DragDropHandler({ children, onDrop }) {
|
|
6632
|
+
return /* @__PURE__ */ jsxRuntime.jsx(jsxRuntime.Fragment, { children });
|
|
6633
|
+
}
|
|
6634
|
+
function DraggableEvent({
|
|
6635
|
+
event,
|
|
6636
|
+
children,
|
|
6637
|
+
disabled = false
|
|
6638
|
+
}) {
|
|
6639
|
+
const { setDraggedEvent, isDragging, draggedEvent } = useDrag();
|
|
6640
|
+
const isDragged = draggedEvent?.id === event.id;
|
|
6641
|
+
const handleDragStart = (e) => {
|
|
6642
|
+
if (disabled) return;
|
|
6643
|
+
e.dataTransfer.effectAllowed = "move";
|
|
6644
|
+
e.dataTransfer.setData("text/plain", event.id);
|
|
6645
|
+
setDraggedEvent(event);
|
|
6646
|
+
};
|
|
6647
|
+
const handleDragEnd = () => {
|
|
6648
|
+
setDraggedEvent(null);
|
|
6649
|
+
};
|
|
6650
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
6651
|
+
"div",
|
|
6652
|
+
{
|
|
6653
|
+
draggable: !disabled,
|
|
6654
|
+
onDragStart: handleDragStart,
|
|
6655
|
+
onDragEnd: handleDragEnd,
|
|
6656
|
+
className: isDragged ? "opacity-50" : "",
|
|
6657
|
+
style: { cursor: disabled ? "default" : "grab" },
|
|
6658
|
+
children
|
|
6659
|
+
}
|
|
6660
|
+
);
|
|
6661
|
+
}
|
|
6662
|
+
function DroppableZone({
|
|
6663
|
+
date,
|
|
6664
|
+
children,
|
|
6665
|
+
onDrop,
|
|
6666
|
+
className
|
|
6667
|
+
}) {
|
|
6668
|
+
const { draggedEvent, setDraggedEvent } = useDrag();
|
|
6669
|
+
const { updateEvent } = useEventCalendar();
|
|
6670
|
+
const [isOver, setIsOver] = React14__namespace.useState(false);
|
|
6671
|
+
const handleDragOver = (e) => {
|
|
6672
|
+
e.preventDefault();
|
|
6673
|
+
e.dataTransfer.dropEffect = "move";
|
|
6674
|
+
setIsOver(true);
|
|
6675
|
+
};
|
|
6676
|
+
const handleDragLeave = () => {
|
|
6677
|
+
setIsOver(false);
|
|
6678
|
+
};
|
|
6679
|
+
const handleDrop = (e) => {
|
|
6680
|
+
e.preventDefault();
|
|
6681
|
+
setIsOver(false);
|
|
6682
|
+
if (!draggedEvent) return;
|
|
6683
|
+
const { startDate, endDate } = calculateDropDates(draggedEvent, date);
|
|
6684
|
+
const updatedEvent = {
|
|
6685
|
+
...draggedEvent,
|
|
6686
|
+
startDate,
|
|
6687
|
+
endDate
|
|
6688
|
+
};
|
|
6689
|
+
updateEvent(updatedEvent);
|
|
6690
|
+
onDrop?.(updatedEvent, date);
|
|
6691
|
+
setDraggedEvent(null);
|
|
6692
|
+
};
|
|
6693
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
6694
|
+
"div",
|
|
6695
|
+
{
|
|
6696
|
+
onDragOver: handleDragOver,
|
|
6697
|
+
onDragLeave: handleDragLeave,
|
|
6698
|
+
onDrop: handleDrop,
|
|
6699
|
+
className,
|
|
6700
|
+
"data-drag-over": isOver,
|
|
6701
|
+
children
|
|
6702
|
+
}
|
|
6703
|
+
);
|
|
6704
|
+
}
|
|
6705
|
+
function useDroppable({ date, hour, minute = 0, onDrop }) {
|
|
6706
|
+
const { draggedEvent, setDraggedEvent } = useDrag();
|
|
6707
|
+
const { updateEvent } = useEventCalendar();
|
|
6708
|
+
const [isOver, setIsOver] = React14__namespace.useState(false);
|
|
6709
|
+
const dropTargetDate = React14__namespace.useMemo(() => {
|
|
6710
|
+
const targetDate = new Date(date);
|
|
6711
|
+
if (hour !== void 0) {
|
|
6712
|
+
targetDate.setHours(hour, minute, 0, 0);
|
|
6713
|
+
}
|
|
6714
|
+
return targetDate;
|
|
6715
|
+
}, [date, hour, minute]);
|
|
6716
|
+
const handleDragOver = React14__namespace.useCallback((e) => {
|
|
6717
|
+
e.preventDefault();
|
|
6718
|
+
e.dataTransfer.dropEffect = "move";
|
|
6719
|
+
if (!isOver) setIsOver(true);
|
|
6720
|
+
}, [isOver]);
|
|
6721
|
+
const handleDragLeave = React14__namespace.useCallback(() => {
|
|
6722
|
+
setIsOver(false);
|
|
6723
|
+
}, []);
|
|
6724
|
+
const handleDrop = React14__namespace.useCallback((e) => {
|
|
6725
|
+
e.preventDefault();
|
|
6726
|
+
setIsOver(false);
|
|
6727
|
+
if (!draggedEvent) return;
|
|
6728
|
+
const { startDate, endDate } = calculateDropDates(draggedEvent, dropTargetDate);
|
|
6729
|
+
const updatedEvent = {
|
|
6730
|
+
...draggedEvent,
|
|
6731
|
+
startDate,
|
|
6732
|
+
endDate
|
|
6733
|
+
};
|
|
6734
|
+
updateEvent(updatedEvent);
|
|
6735
|
+
onDrop?.(updatedEvent, dropTargetDate);
|
|
6736
|
+
setDraggedEvent(null);
|
|
6737
|
+
}, [draggedEvent, dropTargetDate, updateEvent, onDrop, setDraggedEvent]);
|
|
6738
|
+
return {
|
|
6739
|
+
isOver,
|
|
6740
|
+
dropProps: {
|
|
6741
|
+
onDragOver: handleDragOver,
|
|
6742
|
+
onDragLeave: handleDragLeave,
|
|
6743
|
+
onDrop: handleDrop,
|
|
6744
|
+
"data-drag-over": isOver
|
|
6745
|
+
}
|
|
6746
|
+
};
|
|
6747
|
+
}
|
|
6748
|
+
function useDraggable(event, disabled = false) {
|
|
6749
|
+
const { setDraggedEvent, draggedEvent } = useDrag();
|
|
6750
|
+
const isDragged = draggedEvent?.id === event.id;
|
|
6751
|
+
const handleDragStart = React14__namespace.useCallback((e) => {
|
|
6752
|
+
if (disabled) return;
|
|
6753
|
+
e.dataTransfer.effectAllowed = "move";
|
|
6754
|
+
e.dataTransfer.setData("text/plain", event.id);
|
|
6755
|
+
setDraggedEvent(event);
|
|
6756
|
+
}, [disabled, event, setDraggedEvent]);
|
|
6757
|
+
const handleDragEnd = React14__namespace.useCallback(() => {
|
|
6758
|
+
setDraggedEvent(null);
|
|
6759
|
+
}, [setDraggedEvent]);
|
|
6760
|
+
return {
|
|
6761
|
+
isDragged,
|
|
6762
|
+
dragProps: {
|
|
6763
|
+
draggable: !disabled,
|
|
6764
|
+
onDragStart: handleDragStart,
|
|
6765
|
+
onDragEnd: handleDragEnd,
|
|
6766
|
+
style: { cursor: disabled ? "default" : "grab" }
|
|
6767
|
+
}
|
|
6768
|
+
};
|
|
6769
|
+
}
|
|
6770
|
+
var WEEK_DAYS = ["Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat"];
|
|
6771
|
+
function DraggableEventWrapper({
|
|
6772
|
+
event,
|
|
6773
|
+
children
|
|
6774
|
+
}) {
|
|
6775
|
+
const { isDragged, dragProps } = useDraggable(event);
|
|
6776
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
6777
|
+
"div",
|
|
6778
|
+
{
|
|
6779
|
+
...dragProps,
|
|
6780
|
+
className: cn(
|
|
6781
|
+
"transition-opacity",
|
|
6782
|
+
isDragged && "opacity-50"
|
|
6783
|
+
),
|
|
6784
|
+
children
|
|
6785
|
+
}
|
|
6786
|
+
);
|
|
6787
|
+
}
|
|
6788
|
+
function MonthView({
|
|
6789
|
+
className,
|
|
6790
|
+
maxEventsPerDay = 3,
|
|
6791
|
+
weekStartsOn = 0,
|
|
6792
|
+
onEventClick,
|
|
6793
|
+
onDateClick,
|
|
6794
|
+
onMoreClick
|
|
6795
|
+
}) {
|
|
6796
|
+
const { selectedDate, badgeVariant, setSelectedDate, setView } = useEventCalendar();
|
|
6797
|
+
const filteredEvents = useFilteredEvents();
|
|
6798
|
+
const { singleDayEvents, multiDayEvents } = React14__namespace.useMemo(
|
|
6799
|
+
() => splitEventsByDuration(filteredEvents),
|
|
6800
|
+
[filteredEvents]
|
|
6801
|
+
);
|
|
6802
|
+
const cells = React14__namespace.useMemo(
|
|
6803
|
+
() => getCalendarCells(selectedDate),
|
|
6804
|
+
[selectedDate]
|
|
6805
|
+
);
|
|
6806
|
+
const eventPositions = React14__namespace.useMemo(
|
|
6807
|
+
() => calculateMonthEventPositions(multiDayEvents, singleDayEvents, selectedDate),
|
|
6808
|
+
[multiDayEvents, singleDayEvents, selectedDate]
|
|
6809
|
+
);
|
|
6810
|
+
const allEvents = [...multiDayEvents, ...singleDayEvents];
|
|
6811
|
+
const handleDateClick = (date) => {
|
|
6812
|
+
setSelectedDate(date);
|
|
6813
|
+
setView("day");
|
|
6814
|
+
onDateClick?.(date);
|
|
6815
|
+
};
|
|
6816
|
+
const handleMoreClick = (date, events) => {
|
|
6817
|
+
setSelectedDate(date);
|
|
6818
|
+
setView("day");
|
|
6819
|
+
onMoreClick?.(date, events);
|
|
6820
|
+
};
|
|
6821
|
+
return /* @__PURE__ */ jsxRuntime.jsxs("div", { className: cn("", className), children: [
|
|
6822
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "grid grid-cols-7 divide-x divide-border/50", children: WEEK_DAYS.map((day) => /* @__PURE__ */ jsxRuntime.jsx(
|
|
6823
|
+
"div",
|
|
6824
|
+
{
|
|
6825
|
+
className: "flex items-center justify-center py-2",
|
|
6826
|
+
children: /* @__PURE__ */ jsxRuntime.jsx("span", { className: "text-xs font-medium text-muted-foreground", children: day })
|
|
6827
|
+
},
|
|
6828
|
+
day
|
|
6829
|
+
)) }),
|
|
6830
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "grid grid-cols-7 overflow-hidden", children: cells.map((cell) => /* @__PURE__ */ jsxRuntime.jsx(
|
|
6831
|
+
DayCell,
|
|
6832
|
+
{
|
|
6833
|
+
cell,
|
|
6834
|
+
events: allEvents,
|
|
6835
|
+
eventPositions,
|
|
6836
|
+
selectedDate,
|
|
6837
|
+
badgeVariant,
|
|
6838
|
+
maxEvents: maxEventsPerDay,
|
|
6839
|
+
onDateClick: handleDateClick,
|
|
6840
|
+
onEventClick,
|
|
6841
|
+
onMoreClick: handleMoreClick
|
|
6842
|
+
},
|
|
6843
|
+
cell.date.toISOString()
|
|
6844
|
+
)) })
|
|
6845
|
+
] });
|
|
6846
|
+
}
|
|
6847
|
+
function DayCell({
|
|
6848
|
+
cell,
|
|
6849
|
+
events,
|
|
6850
|
+
eventPositions,
|
|
6851
|
+
selectedDate,
|
|
6852
|
+
badgeVariant,
|
|
6853
|
+
maxEvents,
|
|
6854
|
+
onDateClick,
|
|
6855
|
+
onEventClick,
|
|
6856
|
+
onMoreClick
|
|
6857
|
+
}) {
|
|
6858
|
+
const { date, currentMonth } = cell;
|
|
6859
|
+
const isCurrentDay = dateFns.isToday(date);
|
|
6860
|
+
const isSelectedDay = dateFns.isSameDay(date, selectedDate);
|
|
6861
|
+
const { isOver, dropProps } = useDroppable({ date });
|
|
6862
|
+
const cellEvents = getMonthCellEvents(date, events, eventPositions);
|
|
6863
|
+
const positionedEvents = cellEvents.filter((e) => e.position !== -1);
|
|
6864
|
+
const hiddenEvents = cellEvents.filter((e) => e.position === -1);
|
|
6865
|
+
const slots = [null, null, null];
|
|
6866
|
+
positionedEvents.forEach((event) => {
|
|
6867
|
+
if (event.position >= 0 && event.position < 3) {
|
|
6868
|
+
slots[event.position] = event;
|
|
6869
|
+
}
|
|
6870
|
+
});
|
|
6871
|
+
const hiddenCount = hiddenEvents.length + positionedEvents.filter((e) => e.position >= 3).length;
|
|
6872
|
+
const isEventStart = (event) => dateFns.isSameDay(dateFns.parseISO(event.startDate), date);
|
|
6873
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(
|
|
6874
|
+
"div",
|
|
6875
|
+
{
|
|
6876
|
+
...dropProps,
|
|
6877
|
+
className: cn(
|
|
6878
|
+
"relative min-h-[120px] border-b border-r border-border/50 p-1 transition-colors",
|
|
6879
|
+
!currentMonth && "bg-muted/30",
|
|
6880
|
+
isOver && "bg-primary/10 ring-2 ring-primary/50 ring-inset"
|
|
6881
|
+
),
|
|
6882
|
+
children: [
|
|
6883
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
6884
|
+
"button",
|
|
6885
|
+
{
|
|
6886
|
+
type: "button",
|
|
6887
|
+
onClick: () => onDateClick(date),
|
|
6888
|
+
className: cn(
|
|
6889
|
+
"mb-1 flex size-7 items-center justify-center text-sm transition-colors",
|
|
6890
|
+
"hover:bg-muted rounded-sm",
|
|
6891
|
+
isCurrentDay && "bg-primary text-primary-foreground hover:bg-primary/90 rounded-sm",
|
|
6892
|
+
isSelectedDay && !isCurrentDay && "bg-muted font-semibold rounded-sm",
|
|
6893
|
+
!currentMonth && "text-muted-foreground"
|
|
6894
|
+
),
|
|
6895
|
+
children: cell.day
|
|
6896
|
+
}
|
|
6897
|
+
),
|
|
6898
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "space-y-0.5", children: [
|
|
6899
|
+
slots.map((event, index) => {
|
|
6900
|
+
if (!event) {
|
|
6901
|
+
return /* @__PURE__ */ jsxRuntime.jsx("div", { className: "h-5" }, `empty-${index}`);
|
|
6902
|
+
}
|
|
6903
|
+
const showTitle = isEventStart(event) || dateFns.startOfDay(date).getDay() === 0;
|
|
6904
|
+
return /* @__PURE__ */ jsxRuntime.jsx(DraggableEventWrapper, { event, children: /* @__PURE__ */ jsxRuntime.jsx(
|
|
6905
|
+
EventBadge,
|
|
6906
|
+
{
|
|
6907
|
+
event,
|
|
6908
|
+
variant: badgeVariant,
|
|
6909
|
+
compact: true,
|
|
6910
|
+
showTime: showTitle,
|
|
6911
|
+
onClick: (e) => onEventClick?.(e),
|
|
6912
|
+
className: cn(
|
|
6913
|
+
"w-full",
|
|
6914
|
+
// If not showing title, make it appear as a continuation
|
|
6915
|
+
!showTitle && "rounded-l-none border-l-0"
|
|
6916
|
+
)
|
|
6917
|
+
}
|
|
6918
|
+
) }, event.id);
|
|
6919
|
+
}),
|
|
6920
|
+
hiddenCount > 0 && /* @__PURE__ */ jsxRuntime.jsx(
|
|
6921
|
+
MoreEvents,
|
|
6922
|
+
{
|
|
6923
|
+
count: hiddenCount,
|
|
6924
|
+
onClick: () => onMoreClick(date, cellEvents)
|
|
6925
|
+
}
|
|
6926
|
+
)
|
|
6927
|
+
] })
|
|
6928
|
+
]
|
|
6929
|
+
}
|
|
6930
|
+
);
|
|
6931
|
+
}
|
|
6932
|
+
function DraggableEventWrapper2({
|
|
6933
|
+
event,
|
|
6934
|
+
children,
|
|
6935
|
+
className,
|
|
6936
|
+
style
|
|
6937
|
+
}) {
|
|
6938
|
+
const { isDragged, dragProps } = useDraggable(event);
|
|
6939
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
6940
|
+
"div",
|
|
6941
|
+
{
|
|
6942
|
+
...dragProps,
|
|
6943
|
+
className: cn(
|
|
6944
|
+
className,
|
|
6945
|
+
"transition-opacity",
|
|
6946
|
+
isDragged && "opacity-50"
|
|
6947
|
+
),
|
|
6948
|
+
style,
|
|
6949
|
+
children
|
|
6950
|
+
}
|
|
6951
|
+
);
|
|
6952
|
+
}
|
|
6953
|
+
function DroppableTimeSlot({
|
|
6954
|
+
date,
|
|
6955
|
+
hour,
|
|
6956
|
+
minute,
|
|
6957
|
+
className,
|
|
6958
|
+
onClick
|
|
6959
|
+
}) {
|
|
6960
|
+
const { isOver, dropProps } = useDroppable({ date, hour, minute });
|
|
6961
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
6962
|
+
"div",
|
|
6963
|
+
{
|
|
6964
|
+
...dropProps,
|
|
6965
|
+
onClick,
|
|
6966
|
+
className: cn(
|
|
6967
|
+
className,
|
|
6968
|
+
"cursor-pointer transition-colors hover:bg-accent",
|
|
6969
|
+
isOver && "bg-primary/20"
|
|
6970
|
+
)
|
|
6971
|
+
}
|
|
6972
|
+
);
|
|
6973
|
+
}
|
|
6974
|
+
function WeekView({
|
|
6975
|
+
className,
|
|
6976
|
+
weekStartsOn = 0,
|
|
6977
|
+
onEventClick,
|
|
6978
|
+
onDateClick,
|
|
6979
|
+
onTimeClick
|
|
6980
|
+
}) {
|
|
6981
|
+
const {
|
|
6982
|
+
selectedDate,
|
|
6983
|
+
badgeVariant,
|
|
6984
|
+
workingHours,
|
|
6985
|
+
visibleHours
|
|
6986
|
+
} = useEventCalendar();
|
|
6987
|
+
const filteredEvents = useFilteredEvents();
|
|
6988
|
+
const { singleDayEvents, multiDayEvents } = React14__namespace.useMemo(
|
|
6989
|
+
() => splitEventsByDuration(filteredEvents),
|
|
6990
|
+
[filteredEvents]
|
|
6991
|
+
);
|
|
6992
|
+
const { hours, earliestEventHour, latestEventHour } = getVisibleHours(
|
|
6993
|
+
visibleHours,
|
|
6994
|
+
singleDayEvents
|
|
6995
|
+
);
|
|
6996
|
+
const weekStart = dateFns.startOfWeek(selectedDate, { weekStartsOn });
|
|
6997
|
+
const weekDays = Array.from({ length: 7 }, (_, i) => dateFns.addDays(weekStart, i));
|
|
6998
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
|
|
6999
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex flex-col items-center justify-center border-b py-4 text-sm text-muted-foreground sm:hidden", children: [
|
|
7000
|
+
/* @__PURE__ */ jsxRuntime.jsx("p", { children: "Weekly view is not available on smaller devices." }),
|
|
7001
|
+
/* @__PURE__ */ jsxRuntime.jsx("p", { children: "Please switch to daily or monthly view." })
|
|
7002
|
+
] }),
|
|
7003
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: cn("hidden flex-col sm:flex", className), children: [
|
|
7004
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
7005
|
+
WeekViewMultiDayEventsRow,
|
|
7006
|
+
{
|
|
7007
|
+
selectedDate,
|
|
7008
|
+
multiDayEvents
|
|
7009
|
+
}
|
|
7010
|
+
),
|
|
7011
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "relative z-20 flex border-b border-border/50", children: [
|
|
7012
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "w-18" }),
|
|
7013
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "grid flex-1 grid-cols-7 divide-x divide-border/50 border-l border-border/50", children: weekDays.map((day, index) => /* @__PURE__ */ jsxRuntime.jsxs(
|
|
7014
|
+
"span",
|
|
7015
|
+
{
|
|
7016
|
+
className: "py-2 text-center text-xs font-medium text-muted-foreground",
|
|
7017
|
+
children: [
|
|
7018
|
+
dateFns.format(day, "EE"),
|
|
7019
|
+
" ",
|
|
7020
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "ml-1 font-semibold text-foreground", children: dateFns.format(day, "d") })
|
|
7021
|
+
]
|
|
7022
|
+
},
|
|
7023
|
+
index
|
|
7024
|
+
)) })
|
|
7025
|
+
] }),
|
|
7026
|
+
/* @__PURE__ */ jsxRuntime.jsx(ScrollArea, { className: "h-[736px]", type: "always", children: /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex overflow-hidden", children: [
|
|
7027
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "relative w-18", children: hours.map((hour, index) => /* @__PURE__ */ jsxRuntime.jsx("div", { className: "relative", style: { height: "96px" }, children: /* @__PURE__ */ jsxRuntime.jsx("div", { className: "absolute -top-3 right-2 flex h-6 items-center", children: index !== 0 && /* @__PURE__ */ jsxRuntime.jsx("span", { className: "text-xs text-muted-foreground", children: dateFns.format((/* @__PURE__ */ new Date()).setHours(hour, 0, 0, 0), "hh a") }) }) }, hour)) }),
|
|
7028
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "relative flex-1 border-l border-border/50", children: [
|
|
7029
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "grid grid-cols-7 divide-x divide-border/50", children: weekDays.map((day, dayIndex) => {
|
|
7030
|
+
const dayEvents = singleDayEvents.filter(
|
|
7031
|
+
(event) => dateFns.isSameDay(dateFns.parseISO(event.startDate), day) || dateFns.isSameDay(dateFns.parseISO(event.endDate), day)
|
|
7032
|
+
);
|
|
7033
|
+
const groupedEvents = groupEvents(dayEvents);
|
|
7034
|
+
return /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "relative", children: [
|
|
7035
|
+
hours.map((hour, index) => {
|
|
7036
|
+
const isDisabled = !isWorkingHour(day, hour, workingHours);
|
|
7037
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(
|
|
7038
|
+
"div",
|
|
7039
|
+
{
|
|
7040
|
+
className: cn(
|
|
7041
|
+
"relative",
|
|
7042
|
+
isDisabled && "bg-[repeating-linear-gradient(45deg,transparent,transparent_5px,rgba(0,0,0,0.04)_5px,rgba(0,0,0,0.04)_10px)] dark:bg-[repeating-linear-gradient(45deg,transparent,transparent_5px,rgba(255,255,255,0.04)_5px,rgba(255,255,255,0.04)_10px)]"
|
|
7043
|
+
),
|
|
7044
|
+
style: { height: "96px" },
|
|
7045
|
+
children: [
|
|
7046
|
+
index !== 0 && /* @__PURE__ */ jsxRuntime.jsx("div", { className: "pointer-events-none absolute inset-x-0 top-0 border-b border-border/40" }),
|
|
7047
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
7048
|
+
DroppableTimeSlot,
|
|
7049
|
+
{
|
|
7050
|
+
date: day,
|
|
7051
|
+
hour,
|
|
7052
|
+
minute: 0,
|
|
7053
|
+
className: "absolute inset-x-0 top-0 h-[24px]",
|
|
7054
|
+
onClick: () => onTimeClick?.(day, hour, 0)
|
|
7055
|
+
}
|
|
7056
|
+
),
|
|
7057
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
7058
|
+
DroppableTimeSlot,
|
|
7059
|
+
{
|
|
7060
|
+
date: day,
|
|
7061
|
+
hour,
|
|
7062
|
+
minute: 15,
|
|
7063
|
+
className: "absolute inset-x-0 top-[24px] h-[24px]",
|
|
7064
|
+
onClick: () => onTimeClick?.(day, hour, 15)
|
|
7065
|
+
}
|
|
7066
|
+
),
|
|
7067
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "pointer-events-none absolute inset-x-0 top-1/2 border-b border-dashed border-border/30" }),
|
|
7068
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
7069
|
+
DroppableTimeSlot,
|
|
7070
|
+
{
|
|
7071
|
+
date: day,
|
|
7072
|
+
hour,
|
|
7073
|
+
minute: 30,
|
|
7074
|
+
className: "absolute inset-x-0 top-[48px] h-[24px]",
|
|
7075
|
+
onClick: () => onTimeClick?.(day, hour, 30)
|
|
7076
|
+
}
|
|
7077
|
+
),
|
|
7078
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
7079
|
+
DroppableTimeSlot,
|
|
7080
|
+
{
|
|
7081
|
+
date: day,
|
|
7082
|
+
hour,
|
|
7083
|
+
minute: 45,
|
|
7084
|
+
className: "absolute inset-x-0 top-[72px] h-[24px]",
|
|
7085
|
+
onClick: () => onTimeClick?.(day, hour, 45)
|
|
7086
|
+
}
|
|
7087
|
+
)
|
|
7088
|
+
]
|
|
7089
|
+
},
|
|
7090
|
+
hour
|
|
7091
|
+
);
|
|
7092
|
+
}),
|
|
7093
|
+
groupedEvents.map(
|
|
7094
|
+
(group, groupIndex) => group.map((event) => {
|
|
7095
|
+
let style = getEventBlockStyle(
|
|
7096
|
+
event,
|
|
7097
|
+
day,
|
|
7098
|
+
groupIndex,
|
|
7099
|
+
groupedEvents.length,
|
|
7100
|
+
{ from: earliestEventHour}
|
|
7101
|
+
);
|
|
7102
|
+
const hasOverlap = groupedEvents.some(
|
|
7103
|
+
(otherGroup, otherIndex) => otherIndex !== groupIndex && otherGroup.some(
|
|
7104
|
+
(otherEvent) => dateFns.areIntervalsOverlapping(
|
|
7105
|
+
{
|
|
7106
|
+
start: dateFns.parseISO(event.startDate),
|
|
7107
|
+
end: dateFns.parseISO(event.endDate)
|
|
7108
|
+
},
|
|
7109
|
+
{
|
|
7110
|
+
start: dateFns.parseISO(otherEvent.startDate),
|
|
7111
|
+
end: dateFns.parseISO(otherEvent.endDate)
|
|
7112
|
+
}
|
|
7113
|
+
)
|
|
7114
|
+
)
|
|
7115
|
+
);
|
|
7116
|
+
if (!hasOverlap) {
|
|
7117
|
+
style = { ...style, width: "100%", left: "0%" };
|
|
7118
|
+
}
|
|
7119
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
7120
|
+
DraggableEventWrapper2,
|
|
7121
|
+
{
|
|
7122
|
+
event,
|
|
7123
|
+
className: "absolute px-0.5 py-0.5",
|
|
7124
|
+
style,
|
|
7125
|
+
children: /* @__PURE__ */ jsxRuntime.jsx(
|
|
7126
|
+
EventBadge,
|
|
7127
|
+
{
|
|
7128
|
+
event,
|
|
7129
|
+
variant: badgeVariant,
|
|
7130
|
+
showTime: true,
|
|
7131
|
+
onClick: (e) => onEventClick?.(e),
|
|
7132
|
+
className: "h-full w-full"
|
|
7133
|
+
}
|
|
7134
|
+
)
|
|
7135
|
+
},
|
|
7136
|
+
event.id
|
|
7137
|
+
);
|
|
7138
|
+
})
|
|
7139
|
+
)
|
|
7140
|
+
] }, dayIndex);
|
|
7141
|
+
}) }),
|
|
7142
|
+
weekDays.some((day) => dateFns.isToday(day)) && /* @__PURE__ */ jsxRuntime.jsx(
|
|
7143
|
+
CalendarTimeline,
|
|
7144
|
+
{
|
|
7145
|
+
firstVisibleHour: earliestEventHour,
|
|
7146
|
+
lastVisibleHour: latestEventHour
|
|
7147
|
+
}
|
|
7148
|
+
)
|
|
7149
|
+
] })
|
|
7150
|
+
] }) })
|
|
7151
|
+
] })
|
|
7152
|
+
] });
|
|
7153
|
+
}
|
|
7154
|
+
function WeekViewMultiDayEventsRow({
|
|
7155
|
+
selectedDate,
|
|
7156
|
+
multiDayEvents
|
|
7157
|
+
}) {
|
|
7158
|
+
const { badgeVariant } = useEventCalendar();
|
|
7159
|
+
if (multiDayEvents.length === 0) return null;
|
|
7160
|
+
const weekStart = dateFns.startOfWeek(selectedDate);
|
|
7161
|
+
const weekDays = Array.from({ length: 7 }, (_, i) => dateFns.addDays(weekStart, i));
|
|
7162
|
+
return /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "hidden border-b sm:flex", children: [
|
|
7163
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "w-18 shrink-0" }),
|
|
7164
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "grid flex-1 grid-cols-7 divide-x border-l", children: weekDays.map((day, index) => {
|
|
7165
|
+
const dayMultiEvents = multiDayEvents.filter((event) => {
|
|
7166
|
+
const start = dateFns.parseISO(event.startDate);
|
|
7167
|
+
const end = dateFns.parseISO(event.endDate);
|
|
7168
|
+
return day >= start && day <= end;
|
|
7169
|
+
});
|
|
7170
|
+
return /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "min-h-[32px] space-y-1 p-1", children: [
|
|
7171
|
+
dayMultiEvents.slice(0, 2).map((event) => /* @__PURE__ */ jsxRuntime.jsx(
|
|
7172
|
+
EventBadge,
|
|
7173
|
+
{
|
|
7174
|
+
event,
|
|
7175
|
+
variant: badgeVariant,
|
|
7176
|
+
compact: true,
|
|
7177
|
+
className: "w-full"
|
|
7178
|
+
},
|
|
7179
|
+
event.id
|
|
7180
|
+
)),
|
|
7181
|
+
dayMultiEvents.length > 2 && /* @__PURE__ */ jsxRuntime.jsxs("p", { className: "text-xs text-muted-foreground text-center", children: [
|
|
7182
|
+
"+",
|
|
7183
|
+
dayMultiEvents.length - 2,
|
|
7184
|
+
" more"
|
|
7185
|
+
] })
|
|
7186
|
+
] }, index);
|
|
7187
|
+
}) })
|
|
7188
|
+
] });
|
|
7189
|
+
}
|
|
7190
|
+
function CalendarTimeline({
|
|
7191
|
+
firstVisibleHour,
|
|
7192
|
+
lastVisibleHour
|
|
7193
|
+
}) {
|
|
7194
|
+
const [currentTime, setCurrentTime] = React14__namespace.useState(/* @__PURE__ */ new Date());
|
|
7195
|
+
React14__namespace.useEffect(() => {
|
|
7196
|
+
const interval = setInterval(() => {
|
|
7197
|
+
setCurrentTime(/* @__PURE__ */ new Date());
|
|
7198
|
+
}, 6e4);
|
|
7199
|
+
return () => clearInterval(interval);
|
|
7200
|
+
}, []);
|
|
7201
|
+
const currentHour = currentTime.getHours();
|
|
7202
|
+
const currentMinute = currentTime.getMinutes();
|
|
7203
|
+
if (currentHour < firstVisibleHour || currentHour >= lastVisibleHour) {
|
|
7204
|
+
return null;
|
|
7205
|
+
}
|
|
7206
|
+
const minutesSinceStart = (currentHour - firstVisibleHour) * 60 + currentMinute;
|
|
7207
|
+
const totalMinutes = (lastVisibleHour - firstVisibleHour) * 60;
|
|
7208
|
+
const topPercent = minutesSinceStart / totalMinutes * 100;
|
|
7209
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(
|
|
7210
|
+
"div",
|
|
7211
|
+
{
|
|
7212
|
+
className: "pointer-events-none absolute inset-x-0 z-30 flex items-center",
|
|
7213
|
+
style: { top: `${topPercent}%` },
|
|
7214
|
+
children: [
|
|
7215
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "size-3 -translate-x-1/2 rounded-full bg-red-500" }),
|
|
7216
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "h-0.5 flex-1 bg-red-500" })
|
|
7217
|
+
]
|
|
7218
|
+
}
|
|
7219
|
+
);
|
|
7220
|
+
}
|
|
7221
|
+
function DraggableEventWrapper3({
|
|
7222
|
+
event,
|
|
7223
|
+
children,
|
|
7224
|
+
className,
|
|
7225
|
+
style
|
|
7226
|
+
}) {
|
|
7227
|
+
const { isDragged, dragProps } = useDraggable(event);
|
|
7228
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
7229
|
+
"div",
|
|
7230
|
+
{
|
|
7231
|
+
...dragProps,
|
|
7232
|
+
className: cn(
|
|
7233
|
+
className,
|
|
7234
|
+
"transition-opacity",
|
|
7235
|
+
isDragged && "opacity-50"
|
|
7236
|
+
),
|
|
7237
|
+
style,
|
|
7238
|
+
children
|
|
7239
|
+
}
|
|
7240
|
+
);
|
|
7241
|
+
}
|
|
7242
|
+
function DroppableTimeSlot2({
|
|
7243
|
+
date,
|
|
7244
|
+
hour,
|
|
7245
|
+
minute,
|
|
7246
|
+
className,
|
|
7247
|
+
onClick
|
|
7248
|
+
}) {
|
|
7249
|
+
const { isOver, dropProps } = useDroppable({ date, hour, minute });
|
|
7250
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
7251
|
+
"div",
|
|
7252
|
+
{
|
|
7253
|
+
...dropProps,
|
|
7254
|
+
onClick,
|
|
7255
|
+
className: cn(
|
|
7256
|
+
className,
|
|
7257
|
+
"cursor-pointer transition-colors hover:bg-accent",
|
|
7258
|
+
isOver && "bg-primary/20"
|
|
7259
|
+
)
|
|
7260
|
+
}
|
|
7261
|
+
);
|
|
7262
|
+
}
|
|
7263
|
+
function DayView({
|
|
7264
|
+
className,
|
|
7265
|
+
showSidebar = true,
|
|
7266
|
+
onEventClick,
|
|
7267
|
+
onTimeClick
|
|
7268
|
+
}) {
|
|
7269
|
+
const {
|
|
7270
|
+
selectedDate,
|
|
7271
|
+
setSelectedDate,
|
|
7272
|
+
badgeVariant,
|
|
7273
|
+
users,
|
|
7274
|
+
workingHours,
|
|
7275
|
+
visibleHours
|
|
7276
|
+
} = useEventCalendar();
|
|
7277
|
+
const filteredEvents = useFilteredEvents();
|
|
7278
|
+
const { singleDayEvents, multiDayEvents } = React14__namespace.useMemo(
|
|
7279
|
+
() => splitEventsByDuration(filteredEvents),
|
|
7280
|
+
[filteredEvents]
|
|
7281
|
+
);
|
|
7282
|
+
const { hours, earliestEventHour, latestEventHour } = getVisibleHours(
|
|
7283
|
+
visibleHours,
|
|
7284
|
+
singleDayEvents
|
|
7285
|
+
);
|
|
7286
|
+
const currentEvents = React14__namespace.useMemo(() => {
|
|
7287
|
+
if (!dateFns.isToday(selectedDate)) return [];
|
|
7288
|
+
return getCurrentEvents(singleDayEvents);
|
|
7289
|
+
}, [singleDayEvents, selectedDate]);
|
|
7290
|
+
const dayEvents = singleDayEvents.filter((event) => {
|
|
7291
|
+
const eventDate = dateFns.parseISO(event.startDate);
|
|
7292
|
+
return eventDate.getDate() === selectedDate.getDate() && eventDate.getMonth() === selectedDate.getMonth() && eventDate.getFullYear() === selectedDate.getFullYear();
|
|
7293
|
+
});
|
|
7294
|
+
const groupedEvents = groupEvents(dayEvents);
|
|
7295
|
+
const handleDateSelect = (date) => {
|
|
7296
|
+
if (date) {
|
|
7297
|
+
setSelectedDate(date);
|
|
7298
|
+
}
|
|
7299
|
+
};
|
|
7300
|
+
return /* @__PURE__ */ jsxRuntime.jsxs("div", { className: cn("flex", className), children: [
|
|
7301
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex flex-1 flex-col", children: [
|
|
7302
|
+
multiDayEvents.length > 0 && /* @__PURE__ */ jsxRuntime.jsx(
|
|
7303
|
+
DayViewMultiDayEventsRow,
|
|
7304
|
+
{
|
|
7305
|
+
selectedDate,
|
|
7306
|
+
multiDayEvents
|
|
7307
|
+
}
|
|
7308
|
+
),
|
|
7309
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "relative z-20 flex border-b border-border/50", children: [
|
|
7310
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "w-18" }),
|
|
7311
|
+
/* @__PURE__ */ jsxRuntime.jsxs("span", { className: "flex-1 border-l border-border/50 py-2 text-center text-xs font-medium text-muted-foreground", children: [
|
|
7312
|
+
dateFns.format(selectedDate, "EE"),
|
|
7313
|
+
" ",
|
|
7314
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "font-semibold text-foreground", children: dateFns.format(selectedDate, "d") })
|
|
7315
|
+
] })
|
|
7316
|
+
] }),
|
|
7317
|
+
/* @__PURE__ */ jsxRuntime.jsx(ScrollArea, { className: "h-[800px]", type: "always", children: /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex", children: [
|
|
7318
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "relative w-18", children: hours.map((hour, index) => /* @__PURE__ */ jsxRuntime.jsx("div", { className: "relative", style: { height: "96px" }, children: /* @__PURE__ */ jsxRuntime.jsx("div", { className: "absolute -top-3 right-2 flex h-6 items-center", children: index !== 0 && /* @__PURE__ */ jsxRuntime.jsx("span", { className: "text-xs text-muted-foreground", children: dateFns.format((/* @__PURE__ */ new Date()).setHours(hour, 0, 0, 0), "hh a") }) }) }, hour)) }),
|
|
7319
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "relative flex-1 border-l border-border/50", children: [
|
|
7320
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "relative", children: [
|
|
7321
|
+
hours.map((hour, index) => {
|
|
7322
|
+
const isDisabled = !isWorkingHour(selectedDate, hour, workingHours);
|
|
7323
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(
|
|
7324
|
+
"div",
|
|
7325
|
+
{
|
|
7326
|
+
className: cn(
|
|
7327
|
+
"relative",
|
|
7328
|
+
isDisabled && "bg-[repeating-linear-gradient(45deg,transparent,transparent_5px,rgba(0,0,0,0.04)_5px,rgba(0,0,0,0.04)_10px)] dark:bg-[repeating-linear-gradient(45deg,transparent,transparent_5px,rgba(255,255,255,0.04)_5px,rgba(255,255,255,0.04)_10px)]"
|
|
7329
|
+
),
|
|
7330
|
+
style: { height: "96px" },
|
|
7331
|
+
children: [
|
|
7332
|
+
index !== 0 && /* @__PURE__ */ jsxRuntime.jsx("div", { className: "pointer-events-none absolute inset-x-0 top-0 border-b border-border/40" }),
|
|
7333
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
7334
|
+
DroppableTimeSlot2,
|
|
7335
|
+
{
|
|
7336
|
+
date: selectedDate,
|
|
7337
|
+
hour,
|
|
7338
|
+
minute: 0,
|
|
7339
|
+
className: "absolute inset-x-0 top-0 h-[24px]",
|
|
7340
|
+
onClick: () => onTimeClick?.(selectedDate, hour, 0)
|
|
7341
|
+
}
|
|
7342
|
+
),
|
|
7343
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
7344
|
+
DroppableTimeSlot2,
|
|
7345
|
+
{
|
|
7346
|
+
date: selectedDate,
|
|
7347
|
+
hour,
|
|
7348
|
+
minute: 15,
|
|
7349
|
+
className: "absolute inset-x-0 top-[24px] h-[24px]",
|
|
7350
|
+
onClick: () => onTimeClick?.(selectedDate, hour, 15)
|
|
7351
|
+
}
|
|
7352
|
+
),
|
|
7353
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "pointer-events-none absolute inset-x-0 top-1/2 border-b border-dashed border-border/30" }),
|
|
7354
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
7355
|
+
DroppableTimeSlot2,
|
|
7356
|
+
{
|
|
7357
|
+
date: selectedDate,
|
|
7358
|
+
hour,
|
|
7359
|
+
minute: 30,
|
|
7360
|
+
className: "absolute inset-x-0 top-[48px] h-[24px]",
|
|
7361
|
+
onClick: () => onTimeClick?.(selectedDate, hour, 30)
|
|
7362
|
+
}
|
|
7363
|
+
),
|
|
7364
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
7365
|
+
DroppableTimeSlot2,
|
|
7366
|
+
{
|
|
7367
|
+
date: selectedDate,
|
|
7368
|
+
hour,
|
|
7369
|
+
minute: 45,
|
|
7370
|
+
className: "absolute inset-x-0 top-[72px] h-[24px]",
|
|
7371
|
+
onClick: () => onTimeClick?.(selectedDate, hour, 45)
|
|
7372
|
+
}
|
|
7373
|
+
)
|
|
7374
|
+
]
|
|
7375
|
+
},
|
|
7376
|
+
hour
|
|
7377
|
+
);
|
|
7378
|
+
}),
|
|
7379
|
+
groupedEvents.map(
|
|
7380
|
+
(group, groupIndex) => group.map((event) => {
|
|
7381
|
+
let style = getEventBlockStyle(
|
|
7382
|
+
event,
|
|
7383
|
+
selectedDate,
|
|
7384
|
+
groupIndex,
|
|
7385
|
+
groupedEvents.length,
|
|
7386
|
+
{ from: earliestEventHour}
|
|
7387
|
+
);
|
|
7388
|
+
const hasOverlap = groupedEvents.some(
|
|
7389
|
+
(otherGroup, otherIndex) => otherIndex !== groupIndex && otherGroup.some(
|
|
7390
|
+
(otherEvent) => dateFns.areIntervalsOverlapping(
|
|
7391
|
+
{
|
|
7392
|
+
start: dateFns.parseISO(event.startDate),
|
|
7393
|
+
end: dateFns.parseISO(event.endDate)
|
|
7394
|
+
},
|
|
7395
|
+
{
|
|
7396
|
+
start: dateFns.parseISO(otherEvent.startDate),
|
|
7397
|
+
end: dateFns.parseISO(otherEvent.endDate)
|
|
7398
|
+
}
|
|
7399
|
+
)
|
|
7400
|
+
)
|
|
7401
|
+
);
|
|
7402
|
+
if (!hasOverlap) {
|
|
7403
|
+
style = { ...style, width: "100%", left: "0%" };
|
|
7404
|
+
}
|
|
7405
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
7406
|
+
DraggableEventWrapper3,
|
|
7407
|
+
{
|
|
7408
|
+
event,
|
|
7409
|
+
className: "absolute px-1 py-0.5",
|
|
7410
|
+
style,
|
|
7411
|
+
children: /* @__PURE__ */ jsxRuntime.jsx(
|
|
7412
|
+
EventBadge,
|
|
7413
|
+
{
|
|
7414
|
+
event,
|
|
7415
|
+
variant: badgeVariant,
|
|
7416
|
+
showTime: true,
|
|
7417
|
+
onClick: (e) => onEventClick?.(e),
|
|
7418
|
+
className: "h-full w-full"
|
|
7419
|
+
}
|
|
7420
|
+
)
|
|
7421
|
+
},
|
|
7422
|
+
event.id
|
|
7423
|
+
);
|
|
7424
|
+
})
|
|
7425
|
+
)
|
|
7426
|
+
] }),
|
|
7427
|
+
dateFns.isToday(selectedDate) && /* @__PURE__ */ jsxRuntime.jsx(
|
|
7428
|
+
CalendarTimeline2,
|
|
7429
|
+
{
|
|
7430
|
+
firstVisibleHour: earliestEventHour,
|
|
7431
|
+
lastVisibleHour: latestEventHour
|
|
7432
|
+
}
|
|
7433
|
+
)
|
|
7434
|
+
] })
|
|
7435
|
+
] }) })
|
|
7436
|
+
] }),
|
|
7437
|
+
showSidebar && /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "hidden w-64 divide-y border-l md:block", children: [
|
|
7438
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
7439
|
+
Calendar,
|
|
7440
|
+
{
|
|
7441
|
+
className: "mx-auto w-fit",
|
|
7442
|
+
mode: "single",
|
|
7443
|
+
selected: selectedDate,
|
|
7444
|
+
onSelect: handleDateSelect
|
|
7445
|
+
}
|
|
7446
|
+
),
|
|
7447
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex-1 space-y-3", children: [
|
|
7448
|
+
currentEvents.length > 0 ? /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-start gap-2 px-4 pt-4", children: [
|
|
7449
|
+
/* @__PURE__ */ jsxRuntime.jsxs("span", { className: "relative mt-[5px] flex size-2.5", children: [
|
|
7450
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "absolute inline-flex size-full animate-ping rounded-full bg-green-400 opacity-75" }),
|
|
7451
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "relative inline-flex size-2.5 rounded-full bg-green-600" })
|
|
7452
|
+
] }),
|
|
7453
|
+
/* @__PURE__ */ jsxRuntime.jsx("p", { className: "text-sm font-semibold text-foreground", children: "Happening now" })
|
|
7454
|
+
] }) : /* @__PURE__ */ jsxRuntime.jsx("p", { className: "p-4 text-center text-sm italic text-muted-foreground", children: "No appointments or consultations at the moment" }),
|
|
7455
|
+
currentEvents.length > 0 && /* @__PURE__ */ jsxRuntime.jsx(ScrollArea, { className: "h-[422px] px-4", type: "always", children: /* @__PURE__ */ jsxRuntime.jsx("div", { className: "space-y-6 pb-4", children: currentEvents.map((event) => {
|
|
7456
|
+
const user = users.find((u) => u.id === event.user.id);
|
|
7457
|
+
return /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "space-y-1.5", children: [
|
|
7458
|
+
/* @__PURE__ */ jsxRuntime.jsx("p", { className: "line-clamp-2 text-sm font-semibold", children: event.title }),
|
|
7459
|
+
user && /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center gap-1.5 text-muted-foreground", children: [
|
|
7460
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.User, { className: "size-3.5" }),
|
|
7461
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "text-sm", children: user.name })
|
|
7462
|
+
] }),
|
|
7463
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center gap-1.5 text-muted-foreground", children: [
|
|
7464
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.Calendar, { className: "size-3.5" }),
|
|
7465
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "text-sm", children: dateFns.format(/* @__PURE__ */ new Date(), "MMM d, yyyy") })
|
|
7466
|
+
] }),
|
|
7467
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center gap-1.5 text-muted-foreground", children: [
|
|
7468
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.Clock, { className: "size-3.5" }),
|
|
7469
|
+
/* @__PURE__ */ jsxRuntime.jsxs("span", { className: "text-sm", children: [
|
|
7470
|
+
dateFns.format(dateFns.parseISO(event.startDate), "h:mm a"),
|
|
7471
|
+
" -",
|
|
7472
|
+
" ",
|
|
7473
|
+
dateFns.format(dateFns.parseISO(event.endDate), "h:mm a")
|
|
7474
|
+
] })
|
|
7475
|
+
] })
|
|
7476
|
+
] }, event.id);
|
|
7477
|
+
}) }) })
|
|
7478
|
+
] })
|
|
7479
|
+
] })
|
|
7480
|
+
] });
|
|
7481
|
+
}
|
|
7482
|
+
function DayViewMultiDayEventsRow({
|
|
7483
|
+
selectedDate,
|
|
7484
|
+
multiDayEvents
|
|
7485
|
+
}) {
|
|
7486
|
+
const { badgeVariant } = useEventCalendar();
|
|
7487
|
+
const relevantEvents = multiDayEvents.filter((event) => {
|
|
7488
|
+
const start = dateFns.parseISO(event.startDate);
|
|
7489
|
+
const end = dateFns.parseISO(event.endDate);
|
|
7490
|
+
return selectedDate >= start && selectedDate <= end;
|
|
7491
|
+
});
|
|
7492
|
+
if (relevantEvents.length === 0) return null;
|
|
7493
|
+
return /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex border-b", children: [
|
|
7494
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "w-18 shrink-0" }),
|
|
7495
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "flex-1 space-y-1 border-l p-2", children: relevantEvents.map((event) => /* @__PURE__ */ jsxRuntime.jsx(
|
|
7496
|
+
EventBadge,
|
|
7497
|
+
{
|
|
7498
|
+
event,
|
|
7499
|
+
variant: badgeVariant,
|
|
7500
|
+
className: "w-full"
|
|
7501
|
+
},
|
|
7502
|
+
event.id
|
|
7503
|
+
)) })
|
|
7504
|
+
] });
|
|
7505
|
+
}
|
|
7506
|
+
function CalendarTimeline2({
|
|
7507
|
+
firstVisibleHour,
|
|
7508
|
+
lastVisibleHour
|
|
7509
|
+
}) {
|
|
7510
|
+
const [currentTime, setCurrentTime] = React14__namespace.useState(/* @__PURE__ */ new Date());
|
|
7511
|
+
React14__namespace.useEffect(() => {
|
|
7512
|
+
const interval = setInterval(() => {
|
|
7513
|
+
setCurrentTime(/* @__PURE__ */ new Date());
|
|
7514
|
+
}, 6e4);
|
|
7515
|
+
return () => clearInterval(interval);
|
|
7516
|
+
}, []);
|
|
7517
|
+
const currentHour = currentTime.getHours();
|
|
7518
|
+
const currentMinute = currentTime.getMinutes();
|
|
7519
|
+
if (currentHour < firstVisibleHour || currentHour >= lastVisibleHour) {
|
|
7520
|
+
return null;
|
|
7521
|
+
}
|
|
7522
|
+
const minutesSinceStart = (currentHour - firstVisibleHour) * 60 + currentMinute;
|
|
7523
|
+
const totalMinutes = (lastVisibleHour - firstVisibleHour) * 60;
|
|
7524
|
+
const topPercent = minutesSinceStart / totalMinutes * 100;
|
|
7525
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(
|
|
7526
|
+
"div",
|
|
7527
|
+
{
|
|
7528
|
+
className: "pointer-events-none absolute inset-x-0 z-30 flex items-center",
|
|
7529
|
+
style: { top: `${topPercent}%` },
|
|
7530
|
+
children: [
|
|
7531
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "size-3 -translate-x-1/2 rounded-full bg-red-500" }),
|
|
7532
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "h-0.5 flex-1 bg-red-500" })
|
|
7533
|
+
]
|
|
7534
|
+
}
|
|
7535
|
+
);
|
|
7536
|
+
}
|
|
7537
|
+
function YearView({
|
|
7538
|
+
className,
|
|
7539
|
+
weekStartsOn = 0,
|
|
7540
|
+
onMonthClick,
|
|
7541
|
+
onDateClick
|
|
7542
|
+
}) {
|
|
7543
|
+
const { selectedDate, setSelectedDate, setView } = useEventCalendar();
|
|
7544
|
+
const filteredEvents = useFilteredEvents();
|
|
7545
|
+
const months = React14__namespace.useMemo(() => {
|
|
7546
|
+
const yearStart = dateFns.startOfYear(selectedDate);
|
|
7547
|
+
return Array.from({ length: 12 }, (_, i) => dateFns.addMonths(yearStart, i));
|
|
7548
|
+
}, [selectedDate]);
|
|
7549
|
+
const handleMonthClick = (date) => {
|
|
7550
|
+
setSelectedDate(date);
|
|
7551
|
+
setView("month");
|
|
7552
|
+
onMonthClick?.(date);
|
|
7553
|
+
};
|
|
7554
|
+
const handleDateClick = (date) => {
|
|
7555
|
+
setSelectedDate(date);
|
|
7556
|
+
setView("day");
|
|
7557
|
+
onDateClick?.(date);
|
|
7558
|
+
};
|
|
7559
|
+
return /* @__PURE__ */ jsxRuntime.jsx(ScrollArea, { className: cn("h-full", className), type: "always", children: /* @__PURE__ */ jsxRuntime.jsx("div", { className: "p-4", children: /* @__PURE__ */ jsxRuntime.jsx("div", { className: "grid grid-cols-1 gap-4 md:grid-cols-2 lg:grid-cols-3 xl:grid-cols-4", children: months.map((month) => /* @__PURE__ */ jsxRuntime.jsx(
|
|
7560
|
+
YearViewMonth,
|
|
7561
|
+
{
|
|
7562
|
+
month,
|
|
7563
|
+
events: filteredEvents,
|
|
7564
|
+
onMonthClick: () => handleMonthClick(month),
|
|
7565
|
+
onDateClick: handleDateClick
|
|
7566
|
+
},
|
|
7567
|
+
month.toString()
|
|
7568
|
+
)) }) }) });
|
|
7569
|
+
}
|
|
7570
|
+
function YearViewMonth({
|
|
7571
|
+
month,
|
|
7572
|
+
events,
|
|
7573
|
+
onMonthClick,
|
|
7574
|
+
onDateClick
|
|
7575
|
+
}) {
|
|
7576
|
+
const cells = getCalendarCells(month);
|
|
7577
|
+
const monthEvents = events.filter((event) => {
|
|
7578
|
+
const eventStart = dateFns.parseISO(event.startDate);
|
|
7579
|
+
return dateFns.isSameMonth(eventStart, month);
|
|
7580
|
+
});
|
|
7581
|
+
return /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "rounded-sm border border-border/50 bg-card p-3", children: [
|
|
7582
|
+
/* @__PURE__ */ jsxRuntime.jsxs(
|
|
7583
|
+
"button",
|
|
7584
|
+
{
|
|
7585
|
+
type: "button",
|
|
7586
|
+
onClick: onMonthClick,
|
|
7587
|
+
className: "mb-2 w-full text-left text-sm font-semibold transition-colors hover:text-primary",
|
|
7588
|
+
children: [
|
|
7589
|
+
dateFns.format(month, "MMMM"),
|
|
7590
|
+
monthEvents.length > 0 && /* @__PURE__ */ jsxRuntime.jsxs("span", { className: "ml-2 text-xs font-normal text-muted-foreground", children: [
|
|
7591
|
+
"(",
|
|
7592
|
+
monthEvents.length,
|
|
7593
|
+
")"
|
|
7594
|
+
] })
|
|
7595
|
+
]
|
|
7596
|
+
}
|
|
7597
|
+
),
|
|
7598
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "mb-1 grid grid-cols-7", children: ["S", "M", "T", "W", "T", "F", "S"].map((day, i) => /* @__PURE__ */ jsxRuntime.jsx(
|
|
7599
|
+
"div",
|
|
7600
|
+
{
|
|
7601
|
+
className: "text-center text-[10px] font-medium text-muted-foreground",
|
|
7602
|
+
children: day
|
|
7603
|
+
},
|
|
7604
|
+
i
|
|
7605
|
+
)) }),
|
|
7606
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "grid grid-cols-7", children: cells.map((cell) => /* @__PURE__ */ jsxRuntime.jsx(
|
|
7607
|
+
YearViewDayCell,
|
|
7608
|
+
{
|
|
7609
|
+
cell,
|
|
7610
|
+
month,
|
|
7611
|
+
events,
|
|
7612
|
+
onDateClick
|
|
7613
|
+
},
|
|
7614
|
+
cell.date.toISOString()
|
|
7615
|
+
)) })
|
|
7616
|
+
] });
|
|
7617
|
+
}
|
|
7618
|
+
function YearViewDayCell({
|
|
7619
|
+
cell,
|
|
7620
|
+
month,
|
|
7621
|
+
events,
|
|
7622
|
+
onDateClick
|
|
7623
|
+
}) {
|
|
7624
|
+
const { date, currentMonth } = cell;
|
|
7625
|
+
const isCurrentDay = dateFns.isToday(date);
|
|
7626
|
+
const dayEvents = events.filter((event) => {
|
|
7627
|
+
const eventStart = dateFns.parseISO(event.startDate);
|
|
7628
|
+
const eventEnd = dateFns.parseISO(event.endDate);
|
|
7629
|
+
return date >= eventStart && date <= eventEnd || dateFns.isSameDay(eventStart, date) || dateFns.isSameDay(eventEnd, date);
|
|
7630
|
+
});
|
|
7631
|
+
const hasEvents = dayEvents.length > 0;
|
|
7632
|
+
if (!currentMonth) {
|
|
7633
|
+
return /* @__PURE__ */ jsxRuntime.jsx("div", { className: "aspect-square" });
|
|
7634
|
+
}
|
|
7635
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(
|
|
7636
|
+
"button",
|
|
7637
|
+
{
|
|
7638
|
+
type: "button",
|
|
7639
|
+
onClick: () => onDateClick(date),
|
|
7640
|
+
className: cn(
|
|
7641
|
+
"relative flex aspect-square items-center justify-center text-[11px] transition-colors",
|
|
7642
|
+
"hover:bg-muted rounded-sm",
|
|
7643
|
+
isCurrentDay && "bg-primary text-primary-foreground rounded-sm hover:bg-primary/90"
|
|
7644
|
+
),
|
|
7645
|
+
children: [
|
|
7646
|
+
cell.day,
|
|
7647
|
+
hasEvents && !isCurrentDay && /* @__PURE__ */ jsxRuntime.jsx("span", { className: "absolute bottom-0.5 left-1/2 size-1 -translate-x-1/2 rounded-full bg-primary" })
|
|
7648
|
+
]
|
|
7649
|
+
}
|
|
7650
|
+
);
|
|
7651
|
+
}
|
|
7652
|
+
var colorClasses2 = {
|
|
7653
|
+
blue: { border: "border-l-blue-500", bg: "bg-blue-50 dark:bg-blue-950/20" },
|
|
7654
|
+
green: { border: "border-l-green-500", bg: "bg-green-50 dark:bg-green-950/20" },
|
|
7655
|
+
red: { border: "border-l-red-500", bg: "bg-red-50 dark:bg-red-950/20" },
|
|
7656
|
+
yellow: { border: "border-l-yellow-500", bg: "bg-yellow-50 dark:bg-yellow-950/20" },
|
|
7657
|
+
purple: { border: "border-l-purple-500", bg: "bg-purple-50 dark:bg-purple-950/20" },
|
|
7658
|
+
orange: { border: "border-l-primary", bg: "bg-orange-50 dark:bg-orange-950/20" }
|
|
7659
|
+
};
|
|
7660
|
+
function AgendaView({
|
|
7661
|
+
className,
|
|
7662
|
+
emptyMessage = "No events scheduled for the selected month",
|
|
7663
|
+
onEventClick,
|
|
7664
|
+
onDateClick
|
|
7665
|
+
}) {
|
|
7666
|
+
const { selectedDate, setSelectedDate, setView } = useEventCalendar();
|
|
7667
|
+
const filteredEvents = useFilteredEvents();
|
|
7668
|
+
const { singleDayEvents, multiDayEvents } = React14__namespace.useMemo(
|
|
7669
|
+
() => splitEventsByDuration(filteredEvents),
|
|
7670
|
+
[filteredEvents]
|
|
7671
|
+
);
|
|
7672
|
+
const eventsByDay = React14__namespace.useMemo(() => {
|
|
7673
|
+
const allDates = /* @__PURE__ */ new Map();
|
|
7674
|
+
singleDayEvents.forEach((event) => {
|
|
7675
|
+
const eventDate = dateFns.parseISO(event.startDate);
|
|
7676
|
+
if (!dateFns.isSameMonth(eventDate, selectedDate)) return;
|
|
7677
|
+
const dateKey = dateFns.format(eventDate, "yyyy-MM-dd");
|
|
7678
|
+
if (!allDates.has(dateKey)) {
|
|
7679
|
+
allDates.set(dateKey, {
|
|
7680
|
+
date: dateFns.startOfDay(eventDate),
|
|
7681
|
+
events: [],
|
|
7682
|
+
multiDayEvents: []
|
|
7683
|
+
});
|
|
7684
|
+
}
|
|
7685
|
+
allDates.get(dateKey)?.events.push(event);
|
|
7686
|
+
});
|
|
7687
|
+
multiDayEvents.forEach((event) => {
|
|
7688
|
+
const eventStart = dateFns.parseISO(event.startDate);
|
|
7689
|
+
const eventEnd = dateFns.parseISO(event.endDate);
|
|
7690
|
+
let currentDate = dateFns.startOfDay(eventStart);
|
|
7691
|
+
const lastDate = dateFns.endOfDay(eventEnd);
|
|
7692
|
+
while (currentDate <= lastDate) {
|
|
7693
|
+
if (dateFns.isSameMonth(currentDate, selectedDate)) {
|
|
7694
|
+
const dateKey = dateFns.format(currentDate, "yyyy-MM-dd");
|
|
7695
|
+
if (!allDates.has(dateKey)) {
|
|
7696
|
+
allDates.set(dateKey, {
|
|
7697
|
+
date: new Date(currentDate),
|
|
7698
|
+
events: [],
|
|
7699
|
+
multiDayEvents: []
|
|
7700
|
+
});
|
|
7701
|
+
}
|
|
7702
|
+
allDates.get(dateKey)?.multiDayEvents.push(event);
|
|
7703
|
+
}
|
|
7704
|
+
currentDate = new Date(currentDate.setDate(currentDate.getDate() + 1));
|
|
7705
|
+
}
|
|
7706
|
+
});
|
|
7707
|
+
return Array.from(allDates.values()).sort(
|
|
7708
|
+
(a, b) => a.date.getTime() - b.date.getTime()
|
|
7709
|
+
);
|
|
7710
|
+
}, [singleDayEvents, multiDayEvents, selectedDate]);
|
|
7711
|
+
const hasAnyEvents = singleDayEvents.length > 0 || multiDayEvents.length > 0;
|
|
7712
|
+
const handleDateClick = (date) => {
|
|
7713
|
+
setSelectedDate(date);
|
|
7714
|
+
setView("day");
|
|
7715
|
+
onDateClick?.(date);
|
|
7716
|
+
};
|
|
7717
|
+
return /* @__PURE__ */ jsxRuntime.jsx("div", { className: cn("h-[800px]", className), children: /* @__PURE__ */ jsxRuntime.jsx(ScrollArea, { className: "h-full", type: "always", children: /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "space-y-6 p-4", children: [
|
|
7718
|
+
eventsByDay.map((dayGroup) => /* @__PURE__ */ jsxRuntime.jsx(
|
|
7719
|
+
AgendaDayGroup,
|
|
7720
|
+
{
|
|
7721
|
+
date: dayGroup.date,
|
|
7722
|
+
events: dayGroup.events,
|
|
7723
|
+
multiDayEvents: dayGroup.multiDayEvents,
|
|
7724
|
+
onDateClick: handleDateClick,
|
|
7725
|
+
onEventClick
|
|
7726
|
+
},
|
|
7727
|
+
dateFns.format(dayGroup.date, "yyyy-MM-dd")
|
|
7728
|
+
)),
|
|
7729
|
+
!hasAnyEvents && /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex flex-col items-center justify-center gap-2 py-20 text-muted-foreground", children: [
|
|
7730
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.CalendarX2, { className: "size-10" }),
|
|
7731
|
+
/* @__PURE__ */ jsxRuntime.jsx("p", { className: "text-sm md:text-base", children: emptyMessage })
|
|
7732
|
+
] })
|
|
7733
|
+
] }) }) });
|
|
7734
|
+
}
|
|
7735
|
+
function AgendaDayGroup({
|
|
7736
|
+
date,
|
|
7737
|
+
events,
|
|
7738
|
+
multiDayEvents,
|
|
7739
|
+
onDateClick,
|
|
7740
|
+
onEventClick
|
|
7741
|
+
}) {
|
|
7742
|
+
const isCurrentDay = dateFns.isToday(date);
|
|
7743
|
+
return /* @__PURE__ */ jsxRuntime.jsxs("div", { children: [
|
|
7744
|
+
/* @__PURE__ */ jsxRuntime.jsxs(
|
|
7745
|
+
"button",
|
|
7746
|
+
{
|
|
7747
|
+
type: "button",
|
|
7748
|
+
onClick: () => onDateClick(date),
|
|
7749
|
+
className: cn(
|
|
7750
|
+
"mb-3 flex items-center gap-2 text-left transition-colors hover:text-primary",
|
|
7751
|
+
isCurrentDay && "text-primary"
|
|
7752
|
+
),
|
|
7753
|
+
children: [
|
|
7754
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
7755
|
+
"span",
|
|
7756
|
+
{
|
|
7757
|
+
className: cn(
|
|
7758
|
+
"flex size-8 items-center justify-center rounded-full text-sm font-bold",
|
|
7759
|
+
isCurrentDay && "bg-primary text-primary-foreground"
|
|
7760
|
+
),
|
|
7761
|
+
children: dateFns.format(date, "d")
|
|
7762
|
+
}
|
|
7763
|
+
),
|
|
7764
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { children: [
|
|
7765
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "font-semibold", children: dateFns.format(date, "EEEE") }),
|
|
7766
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "ml-2 text-muted-foreground", children: dateFns.format(date, "MMMM d, yyyy") })
|
|
7767
|
+
] })
|
|
7768
|
+
]
|
|
7769
|
+
}
|
|
7770
|
+
),
|
|
7771
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "space-y-2 pl-10", children: [
|
|
7772
|
+
multiDayEvents.map((event) => /* @__PURE__ */ jsxRuntime.jsx(
|
|
7773
|
+
AgendaEventCard,
|
|
7774
|
+
{
|
|
7775
|
+
event,
|
|
7776
|
+
isMultiDay: true,
|
|
7777
|
+
onClick: () => onEventClick?.(event)
|
|
7778
|
+
},
|
|
7779
|
+
`multi-${event.id}`
|
|
7780
|
+
)),
|
|
7781
|
+
events.map((event) => /* @__PURE__ */ jsxRuntime.jsx(
|
|
7782
|
+
AgendaEventCard,
|
|
7783
|
+
{
|
|
7784
|
+
event,
|
|
7785
|
+
onClick: () => onEventClick?.(event)
|
|
7786
|
+
},
|
|
7787
|
+
event.id
|
|
7788
|
+
))
|
|
7789
|
+
] })
|
|
7790
|
+
] });
|
|
7791
|
+
}
|
|
7792
|
+
function AgendaEventCard({ event, isMultiDay, onClick }) {
|
|
7793
|
+
const colors = colorClasses2[event.color];
|
|
7794
|
+
const startTime = dateFns.format(dateFns.parseISO(event.startDate), "h:mm a");
|
|
7795
|
+
const endTime = dateFns.format(dateFns.parseISO(event.endDate), "h:mm a");
|
|
7796
|
+
const getInitials = (name) => {
|
|
7797
|
+
return name.split(" ").map((n) => n[0]).join("").toUpperCase().slice(0, 2);
|
|
7798
|
+
};
|
|
7799
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(
|
|
7800
|
+
"button",
|
|
7801
|
+
{
|
|
7802
|
+
type: "button",
|
|
7803
|
+
onClick,
|
|
7804
|
+
className: cn(
|
|
7805
|
+
"flex w-full items-start gap-3 rounded-lg border-l-4 p-3 text-left transition-colors",
|
|
7806
|
+
"hover:opacity-90",
|
|
7807
|
+
colors.border,
|
|
7808
|
+
colors.bg
|
|
7809
|
+
),
|
|
7810
|
+
children: [
|
|
7811
|
+
/* @__PURE__ */ jsxRuntime.jsxs(Avatar, { className: "size-10 shrink-0", children: [
|
|
7812
|
+
/* @__PURE__ */ jsxRuntime.jsx(AvatarImage, { src: event.user.picturePath, alt: event.user.name }),
|
|
7813
|
+
/* @__PURE__ */ jsxRuntime.jsx(AvatarFallback, { children: getInitials(event.user.name) })
|
|
7814
|
+
] }),
|
|
7815
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex-1 min-w-0", children: [
|
|
7816
|
+
isMultiDay && /* @__PURE__ */ jsxRuntime.jsx("span", { className: "text-xs text-muted-foreground", children: "Multi-day event" }),
|
|
7817
|
+
/* @__PURE__ */ jsxRuntime.jsx("h3", { className: "font-semibold truncate", children: event.title }),
|
|
7818
|
+
/* @__PURE__ */ jsxRuntime.jsx("p", { className: "text-sm text-muted-foreground", children: event.user.name }),
|
|
7819
|
+
/* @__PURE__ */ jsxRuntime.jsxs("p", { className: "mt-1 text-xs text-muted-foreground", children: [
|
|
7820
|
+
startTime,
|
|
7821
|
+
" - ",
|
|
7822
|
+
endTime
|
|
7823
|
+
] }),
|
|
7824
|
+
event.description && /* @__PURE__ */ jsxRuntime.jsx("p", { className: "mt-2 text-sm text-muted-foreground line-clamp-2", children: event.description })
|
|
7825
|
+
] })
|
|
7826
|
+
]
|
|
7827
|
+
}
|
|
7828
|
+
);
|
|
7829
|
+
}
|
|
7830
|
+
var VIEW_CONFIG = [
|
|
7831
|
+
{ view: "day", icon: lucideReact.List, label: "View by day" },
|
|
7832
|
+
{ view: "week", icon: lucideReact.Columns, label: "View by week" },
|
|
7833
|
+
{ view: "month", icon: lucideReact.Grid2x2, label: "View by month" },
|
|
7834
|
+
{ view: "year", icon: lucideReact.Grid3x3, label: "View by year" },
|
|
7835
|
+
{ view: "agenda", icon: lucideReact.CalendarRange, label: "View by agenda" }
|
|
7836
|
+
];
|
|
7837
|
+
function CalendarHeader({
|
|
7838
|
+
className,
|
|
7839
|
+
showViewSwitcher = true,
|
|
7840
|
+
showUserFilter = true,
|
|
7841
|
+
showBadgeVariant = false,
|
|
7842
|
+
// Hidden by default, controlled via settings
|
|
7843
|
+
showToday = true,
|
|
7844
|
+
showAddButton = true,
|
|
7845
|
+
onAddClick
|
|
7846
|
+
}) {
|
|
7847
|
+
const {
|
|
7848
|
+
selectedDate,
|
|
7849
|
+
view,
|
|
7850
|
+
setView,
|
|
7851
|
+
setSelectedDate,
|
|
7852
|
+
selectedUserId,
|
|
7853
|
+
setSelectedUserId,
|
|
7854
|
+
users,
|
|
7855
|
+
badgeVariant,
|
|
7856
|
+
setBadgeVariant,
|
|
7857
|
+
goToPrevious,
|
|
7858
|
+
goToNext
|
|
7859
|
+
} = useEventCalendar();
|
|
7860
|
+
const filteredEvents = useFilteredEvents();
|
|
7861
|
+
const eventCount = filteredEvents.length;
|
|
7862
|
+
const { start: rangeStart, end: rangeEnd } = getViewDateRange(selectedDate, view);
|
|
7863
|
+
const dateRangeLabel = formatDateRange(rangeStart, rangeEnd);
|
|
7864
|
+
const getInitials = (name) => {
|
|
7865
|
+
return name.split(" ").map((n) => n[0]).join("").toUpperCase().slice(0, 2);
|
|
7866
|
+
};
|
|
7867
|
+
const handleTodayClick = () => {
|
|
7868
|
+
setSelectedDate(/* @__PURE__ */ new Date());
|
|
7869
|
+
};
|
|
7870
|
+
const today = /* @__PURE__ */ new Date();
|
|
7871
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(
|
|
7872
|
+
"div",
|
|
7873
|
+
{
|
|
7874
|
+
className: cn(
|
|
7875
|
+
"flex flex-col gap-4 border-b border-border p-4 lg:flex-row lg:items-center lg:justify-between",
|
|
7876
|
+
className
|
|
7877
|
+
),
|
|
7878
|
+
children: [
|
|
7879
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center gap-3", children: [
|
|
7880
|
+
/* @__PURE__ */ jsxRuntime.jsxs(
|
|
7881
|
+
"button",
|
|
7882
|
+
{
|
|
7883
|
+
type: "button",
|
|
7884
|
+
onClick: handleTodayClick,
|
|
7885
|
+
className: "flex size-14 flex-col items-start overflow-hidden rounded-lg border focus-visible:outline-none focus-visible:ring-1 focus-visible:ring-ring",
|
|
7886
|
+
children: [
|
|
7887
|
+
/* @__PURE__ */ jsxRuntime.jsx("p", { className: "flex h-6 w-full items-center justify-center bg-primary text-center text-xs font-semibold text-primary-foreground", children: dateFns.format(today, "MMM").toUpperCase() }),
|
|
7888
|
+
/* @__PURE__ */ jsxRuntime.jsx("p", { className: "flex w-full flex-1 items-center justify-center text-lg font-bold", children: today.getDate() })
|
|
7889
|
+
]
|
|
7890
|
+
}
|
|
7891
|
+
),
|
|
7892
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "space-y-0.5", children: [
|
|
7893
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center gap-2", children: [
|
|
7894
|
+
/* @__PURE__ */ jsxRuntime.jsxs("span", { className: "text-lg font-semibold", children: [
|
|
7895
|
+
dateFns.format(selectedDate, "MMMM"),
|
|
7896
|
+
" ",
|
|
7897
|
+
selectedDate.getFullYear()
|
|
7898
|
+
] }),
|
|
7899
|
+
/* @__PURE__ */ jsxRuntime.jsxs(Badge, { variant: "outline", className: "px-1.5", children: [
|
|
7900
|
+
eventCount,
|
|
7901
|
+
" event",
|
|
7902
|
+
eventCount !== 1 ? "s" : ""
|
|
7903
|
+
] })
|
|
7904
|
+
] }),
|
|
7905
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center gap-2", children: [
|
|
7906
|
+
/* @__PURE__ */ jsxRuntime.jsxs(
|
|
7907
|
+
Button,
|
|
7908
|
+
{
|
|
7909
|
+
variant: "outline",
|
|
7910
|
+
size: "icon",
|
|
7911
|
+
className: "size-7 [&_svg]:size-4",
|
|
7912
|
+
onClick: goToPrevious,
|
|
7913
|
+
children: [
|
|
7914
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.ChevronLeft, {}),
|
|
7915
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "sr-only", children: "Previous" })
|
|
7916
|
+
]
|
|
7917
|
+
}
|
|
7918
|
+
),
|
|
7919
|
+
/* @__PURE__ */ jsxRuntime.jsx("p", { className: "text-sm text-muted-foreground", children: dateRangeLabel }),
|
|
7920
|
+
/* @__PURE__ */ jsxRuntime.jsxs(
|
|
7921
|
+
Button,
|
|
7922
|
+
{
|
|
7923
|
+
variant: "outline",
|
|
7924
|
+
size: "icon",
|
|
7925
|
+
className: "size-7 [&_svg]:size-4",
|
|
7926
|
+
onClick: goToNext,
|
|
7927
|
+
children: [
|
|
7928
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.ChevronRight, {}),
|
|
7929
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "sr-only", children: "Next" })
|
|
7930
|
+
]
|
|
7931
|
+
}
|
|
7932
|
+
)
|
|
7933
|
+
] })
|
|
7934
|
+
] })
|
|
7935
|
+
] }),
|
|
7936
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex flex-col items-center gap-1.5 sm:flex-row sm:justify-between", children: [
|
|
7937
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex w-full items-center gap-1.5", children: [
|
|
7938
|
+
showViewSwitcher && /* @__PURE__ */ jsxRuntime.jsx("div", { className: "inline-flex items-center gap-1 rounded-full border border-border px-1 py-1", children: VIEW_CONFIG.map((config, index) => {
|
|
7939
|
+
const Icon2 = config.icon;
|
|
7940
|
+
const isFirst = index === 0;
|
|
7941
|
+
const isLast = index === VIEW_CONFIG.length - 1;
|
|
7942
|
+
const isActive = view === config.view;
|
|
7943
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
7944
|
+
Button,
|
|
7945
|
+
{
|
|
7946
|
+
"aria-label": config.label,
|
|
7947
|
+
size: "icon",
|
|
7948
|
+
variant: isActive ? "default" : "ghost",
|
|
7949
|
+
className: cn(
|
|
7950
|
+
"size-8 border-0 [&_svg]:size-4",
|
|
7951
|
+
isFirst && "rounded-l-full rounded-r-sm",
|
|
7952
|
+
isLast && "rounded-r-full rounded-l-sm",
|
|
7953
|
+
!isFirst && !isLast && "rounded-sm"
|
|
7954
|
+
),
|
|
7955
|
+
onClick: () => setView(config.view),
|
|
7956
|
+
children: /* @__PURE__ */ jsxRuntime.jsx(Icon2, { strokeWidth: 1.8 })
|
|
7957
|
+
},
|
|
7958
|
+
config.view
|
|
7959
|
+
);
|
|
7960
|
+
}) }),
|
|
7961
|
+
showUserFilter && users.length > 0 && /* @__PURE__ */ jsxRuntime.jsxs(
|
|
7962
|
+
Select,
|
|
7963
|
+
{
|
|
7964
|
+
value: selectedUserId || "all",
|
|
7965
|
+
onValueChange: (value) => setSelectedUserId(value === "all" ? null : value),
|
|
7966
|
+
children: [
|
|
7967
|
+
/* @__PURE__ */ jsxRuntime.jsx(SelectTrigger, { className: "flex-1 md:w-48", children: /* @__PURE__ */ jsxRuntime.jsx(SelectValue, {}) }),
|
|
7968
|
+
/* @__PURE__ */ jsxRuntime.jsxs(SelectContent, { align: "end", children: [
|
|
7969
|
+
/* @__PURE__ */ jsxRuntime.jsx(SelectItem, { value: "all", children: /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center gap-1", children: [
|
|
7970
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex -space-x-2", children: [
|
|
7971
|
+
users.slice(0, 2).map((user) => /* @__PURE__ */ jsxRuntime.jsxs(Avatar, { className: "size-6 border-2 border-background", children: [
|
|
7972
|
+
/* @__PURE__ */ jsxRuntime.jsx(AvatarImage, { src: user.picturePath, alt: user.name }),
|
|
7973
|
+
/* @__PURE__ */ jsxRuntime.jsx(AvatarFallback, { className: "text-[10px]", children: getInitials(user.name) })
|
|
7974
|
+
] }, user.id)),
|
|
7975
|
+
users.length > 2 && /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex size-6 items-center justify-center rounded-full border-2 border-background bg-muted text-[10px] font-medium", children: [
|
|
7976
|
+
"+",
|
|
7977
|
+
users.length - 2
|
|
7978
|
+
] })
|
|
7979
|
+
] }),
|
|
7980
|
+
"All"
|
|
7981
|
+
] }) }),
|
|
7982
|
+
users.map((user) => /* @__PURE__ */ jsxRuntime.jsx(SelectItem, { value: user.id, children: /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center gap-2", children: [
|
|
7983
|
+
/* @__PURE__ */ jsxRuntime.jsxs(Avatar, { className: "size-6", children: [
|
|
7984
|
+
/* @__PURE__ */ jsxRuntime.jsx(AvatarImage, { src: user.picturePath, alt: user.name }),
|
|
7985
|
+
/* @__PURE__ */ jsxRuntime.jsx(AvatarFallback, { className: "text-[10px]", children: getInitials(user.name) })
|
|
7986
|
+
] }),
|
|
7987
|
+
/* @__PURE__ */ jsxRuntime.jsx("p", { className: "truncate", children: user.name })
|
|
7988
|
+
] }) }, user.id))
|
|
7989
|
+
] })
|
|
7990
|
+
]
|
|
7991
|
+
}
|
|
7992
|
+
)
|
|
7993
|
+
] }),
|
|
7994
|
+
showAddButton && /* @__PURE__ */ jsxRuntime.jsxs(Button, { onClick: onAddClick, className: "w-full sm:w-auto", children: [
|
|
7995
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.Plus, {}),
|
|
7996
|
+
"Add Event"
|
|
7997
|
+
] })
|
|
7998
|
+
] })
|
|
7999
|
+
]
|
|
8000
|
+
}
|
|
8001
|
+
);
|
|
8002
|
+
}
|
|
8003
|
+
function CalendarHeaderCompact({
|
|
8004
|
+
className,
|
|
8005
|
+
showAddButton = true,
|
|
8006
|
+
onAddClick
|
|
8007
|
+
}) {
|
|
8008
|
+
const {
|
|
8009
|
+
selectedDate,
|
|
8010
|
+
setSelectedDate,
|
|
8011
|
+
view,
|
|
8012
|
+
setView,
|
|
8013
|
+
goToPrevious,
|
|
8014
|
+
goToNext
|
|
8015
|
+
} = useEventCalendar();
|
|
8016
|
+
const filteredEvents = useFilteredEvents();
|
|
8017
|
+
const eventCount = filteredEvents.length;
|
|
8018
|
+
const today = /* @__PURE__ */ new Date();
|
|
8019
|
+
const handleTodayClick = () => {
|
|
8020
|
+
setSelectedDate(/* @__PURE__ */ new Date());
|
|
8021
|
+
};
|
|
8022
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(
|
|
8023
|
+
"div",
|
|
8024
|
+
{
|
|
8025
|
+
className: cn(
|
|
8026
|
+
"flex items-center justify-between border-b border-border p-3",
|
|
8027
|
+
className
|
|
8028
|
+
),
|
|
8029
|
+
children: [
|
|
8030
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center gap-2", children: [
|
|
8031
|
+
/* @__PURE__ */ jsxRuntime.jsxs(
|
|
8032
|
+
"button",
|
|
8033
|
+
{
|
|
8034
|
+
type: "button",
|
|
8035
|
+
onClick: handleTodayClick,
|
|
8036
|
+
className: "flex size-10 flex-col items-start overflow-hidden rounded border focus-visible:outline-none focus-visible:ring-1 focus-visible:ring-ring",
|
|
8037
|
+
children: [
|
|
8038
|
+
/* @__PURE__ */ jsxRuntime.jsx("p", { className: "flex h-4 w-full items-center justify-center bg-primary text-center text-[8px] font-semibold text-primary-foreground", children: dateFns.format(today, "MMM").toUpperCase() }),
|
|
8039
|
+
/* @__PURE__ */ jsxRuntime.jsx("p", { className: "flex w-full flex-1 items-center justify-center text-sm font-bold", children: today.getDate() })
|
|
8040
|
+
]
|
|
8041
|
+
}
|
|
8042
|
+
),
|
|
8043
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { children: [
|
|
8044
|
+
/* @__PURE__ */ jsxRuntime.jsx("h2", { className: "text-sm font-semibold", children: dateFns.format(selectedDate, "MMM yyyy") }),
|
|
8045
|
+
/* @__PURE__ */ jsxRuntime.jsxs("span", { className: "text-xs text-muted-foreground", children: [
|
|
8046
|
+
eventCount,
|
|
8047
|
+
" events"
|
|
8048
|
+
] })
|
|
8049
|
+
] })
|
|
8050
|
+
] }),
|
|
8051
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center gap-1", children: [
|
|
8052
|
+
/* @__PURE__ */ jsxRuntime.jsx(Button, { variant: "ghost", size: "icon", className: "size-8", onClick: goToPrevious, children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.ChevronLeft, { className: "size-4" }) }),
|
|
8053
|
+
/* @__PURE__ */ jsxRuntime.jsx(Button, { variant: "ghost", size: "icon", className: "size-8", onClick: goToNext, children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.ChevronRight, { className: "size-4" }) }),
|
|
8054
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "ml-2 inline-flex items-center gap-0.5 rounded-full border border-border px-0.5 py-0.5", children: [
|
|
8055
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
8056
|
+
Button,
|
|
8057
|
+
{
|
|
8058
|
+
size: "icon",
|
|
8059
|
+
variant: view === "day" ? "default" : "ghost",
|
|
8060
|
+
className: "size-6 rounded-l-full rounded-r-sm border-0 [&_svg]:size-3",
|
|
8061
|
+
onClick: () => setView("day"),
|
|
8062
|
+
children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.List, { strokeWidth: 1.8 })
|
|
8063
|
+
}
|
|
8064
|
+
),
|
|
8065
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
8066
|
+
Button,
|
|
8067
|
+
{
|
|
8068
|
+
size: "icon",
|
|
8069
|
+
variant: view === "week" ? "default" : "ghost",
|
|
8070
|
+
className: "size-6 rounded-sm border-0 [&_svg]:size-3",
|
|
8071
|
+
onClick: () => setView("week"),
|
|
8072
|
+
children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Columns, { strokeWidth: 1.8 })
|
|
8073
|
+
}
|
|
8074
|
+
),
|
|
8075
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
8076
|
+
Button,
|
|
8077
|
+
{
|
|
8078
|
+
size: "icon",
|
|
8079
|
+
variant: view === "month" ? "default" : "ghost",
|
|
8080
|
+
className: "size-6 rounded-r-full rounded-l-sm border-0 [&_svg]:size-3",
|
|
8081
|
+
onClick: () => setView("month"),
|
|
8082
|
+
children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Grid2x2, { strokeWidth: 1.8 })
|
|
8083
|
+
}
|
|
8084
|
+
)
|
|
8085
|
+
] }),
|
|
8086
|
+
showAddButton && /* @__PURE__ */ jsxRuntime.jsx(Button, { size: "sm", onClick: onAddClick, className: "ml-2 size-8 p-0", children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Plus, { className: "size-4" }) })
|
|
8087
|
+
] })
|
|
8088
|
+
]
|
|
8089
|
+
}
|
|
8090
|
+
);
|
|
8091
|
+
}
|
|
8092
|
+
var EVENT_COLORS2 = [
|
|
8093
|
+
{ value: "blue", label: "Blue", className: "bg-blue-500" },
|
|
8094
|
+
{ value: "green", label: "Green", className: "bg-green-500" },
|
|
8095
|
+
{ value: "red", label: "Red", className: "bg-red-500" },
|
|
8096
|
+
{ value: "yellow", label: "Yellow", className: "bg-yellow-500" },
|
|
8097
|
+
{ value: "purple", label: "Purple", className: "bg-purple-500" },
|
|
8098
|
+
{ value: "orange", label: "Orange", className: "bg-primary" }
|
|
8099
|
+
];
|
|
8100
|
+
function EventDialog({
|
|
8101
|
+
open,
|
|
8102
|
+
onOpenChange,
|
|
8103
|
+
mode = "add",
|
|
8104
|
+
event,
|
|
8105
|
+
defaultDate = /* @__PURE__ */ new Date(),
|
|
8106
|
+
defaultUserId
|
|
8107
|
+
}) {
|
|
8108
|
+
const { addEvent, updateEvent, deleteEvent, users } = useEventCalendar();
|
|
8109
|
+
const [title, setTitle] = React14__namespace.useState("");
|
|
8110
|
+
const [description, setDescription] = React14__namespace.useState("");
|
|
8111
|
+
const [startDate, setStartDate] = React14__namespace.useState("");
|
|
8112
|
+
const [startTime, setStartTime] = React14__namespace.useState("");
|
|
8113
|
+
const [endDate, setEndDate] = React14__namespace.useState("");
|
|
8114
|
+
const [endTime, setEndTime] = React14__namespace.useState("");
|
|
8115
|
+
const [color, setColor] = React14__namespace.useState("blue");
|
|
8116
|
+
const [userId, setUserId] = React14__namespace.useState("");
|
|
8117
|
+
const [isSubmitting, setIsSubmitting] = React14__namespace.useState(false);
|
|
8118
|
+
React14__namespace.useEffect(() => {
|
|
8119
|
+
if (open) {
|
|
8120
|
+
if (mode === "edit" && event) {
|
|
8121
|
+
const start = dateFns.parseISO(event.startDate);
|
|
8122
|
+
const end = dateFns.parseISO(event.endDate);
|
|
8123
|
+
setTitle(event.title);
|
|
8124
|
+
setDescription(event.description || "");
|
|
8125
|
+
setStartDate(dateFns.format(start, "yyyy-MM-dd"));
|
|
8126
|
+
setStartTime(dateFns.format(start, "HH:mm"));
|
|
8127
|
+
setEndDate(dateFns.format(end, "yyyy-MM-dd"));
|
|
8128
|
+
setEndTime(dateFns.format(end, "HH:mm"));
|
|
8129
|
+
setColor(event.color);
|
|
8130
|
+
setUserId(event.user.id);
|
|
8131
|
+
} else {
|
|
8132
|
+
const start = defaultDate;
|
|
8133
|
+
const end = dateFns.setMinutes(dateFns.setHours(defaultDate, defaultDate.getHours() + 1), 0);
|
|
8134
|
+
setTitle("");
|
|
8135
|
+
setDescription("");
|
|
8136
|
+
setStartDate(dateFns.format(start, "yyyy-MM-dd"));
|
|
8137
|
+
setStartTime(dateFns.format(start, "HH:mm"));
|
|
8138
|
+
setEndDate(dateFns.format(end, "yyyy-MM-dd"));
|
|
8139
|
+
setEndTime(dateFns.format(end, "HH:mm"));
|
|
8140
|
+
setColor("blue");
|
|
8141
|
+
setUserId(defaultUserId || users[0]?.id || "");
|
|
8142
|
+
}
|
|
8143
|
+
}
|
|
8144
|
+
}, [open, mode, event, defaultDate, defaultUserId, users]);
|
|
8145
|
+
const handleSubmit = async (e) => {
|
|
8146
|
+
e.preventDefault();
|
|
8147
|
+
setIsSubmitting(true);
|
|
8148
|
+
try {
|
|
8149
|
+
const [startYear, startMonth, startDay] = startDate.split("-").map(Number);
|
|
8150
|
+
const [startHour, startMinute] = startTime.split(":").map(Number);
|
|
8151
|
+
const [endYear, endMonth, endDay] = endDate.split("-").map(Number);
|
|
8152
|
+
const [endHour, endMinute] = endTime.split(":").map(Number);
|
|
8153
|
+
const startDateTime = new Date(startYear, startMonth - 1, startDay, startHour, startMinute);
|
|
8154
|
+
const endDateTime = new Date(endYear, endMonth - 1, endDay, endHour, endMinute);
|
|
8155
|
+
const selectedUser = users.find((u) => u.id === userId);
|
|
8156
|
+
if (mode === "edit" && event) {
|
|
8157
|
+
const updatedEvent = {
|
|
8158
|
+
...event,
|
|
8159
|
+
title,
|
|
8160
|
+
description,
|
|
8161
|
+
startDate: startDateTime.toISOString(),
|
|
8162
|
+
endDate: endDateTime.toISOString(),
|
|
8163
|
+
color,
|
|
8164
|
+
user: {
|
|
8165
|
+
id: userId,
|
|
8166
|
+
name: selectedUser?.name || "Unknown"
|
|
8167
|
+
}
|
|
8168
|
+
};
|
|
8169
|
+
updateEvent(updatedEvent);
|
|
8170
|
+
} else {
|
|
8171
|
+
const newEvent = {
|
|
8172
|
+
id: generateEventId(),
|
|
8173
|
+
title,
|
|
8174
|
+
description,
|
|
8175
|
+
startDate: startDateTime.toISOString(),
|
|
8176
|
+
endDate: endDateTime.toISOString(),
|
|
8177
|
+
color,
|
|
8178
|
+
user: {
|
|
8179
|
+
id: userId,
|
|
8180
|
+
name: selectedUser?.name || "Unknown"
|
|
8181
|
+
}
|
|
8182
|
+
};
|
|
8183
|
+
addEvent(newEvent);
|
|
8184
|
+
}
|
|
8185
|
+
onOpenChange(false);
|
|
8186
|
+
} catch (error) {
|
|
8187
|
+
console.error("Failed to save event:", error);
|
|
8188
|
+
} finally {
|
|
8189
|
+
setIsSubmitting(false);
|
|
8190
|
+
}
|
|
8191
|
+
};
|
|
8192
|
+
const handleDelete = () => {
|
|
8193
|
+
if (event) {
|
|
8194
|
+
deleteEvent(event.id);
|
|
8195
|
+
onOpenChange(false);
|
|
8196
|
+
}
|
|
8197
|
+
};
|
|
8198
|
+
return /* @__PURE__ */ jsxRuntime.jsx(Dialog, { open, onOpenChange, children: /* @__PURE__ */ jsxRuntime.jsx(DialogContent, { className: "sm:max-w-[500px]", children: /* @__PURE__ */ jsxRuntime.jsxs("form", { onSubmit: handleSubmit, children: [
|
|
8199
|
+
/* @__PURE__ */ jsxRuntime.jsxs(DialogHeader, { children: [
|
|
8200
|
+
/* @__PURE__ */ jsxRuntime.jsx(DialogTitle, { children: mode === "edit" ? "Edit Event" : "Add Event" }),
|
|
8201
|
+
/* @__PURE__ */ jsxRuntime.jsx(DialogDescription, { children: mode === "edit" ? "Make changes to your event below." : "Fill in the details for your new event." })
|
|
8202
|
+
] }),
|
|
8203
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "grid gap-4 py-4", children: [
|
|
8204
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "grid gap-2", children: [
|
|
8205
|
+
/* @__PURE__ */ jsxRuntime.jsx(Label2, { htmlFor: "title", children: "Title" }),
|
|
8206
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
8207
|
+
Input,
|
|
8208
|
+
{
|
|
8209
|
+
id: "title",
|
|
8210
|
+
value: title,
|
|
8211
|
+
onChange: (e) => setTitle(e.target.value),
|
|
8212
|
+
placeholder: "Event title",
|
|
8213
|
+
required: true
|
|
8214
|
+
}
|
|
8215
|
+
)
|
|
8216
|
+
] }),
|
|
8217
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "grid gap-2", children: [
|
|
8218
|
+
/* @__PURE__ */ jsxRuntime.jsx(Label2, { htmlFor: "description", children: "Description" }),
|
|
8219
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
8220
|
+
Textarea,
|
|
8221
|
+
{
|
|
8222
|
+
id: "description",
|
|
8223
|
+
value: description,
|
|
8224
|
+
onChange: (e) => setDescription(e.target.value),
|
|
8225
|
+
placeholder: "Event description (optional)",
|
|
8226
|
+
rows: 3
|
|
8227
|
+
}
|
|
8228
|
+
)
|
|
8229
|
+
] }),
|
|
8230
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "grid grid-cols-2 gap-4", children: [
|
|
8231
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "grid gap-2", children: [
|
|
8232
|
+
/* @__PURE__ */ jsxRuntime.jsx(Label2, { htmlFor: "startDate", children: "Start Date" }),
|
|
8233
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
8234
|
+
Input,
|
|
8235
|
+
{
|
|
8236
|
+
id: "startDate",
|
|
8237
|
+
type: "date",
|
|
8238
|
+
value: startDate,
|
|
8239
|
+
onChange: (e) => setStartDate(e.target.value),
|
|
8240
|
+
required: true
|
|
8241
|
+
}
|
|
8242
|
+
)
|
|
8243
|
+
] }),
|
|
8244
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "grid gap-2", children: [
|
|
8245
|
+
/* @__PURE__ */ jsxRuntime.jsx(Label2, { htmlFor: "startTime", children: "Start Time" }),
|
|
8246
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
8247
|
+
Input,
|
|
8248
|
+
{
|
|
8249
|
+
id: "startTime",
|
|
8250
|
+
type: "time",
|
|
8251
|
+
value: startTime,
|
|
8252
|
+
onChange: (e) => setStartTime(e.target.value),
|
|
8253
|
+
required: true
|
|
8254
|
+
}
|
|
8255
|
+
)
|
|
8256
|
+
] })
|
|
8257
|
+
] }),
|
|
8258
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "grid grid-cols-2 gap-4", children: [
|
|
8259
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "grid gap-2", children: [
|
|
8260
|
+
/* @__PURE__ */ jsxRuntime.jsx(Label2, { htmlFor: "endDate", children: "End Date" }),
|
|
8261
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
8262
|
+
Input,
|
|
8263
|
+
{
|
|
8264
|
+
id: "endDate",
|
|
8265
|
+
type: "date",
|
|
8266
|
+
value: endDate,
|
|
8267
|
+
onChange: (e) => setEndDate(e.target.value),
|
|
8268
|
+
required: true
|
|
8269
|
+
}
|
|
8270
|
+
)
|
|
8271
|
+
] }),
|
|
8272
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "grid gap-2", children: [
|
|
8273
|
+
/* @__PURE__ */ jsxRuntime.jsx(Label2, { htmlFor: "endTime", children: "End Time" }),
|
|
8274
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
8275
|
+
Input,
|
|
8276
|
+
{
|
|
8277
|
+
id: "endTime",
|
|
8278
|
+
type: "time",
|
|
8279
|
+
value: endTime,
|
|
8280
|
+
onChange: (e) => setEndTime(e.target.value),
|
|
8281
|
+
required: true
|
|
8282
|
+
}
|
|
8283
|
+
)
|
|
8284
|
+
] })
|
|
8285
|
+
] }),
|
|
8286
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "grid grid-cols-2 gap-4", children: [
|
|
8287
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "grid gap-2", children: [
|
|
8288
|
+
/* @__PURE__ */ jsxRuntime.jsx(Label2, { children: "Color" }),
|
|
8289
|
+
/* @__PURE__ */ jsxRuntime.jsxs(Select, { value: color, onValueChange: (v) => setColor(v), children: [
|
|
8290
|
+
/* @__PURE__ */ jsxRuntime.jsx(SelectTrigger, { children: /* @__PURE__ */ jsxRuntime.jsx(SelectValue, { children: /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center gap-2", children: [
|
|
8291
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
8292
|
+
"span",
|
|
8293
|
+
{
|
|
8294
|
+
className: cn(
|
|
8295
|
+
"size-3 rounded-full",
|
|
8296
|
+
EVENT_COLORS2.find((c) => c.value === color)?.className
|
|
8297
|
+
)
|
|
8298
|
+
}
|
|
8299
|
+
),
|
|
8300
|
+
EVENT_COLORS2.find((c) => c.value === color)?.label
|
|
8301
|
+
] }) }) }),
|
|
8302
|
+
/* @__PURE__ */ jsxRuntime.jsx(SelectContent, { children: EVENT_COLORS2.map((c) => /* @__PURE__ */ jsxRuntime.jsx(SelectItem, { value: c.value, children: /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center gap-2", children: [
|
|
8303
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { className: cn("size-3 rounded-full", c.className) }),
|
|
8304
|
+
c.label
|
|
8305
|
+
] }) }, c.value)) })
|
|
8306
|
+
] })
|
|
8307
|
+
] }),
|
|
8308
|
+
users.length > 0 && /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "grid gap-2", children: [
|
|
8309
|
+
/* @__PURE__ */ jsxRuntime.jsx(Label2, { children: "Assignee" }),
|
|
8310
|
+
/* @__PURE__ */ jsxRuntime.jsxs(Select, { value: userId, onValueChange: setUserId, children: [
|
|
8311
|
+
/* @__PURE__ */ jsxRuntime.jsx(SelectTrigger, { children: /* @__PURE__ */ jsxRuntime.jsx(SelectValue, { placeholder: "Select user" }) }),
|
|
8312
|
+
/* @__PURE__ */ jsxRuntime.jsx(SelectContent, { children: users.map((user) => /* @__PURE__ */ jsxRuntime.jsx(SelectItem, { value: user.id, children: user.name }, user.id)) })
|
|
8313
|
+
] })
|
|
8314
|
+
] })
|
|
8315
|
+
] })
|
|
8316
|
+
] }),
|
|
8317
|
+
/* @__PURE__ */ jsxRuntime.jsxs(DialogFooter, { className: "flex-row justify-between gap-2", children: [
|
|
8318
|
+
mode === "edit" ? /* @__PURE__ */ jsxRuntime.jsx(
|
|
8319
|
+
Button,
|
|
8320
|
+
{
|
|
8321
|
+
type: "button",
|
|
8322
|
+
variant: "destructive",
|
|
8323
|
+
onClick: handleDelete,
|
|
8324
|
+
disabled: isSubmitting,
|
|
8325
|
+
children: "Delete"
|
|
8326
|
+
}
|
|
8327
|
+
) : /* @__PURE__ */ jsxRuntime.jsx("div", {}),
|
|
8328
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex gap-2", children: [
|
|
8329
|
+
/* @__PURE__ */ jsxRuntime.jsx(Button, { type: "button", variant: "outline", onClick: () => onOpenChange(false), children: "Cancel" }),
|
|
8330
|
+
/* @__PURE__ */ jsxRuntime.jsx(Button, { type: "submit", disabled: isSubmitting || !title.trim(), children: isSubmitting ? "Saving..." : mode === "edit" ? "Save Changes" : "Add Event" })
|
|
8331
|
+
] })
|
|
8332
|
+
] })
|
|
8333
|
+
] }) }) });
|
|
8334
|
+
}
|
|
8335
|
+
function QuickAddEvent({
|
|
8336
|
+
date,
|
|
8337
|
+
onAdd,
|
|
8338
|
+
onOpenDialog,
|
|
8339
|
+
onClose
|
|
8340
|
+
}) {
|
|
8341
|
+
const [title, setTitle] = React14__namespace.useState("");
|
|
8342
|
+
const { users } = useEventCalendar();
|
|
8343
|
+
const handleSubmit = (e) => {
|
|
8344
|
+
e.preventDefault();
|
|
8345
|
+
if (!title.trim()) return;
|
|
8346
|
+
const end = dateFns.setMinutes(dateFns.setHours(date, date.getHours() + 1), 0);
|
|
8347
|
+
onAdd({
|
|
8348
|
+
title,
|
|
8349
|
+
description: "",
|
|
8350
|
+
startDate: date.toISOString(),
|
|
8351
|
+
endDate: end.toISOString(),
|
|
8352
|
+
color: "blue",
|
|
8353
|
+
user: {
|
|
8354
|
+
id: users[0]?.id || "",
|
|
8355
|
+
name: users[0]?.name || "Unknown"
|
|
8356
|
+
}
|
|
8357
|
+
});
|
|
8358
|
+
onClose();
|
|
8359
|
+
};
|
|
8360
|
+
return /* @__PURE__ */ jsxRuntime.jsxs("form", { onSubmit: handleSubmit, className: "flex flex-col gap-2 p-3", children: [
|
|
8361
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "text-xs text-muted-foreground", children: dateFns.format(date, "EEE, MMM d, h:mm a") }),
|
|
8362
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
8363
|
+
Input,
|
|
8364
|
+
{
|
|
8365
|
+
value: title,
|
|
8366
|
+
onChange: (e) => setTitle(e.target.value),
|
|
8367
|
+
placeholder: "Add title",
|
|
8368
|
+
className: "h-8",
|
|
8369
|
+
autoFocus: true
|
|
8370
|
+
}
|
|
8371
|
+
),
|
|
8372
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex gap-2", children: [
|
|
8373
|
+
/* @__PURE__ */ jsxRuntime.jsx(Button, { type: "submit", size: "sm", disabled: !title.trim(), children: "Add" }),
|
|
8374
|
+
/* @__PURE__ */ jsxRuntime.jsx(Button, { type: "button", variant: "outline", size: "sm", onClick: onOpenDialog, children: "More options" })
|
|
8375
|
+
] })
|
|
8376
|
+
] });
|
|
8377
|
+
}
|
|
8378
|
+
function ChangeBadgeVariantInput() {
|
|
8379
|
+
const { badgeVariant, setBadgeVariant } = useEventCalendar();
|
|
8380
|
+
return /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "space-y-2", children: [
|
|
8381
|
+
/* @__PURE__ */ jsxRuntime.jsx("p", { className: "text-sm font-semibold", children: "Change badge variant" }),
|
|
8382
|
+
/* @__PURE__ */ jsxRuntime.jsxs(
|
|
8383
|
+
Select,
|
|
8384
|
+
{
|
|
8385
|
+
value: badgeVariant,
|
|
8386
|
+
onValueChange: (value) => setBadgeVariant(value),
|
|
8387
|
+
children: [
|
|
8388
|
+
/* @__PURE__ */ jsxRuntime.jsx(SelectTrigger, { className: "w-48", children: /* @__PURE__ */ jsxRuntime.jsx(SelectValue, {}) }),
|
|
8389
|
+
/* @__PURE__ */ jsxRuntime.jsxs(SelectContent, { children: [
|
|
8390
|
+
/* @__PURE__ */ jsxRuntime.jsx(SelectItem, { value: "dot", children: "Dot" }),
|
|
8391
|
+
/* @__PURE__ */ jsxRuntime.jsx(SelectItem, { value: "colored", children: "Colored" }),
|
|
8392
|
+
/* @__PURE__ */ jsxRuntime.jsx(SelectItem, { value: "mixed", children: "Mixed" })
|
|
8393
|
+
] })
|
|
8394
|
+
]
|
|
8395
|
+
}
|
|
8396
|
+
)
|
|
8397
|
+
] });
|
|
8398
|
+
}
|
|
8399
|
+
var HOUR_OPTIONS = Array.from({ length: 25 }, (_, i) => {
|
|
8400
|
+
if (i === 0) return { value: "0", label: "12 AM" };
|
|
8401
|
+
if (i === 12) return { value: "12", label: "12 PM" };
|
|
8402
|
+
if (i === 24) return { value: "24", label: "12 AM (next)" };
|
|
8403
|
+
if (i < 12) return { value: String(i), label: `${i} AM` };
|
|
8404
|
+
return { value: String(i), label: `${i - 12} PM` };
|
|
8405
|
+
});
|
|
8406
|
+
function ChangeVisibleHoursInput() {
|
|
8407
|
+
const { visibleHours, setVisibleHours } = useEventCalendar();
|
|
8408
|
+
const [from, setFrom] = React14__namespace.useState(visibleHours.from);
|
|
8409
|
+
const [to, setTo] = React14__namespace.useState(visibleHours.to);
|
|
8410
|
+
const handleApply = () => {
|
|
8411
|
+
const toHour = to === 0 ? 24 : to;
|
|
8412
|
+
setVisibleHours({ from, to: toHour });
|
|
8413
|
+
};
|
|
8414
|
+
return /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex flex-col gap-2", children: [
|
|
8415
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center gap-2", children: [
|
|
8416
|
+
/* @__PURE__ */ jsxRuntime.jsx("p", { className: "text-sm font-semibold", children: "Change visible hours" }),
|
|
8417
|
+
/* @__PURE__ */ jsxRuntime.jsx(TooltipProvider, { delayDuration: 100, children: /* @__PURE__ */ jsxRuntime.jsxs(Tooltip2, { children: [
|
|
8418
|
+
/* @__PURE__ */ jsxRuntime.jsx(TooltipTrigger, { children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Info, { className: "size-3" }) }),
|
|
8419
|
+
/* @__PURE__ */ jsxRuntime.jsx(TooltipContent, { className: "max-w-80 text-center", children: /* @__PURE__ */ jsxRuntime.jsx("p", { children: "If an event falls outside the specified visible hours, the visible hours will automatically adjust to include that event." }) })
|
|
8420
|
+
] }) })
|
|
8421
|
+
] }),
|
|
8422
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center gap-4", children: [
|
|
8423
|
+
/* @__PURE__ */ jsxRuntime.jsx("p", { children: "From" }),
|
|
8424
|
+
/* @__PURE__ */ jsxRuntime.jsxs(Select, { value: String(from), onValueChange: (v) => setFrom(Number(v)), children: [
|
|
8425
|
+
/* @__PURE__ */ jsxRuntime.jsx(SelectTrigger, { className: "w-28", children: /* @__PURE__ */ jsxRuntime.jsx(SelectValue, {}) }),
|
|
8426
|
+
/* @__PURE__ */ jsxRuntime.jsx(SelectContent, { children: HOUR_OPTIONS.slice(0, 24).map((option) => /* @__PURE__ */ jsxRuntime.jsx(SelectItem, { value: option.value, children: option.label }, option.value)) })
|
|
8427
|
+
] }),
|
|
8428
|
+
/* @__PURE__ */ jsxRuntime.jsx("p", { children: "To" }),
|
|
8429
|
+
/* @__PURE__ */ jsxRuntime.jsxs(Select, { value: String(to), onValueChange: (v) => setTo(Number(v)), children: [
|
|
8430
|
+
/* @__PURE__ */ jsxRuntime.jsx(SelectTrigger, { className: "w-28", children: /* @__PURE__ */ jsxRuntime.jsx(SelectValue, {}) }),
|
|
8431
|
+
/* @__PURE__ */ jsxRuntime.jsx(SelectContent, { children: HOUR_OPTIONS.slice(1).map((option) => /* @__PURE__ */ jsxRuntime.jsx(SelectItem, { value: option.value, children: option.label }, option.value)) })
|
|
8432
|
+
] })
|
|
8433
|
+
] }),
|
|
8434
|
+
/* @__PURE__ */ jsxRuntime.jsx(Button, { className: "mt-4 w-fit", onClick: handleApply, children: "Apply" })
|
|
8435
|
+
] });
|
|
8436
|
+
}
|
|
8437
|
+
var DAYS_OF_WEEK = [
|
|
8438
|
+
{ index: 0, name: "Sunday" },
|
|
8439
|
+
{ index: 1, name: "Monday" },
|
|
8440
|
+
{ index: 2, name: "Tuesday" },
|
|
8441
|
+
{ index: 3, name: "Wednesday" },
|
|
8442
|
+
{ index: 4, name: "Thursday" },
|
|
8443
|
+
{ index: 5, name: "Friday" },
|
|
8444
|
+
{ index: 6, name: "Saturday" }
|
|
8445
|
+
];
|
|
8446
|
+
var HOUR_OPTIONS2 = Array.from({ length: 25 }, (_, i) => {
|
|
8447
|
+
if (i === 0) return { value: "0", label: "12 AM" };
|
|
8448
|
+
if (i === 12) return { value: "12", label: "12 PM" };
|
|
8449
|
+
if (i === 24) return { value: "24", label: "12 AM (next)" };
|
|
8450
|
+
if (i < 12) return { value: String(i), label: `${i} AM` };
|
|
8451
|
+
return { value: String(i), label: `${i - 12} PM` };
|
|
8452
|
+
});
|
|
8453
|
+
function ChangeWorkingHoursInput() {
|
|
8454
|
+
const { workingHours, setWorkingHours } = useEventCalendar();
|
|
8455
|
+
const [localWorkingHours, setLocalWorkingHours] = React14__namespace.useState({
|
|
8456
|
+
...workingHours
|
|
8457
|
+
});
|
|
8458
|
+
const handleToggleDay = (dayId) => {
|
|
8459
|
+
setLocalWorkingHours((prev) => ({
|
|
8460
|
+
...prev,
|
|
8461
|
+
[dayId]: prev[dayId].from > 0 || prev[dayId].to > 0 ? { from: 0, to: 0 } : { from: 9, to: 17 }
|
|
8462
|
+
}));
|
|
8463
|
+
};
|
|
8464
|
+
const handleTimeChange = (dayId, timeType, value) => {
|
|
8465
|
+
const hour = Number(value);
|
|
8466
|
+
setLocalWorkingHours((prev) => {
|
|
8467
|
+
const updatedDay = { ...prev[dayId], [timeType]: hour };
|
|
8468
|
+
if (timeType === "to" && hour === 0 && updatedDay.from === 0) {
|
|
8469
|
+
updatedDay.to = 24;
|
|
8470
|
+
}
|
|
8471
|
+
return { ...prev, [dayId]: updatedDay };
|
|
8472
|
+
});
|
|
8473
|
+
};
|
|
8474
|
+
const handleSave = () => {
|
|
8475
|
+
const updatedWorkingHours = { ...localWorkingHours };
|
|
8476
|
+
for (const dayId in updatedWorkingHours) {
|
|
8477
|
+
const day = updatedWorkingHours[parseInt(dayId)];
|
|
8478
|
+
const isDayActive = localWorkingHours[parseInt(dayId)].from > 0 || localWorkingHours[parseInt(dayId)].to > 0;
|
|
8479
|
+
if (isDayActive) {
|
|
8480
|
+
if (day.from === 0 && day.to === 0) {
|
|
8481
|
+
updatedWorkingHours[dayId] = { from: 0, to: 24 };
|
|
8482
|
+
} else if (day.to === 0 && day.from > 0) {
|
|
8483
|
+
updatedWorkingHours[dayId] = { ...day, to: 24 };
|
|
8484
|
+
}
|
|
8485
|
+
} else {
|
|
8486
|
+
updatedWorkingHours[dayId] = { from: 0, to: 0 };
|
|
8487
|
+
}
|
|
8488
|
+
}
|
|
8489
|
+
setWorkingHours(updatedWorkingHours);
|
|
8490
|
+
};
|
|
8491
|
+
return /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex flex-col gap-2", children: [
|
|
8492
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center gap-2", children: [
|
|
8493
|
+
/* @__PURE__ */ jsxRuntime.jsx("p", { className: "text-sm font-semibold", children: "Change working hours" }),
|
|
8494
|
+
/* @__PURE__ */ jsxRuntime.jsx(TooltipProvider, { delayDuration: 100, children: /* @__PURE__ */ jsxRuntime.jsxs(Tooltip2, { children: [
|
|
8495
|
+
/* @__PURE__ */ jsxRuntime.jsx(TooltipTrigger, { children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Info, { className: "size-3" }) }),
|
|
8496
|
+
/* @__PURE__ */ jsxRuntime.jsx(TooltipContent, { className: "max-w-80 text-center", children: /* @__PURE__ */ jsxRuntime.jsx("p", { children: "This will apply a dashed background to the hour cells that fall outside the working hours \u2014 only for week and day views." }) })
|
|
8497
|
+
] }) })
|
|
8498
|
+
] }),
|
|
8499
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "space-y-3", children: DAYS_OF_WEEK.map((day) => {
|
|
8500
|
+
const isDayActive = localWorkingHours[day.index].from > 0 || localWorkingHours[day.index].to > 0;
|
|
8501
|
+
return /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex flex-wrap items-center gap-2 sm:gap-4", children: [
|
|
8502
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex w-32 items-center gap-2 sm:w-36", children: [
|
|
8503
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
8504
|
+
Switch,
|
|
8505
|
+
{
|
|
8506
|
+
checked: isDayActive,
|
|
8507
|
+
onCheckedChange: () => handleToggleDay(day.index)
|
|
8508
|
+
}
|
|
8509
|
+
),
|
|
8510
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "text-sm font-medium", children: day.name.slice(0, 3) })
|
|
8511
|
+
] }),
|
|
8512
|
+
isDayActive ? /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex flex-wrap items-center gap-2", children: [
|
|
8513
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center gap-1", children: [
|
|
8514
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "text-sm", children: "From" }),
|
|
8515
|
+
/* @__PURE__ */ jsxRuntime.jsxs(
|
|
8516
|
+
Select,
|
|
8517
|
+
{
|
|
8518
|
+
value: String(localWorkingHours[day.index].from),
|
|
8519
|
+
onValueChange: (v) => handleTimeChange(day.index, "from", v),
|
|
8520
|
+
children: [
|
|
8521
|
+
/* @__PURE__ */ jsxRuntime.jsx(SelectTrigger, { className: "w-24", children: /* @__PURE__ */ jsxRuntime.jsx(SelectValue, {}) }),
|
|
8522
|
+
/* @__PURE__ */ jsxRuntime.jsx(SelectContent, { children: HOUR_OPTIONS2.slice(0, 24).map((option) => /* @__PURE__ */ jsxRuntime.jsx(SelectItem, { value: option.value, children: option.label }, option.value)) })
|
|
8523
|
+
]
|
|
8524
|
+
}
|
|
8525
|
+
)
|
|
8526
|
+
] }),
|
|
8527
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center gap-1", children: [
|
|
8528
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "text-sm", children: "To" }),
|
|
8529
|
+
/* @__PURE__ */ jsxRuntime.jsxs(
|
|
8530
|
+
Select,
|
|
8531
|
+
{
|
|
8532
|
+
value: String(localWorkingHours[day.index].to),
|
|
8533
|
+
onValueChange: (v) => handleTimeChange(day.index, "to", v),
|
|
8534
|
+
children: [
|
|
8535
|
+
/* @__PURE__ */ jsxRuntime.jsx(SelectTrigger, { className: "w-24", children: /* @__PURE__ */ jsxRuntime.jsx(SelectValue, {}) }),
|
|
8536
|
+
/* @__PURE__ */ jsxRuntime.jsx(SelectContent, { children: HOUR_OPTIONS2.slice(1).map((option) => /* @__PURE__ */ jsxRuntime.jsx(SelectItem, { value: option.value, children: option.label }, option.value)) })
|
|
8537
|
+
]
|
|
8538
|
+
}
|
|
8539
|
+
)
|
|
8540
|
+
] })
|
|
8541
|
+
] }) : /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center gap-2 text-muted-foreground", children: [
|
|
8542
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.Moon, { className: "size-4" }),
|
|
8543
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "text-sm", children: "Closed" })
|
|
8544
|
+
] })
|
|
8545
|
+
] }, day.index);
|
|
8546
|
+
}) }),
|
|
8547
|
+
/* @__PURE__ */ jsxRuntime.jsx(Button, { className: "mt-4 w-fit", onClick: handleSave, children: "Apply" })
|
|
8548
|
+
] });
|
|
8549
|
+
}
|
|
8550
|
+
function CalendarSettingsPanel({
|
|
8551
|
+
className,
|
|
8552
|
+
showBadgeVariant = true,
|
|
8553
|
+
showVisibleHours = true,
|
|
8554
|
+
showWorkingHours = true
|
|
8555
|
+
}) {
|
|
8556
|
+
return /* @__PURE__ */ jsxRuntime.jsx(Accordion, { type: "single", collapsible: true, className: cn("relative z-10 bg-background", className), children: /* @__PURE__ */ jsxRuntime.jsxs(AccordionItem, { value: "settings", className: "border-none", children: [
|
|
8557
|
+
/* @__PURE__ */ jsxRuntime.jsx(AccordionTrigger, { className: "flex-none gap-2 py-0 hover:no-underline", children: /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center gap-2", children: [
|
|
8558
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.Settings, { className: "size-4" }),
|
|
8559
|
+
/* @__PURE__ */ jsxRuntime.jsx("p", { className: "text-base font-semibold", children: "Calendar settings" })
|
|
8560
|
+
] }) }),
|
|
8561
|
+
/* @__PURE__ */ jsxRuntime.jsx(AccordionContent, { children: /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "mt-4 flex flex-col gap-6", children: [
|
|
8562
|
+
showBadgeVariant && /* @__PURE__ */ jsxRuntime.jsx(ChangeBadgeVariantInput, {}),
|
|
8563
|
+
showVisibleHours && /* @__PURE__ */ jsxRuntime.jsx(ChangeVisibleHoursInput, {}),
|
|
8564
|
+
showWorkingHours && /* @__PURE__ */ jsxRuntime.jsx(ChangeWorkingHoursInput, {})
|
|
8565
|
+
] }) })
|
|
8566
|
+
] }) });
|
|
8567
|
+
}
|
|
8568
|
+
function useMediaQuery(query) {
|
|
8569
|
+
const [matches, setMatches] = React14__namespace.useState(false);
|
|
8570
|
+
React14__namespace.useEffect(() => {
|
|
8571
|
+
const media = window.matchMedia(query);
|
|
8572
|
+
setMatches(media.matches);
|
|
8573
|
+
const listener = (event) => {
|
|
8574
|
+
setMatches(event.matches);
|
|
8575
|
+
};
|
|
8576
|
+
media.addEventListener("change", listener);
|
|
8577
|
+
return () => media.removeEventListener("change", listener);
|
|
8578
|
+
}, [query]);
|
|
8579
|
+
return matches;
|
|
8580
|
+
}
|
|
8581
|
+
function BigCalendar({
|
|
8582
|
+
className,
|
|
8583
|
+
compact = "auto",
|
|
8584
|
+
bordered = true,
|
|
8585
|
+
showHeader = true,
|
|
8586
|
+
showAddButton = true,
|
|
8587
|
+
showSettings = true,
|
|
8588
|
+
enableDragDrop = true,
|
|
8589
|
+
weekStartsOn = 0,
|
|
8590
|
+
maxEventsPerDay = 3,
|
|
8591
|
+
config,
|
|
8592
|
+
...providerProps
|
|
8593
|
+
}) {
|
|
8594
|
+
return /* @__PURE__ */ jsxRuntime.jsx(EventCalendarProvider, { ...providerProps, children: /* @__PURE__ */ jsxRuntime.jsx(DragProvider, { children: /* @__PURE__ */ jsxRuntime.jsx(
|
|
8595
|
+
BigCalendarInner,
|
|
8596
|
+
{
|
|
8597
|
+
className,
|
|
8598
|
+
compact,
|
|
8599
|
+
bordered,
|
|
8600
|
+
showHeader,
|
|
8601
|
+
showAddButton,
|
|
8602
|
+
showSettings,
|
|
8603
|
+
enableDragDrop,
|
|
8604
|
+
weekStartsOn,
|
|
8605
|
+
maxEventsPerDay,
|
|
8606
|
+
config
|
|
8607
|
+
}
|
|
8608
|
+
) }) });
|
|
8609
|
+
}
|
|
8610
|
+
function BigCalendarInner({
|
|
8611
|
+
className,
|
|
8612
|
+
compact,
|
|
8613
|
+
bordered,
|
|
8614
|
+
showHeader,
|
|
8615
|
+
showAddButton,
|
|
8616
|
+
showSettings,
|
|
8617
|
+
enableDragDrop,
|
|
8618
|
+
weekStartsOn,
|
|
8619
|
+
maxEventsPerDay
|
|
8620
|
+
}) {
|
|
8621
|
+
const { view, setView } = useEventCalendar();
|
|
8622
|
+
const [dialogOpen, setDialogOpen] = React14__namespace.useState(false);
|
|
8623
|
+
const [selectedEvent, setSelectedEvent] = React14__namespace.useState(null);
|
|
8624
|
+
const [dialogMode, setDialogMode] = React14__namespace.useState("add");
|
|
8625
|
+
const [defaultDate, setDefaultDate] = React14__namespace.useState(/* @__PURE__ */ new Date());
|
|
8626
|
+
const isMobile = useMediaQuery("(max-width: 768px)");
|
|
8627
|
+
const isCompact = compact === "auto" ? isMobile : compact;
|
|
8628
|
+
const handleAddClick = () => {
|
|
8629
|
+
setSelectedEvent(null);
|
|
8630
|
+
setDialogMode("add");
|
|
8631
|
+
setDefaultDate(/* @__PURE__ */ new Date());
|
|
8632
|
+
setDialogOpen(true);
|
|
8633
|
+
};
|
|
8634
|
+
const handleEventClick = (event) => {
|
|
8635
|
+
setSelectedEvent(event);
|
|
8636
|
+
setDialogMode("edit");
|
|
8637
|
+
setDialogOpen(true);
|
|
8638
|
+
};
|
|
8639
|
+
const handleDateClick = (date) => {
|
|
8640
|
+
setDefaultDate(date);
|
|
8641
|
+
};
|
|
8642
|
+
const handleMoreClick = (date, events) => {
|
|
8643
|
+
setDefaultDate(date);
|
|
8644
|
+
setView("day");
|
|
8645
|
+
};
|
|
8646
|
+
const handleTimeClick = (date, hour, minute) => {
|
|
8647
|
+
setSelectedEvent(null);
|
|
8648
|
+
setDialogMode("add");
|
|
8649
|
+
const clickedDate = new Date(date);
|
|
8650
|
+
clickedDate.setHours(hour, minute, 0, 0);
|
|
8651
|
+
setDefaultDate(clickedDate);
|
|
8652
|
+
setDialogOpen(true);
|
|
8653
|
+
};
|
|
8654
|
+
const Wrapper = bordered ? Card : "div";
|
|
8655
|
+
const Content14 = bordered ? CardContent : "div";
|
|
8656
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
|
|
8657
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: cn("flex flex-col gap-4 relative", className), children: [
|
|
8658
|
+
/* @__PURE__ */ jsxRuntime.jsxs(
|
|
8659
|
+
Wrapper,
|
|
8660
|
+
{
|
|
8661
|
+
className: cn(
|
|
8662
|
+
"flex min-h-[600px] flex-col overflow-hidden rounded-sm",
|
|
8663
|
+
!bordered && "border border-border bg-card"
|
|
8664
|
+
),
|
|
8665
|
+
children: [
|
|
8666
|
+
showHeader && (isCompact ? /* @__PURE__ */ jsxRuntime.jsx(
|
|
8667
|
+
CalendarHeaderCompact,
|
|
8668
|
+
{
|
|
8669
|
+
showAddButton,
|
|
8670
|
+
onAddClick: handleAddClick
|
|
8671
|
+
}
|
|
8672
|
+
) : /* @__PURE__ */ jsxRuntime.jsx(
|
|
8673
|
+
CalendarHeader,
|
|
8674
|
+
{
|
|
8675
|
+
showAddButton,
|
|
8676
|
+
onAddClick: handleAddClick
|
|
8677
|
+
}
|
|
8678
|
+
)),
|
|
8679
|
+
/* @__PURE__ */ jsxRuntime.jsx(Content14, { className: cn("flex-1 overflow-hidden", bordered ? "p-0" : ""), children: /* @__PURE__ */ jsxRuntime.jsx(
|
|
8680
|
+
CalendarView,
|
|
8681
|
+
{
|
|
8682
|
+
view,
|
|
8683
|
+
weekStartsOn,
|
|
8684
|
+
maxEventsPerDay,
|
|
8685
|
+
onEventClick: handleEventClick,
|
|
8686
|
+
onDateClick: handleDateClick,
|
|
8687
|
+
onMoreClick: handleMoreClick,
|
|
8688
|
+
onTimeClick: handleTimeClick
|
|
8689
|
+
}
|
|
8690
|
+
) })
|
|
8691
|
+
]
|
|
8692
|
+
}
|
|
8693
|
+
),
|
|
8694
|
+
showSettings && /* @__PURE__ */ jsxRuntime.jsx(CalendarSettingsPanel, {})
|
|
8695
|
+
] }),
|
|
8696
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
8697
|
+
EventDialog,
|
|
8698
|
+
{
|
|
8699
|
+
open: dialogOpen,
|
|
8700
|
+
onOpenChange: setDialogOpen,
|
|
8701
|
+
mode: dialogMode,
|
|
8702
|
+
event: selectedEvent,
|
|
8703
|
+
defaultDate
|
|
8704
|
+
}
|
|
8705
|
+
)
|
|
8706
|
+
] });
|
|
8707
|
+
}
|
|
8708
|
+
function CalendarView({
|
|
8709
|
+
view,
|
|
8710
|
+
weekStartsOn,
|
|
8711
|
+
maxEventsPerDay,
|
|
8712
|
+
onEventClick,
|
|
8713
|
+
onDateClick,
|
|
8714
|
+
onMoreClick,
|
|
8715
|
+
onTimeClick
|
|
8716
|
+
}) {
|
|
8717
|
+
switch (view) {
|
|
8718
|
+
case "month":
|
|
8719
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
8720
|
+
MonthView,
|
|
8721
|
+
{
|
|
8722
|
+
className: "h-full",
|
|
8723
|
+
weekStartsOn,
|
|
8724
|
+
maxEventsPerDay,
|
|
8725
|
+
onEventClick,
|
|
8726
|
+
onDateClick,
|
|
8727
|
+
onMoreClick
|
|
8728
|
+
}
|
|
8729
|
+
);
|
|
8730
|
+
case "week":
|
|
8731
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
8732
|
+
WeekView,
|
|
8733
|
+
{
|
|
8734
|
+
className: "h-full",
|
|
8735
|
+
weekStartsOn,
|
|
8736
|
+
onEventClick,
|
|
8737
|
+
onDateClick,
|
|
8738
|
+
onTimeClick
|
|
8739
|
+
}
|
|
8740
|
+
);
|
|
8741
|
+
case "day":
|
|
8742
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
8743
|
+
DayView,
|
|
8744
|
+
{
|
|
8745
|
+
className: "h-full",
|
|
8746
|
+
onEventClick,
|
|
8747
|
+
onTimeClick
|
|
8748
|
+
}
|
|
8749
|
+
);
|
|
8750
|
+
case "year":
|
|
8751
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
8752
|
+
YearView,
|
|
8753
|
+
{
|
|
8754
|
+
className: "h-full",
|
|
8755
|
+
weekStartsOn,
|
|
8756
|
+
onDateClick
|
|
8757
|
+
}
|
|
8758
|
+
);
|
|
8759
|
+
case "agenda":
|
|
8760
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
8761
|
+
AgendaView,
|
|
8762
|
+
{
|
|
8763
|
+
className: "h-full",
|
|
8764
|
+
onEventClick,
|
|
8765
|
+
onDateClick
|
|
8766
|
+
}
|
|
8767
|
+
);
|
|
8768
|
+
default:
|
|
8769
|
+
return null;
|
|
8770
|
+
}
|
|
8771
|
+
}
|
|
8772
|
+
|
|
8773
|
+
Object.defineProperty(exports, "areIntervalsOverlapping", {
|
|
8774
|
+
enumerable: true,
|
|
8775
|
+
get: function () { return dateFns.areIntervalsOverlapping; }
|
|
8776
|
+
});
|
|
8777
|
+
Object.defineProperty(exports, "format", {
|
|
8778
|
+
enumerable: true,
|
|
8779
|
+
get: function () { return dateFns.format; }
|
|
8780
|
+
});
|
|
8781
|
+
Object.defineProperty(exports, "getDay", {
|
|
8782
|
+
enumerable: true,
|
|
8783
|
+
get: function () { return dateFns.getDay; }
|
|
8784
|
+
});
|
|
8785
|
+
Object.defineProperty(exports, "isSameDay", {
|
|
8786
|
+
enumerable: true,
|
|
8787
|
+
get: function () { return dateFns.isSameDay; }
|
|
8788
|
+
});
|
|
8789
|
+
Object.defineProperty(exports, "isSameMonth", {
|
|
8790
|
+
enumerable: true,
|
|
8791
|
+
get: function () { return dateFns.isSameMonth; }
|
|
8792
|
+
});
|
|
8793
|
+
Object.defineProperty(exports, "isToday", {
|
|
8794
|
+
enumerable: true,
|
|
8795
|
+
get: function () { return dateFns.isToday; }
|
|
8796
|
+
});
|
|
8797
|
+
Object.defineProperty(exports, "parseISO", {
|
|
8798
|
+
enumerable: true,
|
|
8799
|
+
get: function () { return dateFns.parseISO; }
|
|
8800
|
+
});
|
|
5482
8801
|
exports.Accordion = Accordion;
|
|
5483
8802
|
exports.AccordionContent = AccordionContent;
|
|
5484
8803
|
exports.AccordionItem = AccordionItem;
|
|
5485
8804
|
exports.AccordionTrigger = AccordionTrigger;
|
|
8805
|
+
exports.AgendaView = AgendaView;
|
|
5486
8806
|
exports.Alert = Alert;
|
|
5487
8807
|
exports.AlertDescription = AlertDescription;
|
|
5488
8808
|
exports.AlertDialog = AlertDialog;
|
|
@@ -5501,7 +8821,9 @@ exports.AspectRatio = AspectRatio;
|
|
|
5501
8821
|
exports.Avatar = Avatar;
|
|
5502
8822
|
exports.AvatarFallback = AvatarFallback;
|
|
5503
8823
|
exports.AvatarImage = AvatarImage;
|
|
8824
|
+
exports.BADGE_VARIANT_LABELS = BADGE_VARIANT_LABELS;
|
|
5504
8825
|
exports.Badge = Badge;
|
|
8826
|
+
exports.BigCalendar = BigCalendar;
|
|
5505
8827
|
exports.Breadcrumb = Breadcrumb;
|
|
5506
8828
|
exports.BreadcrumbEllipsis = BreadcrumbEllipsis;
|
|
5507
8829
|
exports.BreadcrumbItem = BreadcrumbItem;
|
|
@@ -5514,7 +8836,11 @@ exports.ButtonGroup = ButtonGroup;
|
|
|
5514
8836
|
exports.ButtonGroupSeparator = ButtonGroupSeparator;
|
|
5515
8837
|
exports.ButtonGroupText = ButtonGroupText;
|
|
5516
8838
|
exports.Calendar = Calendar;
|
|
8839
|
+
exports.CalendarContext = CalendarContext;
|
|
5517
8840
|
exports.CalendarDayButton = CalendarDayButton;
|
|
8841
|
+
exports.CalendarHeader = CalendarHeader;
|
|
8842
|
+
exports.CalendarHeaderCompact = CalendarHeaderCompact;
|
|
8843
|
+
exports.CalendarSettingsPanel = CalendarSettingsPanel;
|
|
5518
8844
|
exports.Card = Card;
|
|
5519
8845
|
exports.CardContent = CardContent;
|
|
5520
8846
|
exports.CardDescription = CardDescription;
|
|
@@ -5526,6 +8852,9 @@ exports.CarouselContent = CarouselContent;
|
|
|
5526
8852
|
exports.CarouselItem = CarouselItem;
|
|
5527
8853
|
exports.CarouselNext = CarouselNext;
|
|
5528
8854
|
exports.CarouselPrevious = CarouselPrevious;
|
|
8855
|
+
exports.ChangeBadgeVariantInput = ChangeBadgeVariantInput;
|
|
8856
|
+
exports.ChangeVisibleHoursInput = ChangeVisibleHoursInput;
|
|
8857
|
+
exports.ChangeWorkingHoursInput = ChangeWorkingHoursInput;
|
|
5529
8858
|
exports.ChartContainer = ChartContainer;
|
|
5530
8859
|
exports.ChartLegend = ChartLegend;
|
|
5531
8860
|
exports.ChartLegendContent = ChartLegendContent;
|
|
@@ -5560,6 +8889,10 @@ exports.ContextMenuSub = ContextMenuSub;
|
|
|
5560
8889
|
exports.ContextMenuSubContent = ContextMenuSubContent;
|
|
5561
8890
|
exports.ContextMenuSubTrigger = ContextMenuSubTrigger;
|
|
5562
8891
|
exports.ContextMenuTrigger = ContextMenuTrigger;
|
|
8892
|
+
exports.DEFAULT_VISIBLE_HOURS = DEFAULT_VISIBLE_HOURS;
|
|
8893
|
+
exports.DEFAULT_WORKING_HOURS = DEFAULT_WORKING_HOURS;
|
|
8894
|
+
exports.DateBadge = DateBadge;
|
|
8895
|
+
exports.DayView = DayView;
|
|
5563
8896
|
exports.Dialog = Dialog;
|
|
5564
8897
|
exports.DialogClose = DialogClose;
|
|
5565
8898
|
exports.DialogContent = DialogContent;
|
|
@@ -5570,6 +8903,9 @@ exports.DialogOverlay = DialogOverlay;
|
|
|
5570
8903
|
exports.DialogPortal = DialogPortal;
|
|
5571
8904
|
exports.DialogTitle = DialogTitle;
|
|
5572
8905
|
exports.DialogTrigger = DialogTrigger;
|
|
8906
|
+
exports.DragContext = DragContext;
|
|
8907
|
+
exports.DragProvider = DragProvider;
|
|
8908
|
+
exports.DraggableEvent = DraggableEvent;
|
|
5573
8909
|
exports.Drawer = Drawer;
|
|
5574
8910
|
exports.DrawerClose = DrawerClose;
|
|
5575
8911
|
exports.DrawerContent = DrawerContent;
|
|
@@ -5595,12 +8931,17 @@ exports.DropdownMenuSub = DropdownMenuSub;
|
|
|
5595
8931
|
exports.DropdownMenuSubContent = DropdownMenuSubContent;
|
|
5596
8932
|
exports.DropdownMenuSubTrigger = DropdownMenuSubTrigger;
|
|
5597
8933
|
exports.DropdownMenuTrigger = DropdownMenuTrigger;
|
|
8934
|
+
exports.DroppableZone = DroppableZone;
|
|
8935
|
+
exports.EVENT_COLORS = EVENT_COLORS;
|
|
5598
8936
|
exports.Empty = Empty;
|
|
5599
8937
|
exports.EmptyContent = EmptyContent;
|
|
5600
8938
|
exports.EmptyDescription = EmptyDescription;
|
|
5601
8939
|
exports.EmptyHeader = EmptyHeader;
|
|
5602
8940
|
exports.EmptyMedia = EmptyMedia;
|
|
5603
8941
|
exports.EmptyTitle = EmptyTitle;
|
|
8942
|
+
exports.EventBadge = EventBadge;
|
|
8943
|
+
exports.EventCalendarProvider = EventCalendarProvider;
|
|
8944
|
+
exports.EventDialog = EventDialog;
|
|
5604
8945
|
exports.Field = Field;
|
|
5605
8946
|
exports.FieldContent = FieldContent;
|
|
5606
8947
|
exports.FieldDescription = FieldDescription;
|
|
@@ -5628,7 +8969,7 @@ exports.InputGroupButton = InputGroupButton;
|
|
|
5628
8969
|
exports.InputGroupInput = InputGroupInput;
|
|
5629
8970
|
exports.InputGroupText = InputGroupText;
|
|
5630
8971
|
exports.InputGroupTextarea = InputGroupTextarea;
|
|
5631
|
-
exports.Item =
|
|
8972
|
+
exports.Item = Item6;
|
|
5632
8973
|
exports.ItemActions = ItemActions;
|
|
5633
8974
|
exports.ItemContent = ItemContent;
|
|
5634
8975
|
exports.ItemDescription = ItemDescription;
|
|
@@ -5657,9 +8998,15 @@ exports.MenubarSub = MenubarSub;
|
|
|
5657
8998
|
exports.MenubarSubContent = MenubarSubContent;
|
|
5658
8999
|
exports.MenubarSubTrigger = MenubarSubTrigger;
|
|
5659
9000
|
exports.MenubarTrigger = MenubarTrigger;
|
|
9001
|
+
exports.MonthView = MonthView;
|
|
9002
|
+
exports.MoreEvents = MoreEvents;
|
|
5660
9003
|
exports.NativeSelect = NativeSelect;
|
|
5661
9004
|
exports.NativeSelectOptGroup = NativeSelectOptGroup;
|
|
5662
9005
|
exports.NativeSelectOption = NativeSelectOption;
|
|
9006
|
+
exports.NavMain = NavMain;
|
|
9007
|
+
exports.NavProjects = NavProjects;
|
|
9008
|
+
exports.NavSecondary = NavSecondary;
|
|
9009
|
+
exports.NavUser = NavUser;
|
|
5663
9010
|
exports.NavigationMenu = NavigationMenu;
|
|
5664
9011
|
exports.NavigationMenuContent = NavigationMenuContent;
|
|
5665
9012
|
exports.NavigationMenuIndicator = NavigationMenuIndicator;
|
|
@@ -5690,6 +9037,7 @@ exports.PopoverAnchor = PopoverAnchor;
|
|
|
5690
9037
|
exports.PopoverContent = PopoverContent;
|
|
5691
9038
|
exports.PopoverTrigger = PopoverTrigger;
|
|
5692
9039
|
exports.Progress = Progress;
|
|
9040
|
+
exports.QuickAddEvent = QuickAddEvent;
|
|
5693
9041
|
exports.RadioGroup = RadioGroup;
|
|
5694
9042
|
exports.RadioGroupItem = RadioGroupItem;
|
|
5695
9043
|
exports.ResizableHandle = ResizableHandle;
|
|
@@ -5697,6 +9045,8 @@ exports.ResizablePanel = ResizablePanel;
|
|
|
5697
9045
|
exports.ResizablePanelGroup = ResizablePanelGroup;
|
|
5698
9046
|
exports.ScrollArea = ScrollArea;
|
|
5699
9047
|
exports.ScrollBar = ScrollBar;
|
|
9048
|
+
exports.SearchForm = SearchForm;
|
|
9049
|
+
exports.SearchTrigger = SearchTrigger;
|
|
5700
9050
|
exports.Section = Section;
|
|
5701
9051
|
exports.SectionContent = SectionContent;
|
|
5702
9052
|
exports.SectionDescription = SectionDescription;
|
|
@@ -5746,6 +9096,7 @@ exports.SidebarProvider = SidebarProvider;
|
|
|
5746
9096
|
exports.SidebarRail = SidebarRail;
|
|
5747
9097
|
exports.SidebarSeparator = SidebarSeparator;
|
|
5748
9098
|
exports.SidebarTrigger = SidebarTrigger;
|
|
9099
|
+
exports.SiteHeader = SiteHeader;
|
|
5749
9100
|
exports.Skeleton = Skeleton;
|
|
5750
9101
|
exports.Slider = Slider;
|
|
5751
9102
|
exports.Spinner = Spinner;
|
|
@@ -5763,6 +9114,7 @@ exports.TabsContent = TabsContent;
|
|
|
5763
9114
|
exports.TabsList = TabsList;
|
|
5764
9115
|
exports.TabsTrigger = TabsTrigger;
|
|
5765
9116
|
exports.Textarea = Textarea;
|
|
9117
|
+
exports.TimeIndicator = TimeIndicator;
|
|
5766
9118
|
exports.Toaster = Toaster;
|
|
5767
9119
|
exports.Toggle = Toggle;
|
|
5768
9120
|
exports.ToggleGroup = ToggleGroup;
|
|
@@ -5775,18 +9127,62 @@ exports.Tooltip = Tooltip2;
|
|
|
5775
9127
|
exports.TooltipContent = TooltipContent;
|
|
5776
9128
|
exports.TooltipProvider = TooltipProvider;
|
|
5777
9129
|
exports.TooltipTrigger = TooltipTrigger;
|
|
9130
|
+
exports.UserAvatarsDropdown = UserAvatarsDropdown;
|
|
9131
|
+
exports.VIEW_LABELS = VIEW_LABELS;
|
|
9132
|
+
exports.WeekView = WeekView;
|
|
9133
|
+
exports.YearView = YearView;
|
|
5778
9134
|
exports.badgeVariants = badgeVariants;
|
|
5779
9135
|
exports.buttonGroupVariants = buttonGroupVariants;
|
|
5780
9136
|
exports.buttonVariants = buttonVariants;
|
|
9137
|
+
exports.calculateDropDates = calculateDropDates;
|
|
9138
|
+
exports.calculateMonthEventPositions = calculateMonthEventPositions;
|
|
5781
9139
|
exports.cardVariants = cardVariants;
|
|
9140
|
+
exports.createDefaultEvent = createDefaultEvent;
|
|
9141
|
+
exports.formatDateRange = formatDateRange;
|
|
9142
|
+
exports.formatTime = formatTime;
|
|
9143
|
+
exports.generateEventId = generateEventId;
|
|
9144
|
+
exports.getCalendarCells = getCalendarCells;
|
|
9145
|
+
exports.getCurrentEvents = getCurrentEvents;
|
|
9146
|
+
exports.getDayHours = getDayHours;
|
|
9147
|
+
exports.getEventBlockStyle = getEventBlockStyle;
|
|
9148
|
+
exports.getEventDuration = getEventDuration;
|
|
9149
|
+
exports.getEventDurationMinutes = getEventDurationMinutes;
|
|
9150
|
+
exports.getEventsCount = getEventsCount;
|
|
9151
|
+
exports.getEventsForDate = getEventsForDate;
|
|
9152
|
+
exports.getEventsInRange = getEventsInRange;
|
|
9153
|
+
exports.getHeaderLabel = getHeaderLabel;
|
|
9154
|
+
exports.getMonthCellEvents = getMonthCellEvents;
|
|
9155
|
+
exports.getMonthDays = getMonthDays;
|
|
9156
|
+
exports.getTimeHeight = getTimeHeight;
|
|
9157
|
+
exports.getTimePosition = getTimePosition;
|
|
9158
|
+
exports.getViewDateRange = getViewDateRange;
|
|
9159
|
+
exports.getVisibleHours = getVisibleHours;
|
|
9160
|
+
exports.getWeekDayNames = getWeekDayNames;
|
|
9161
|
+
exports.getWeekDays = getWeekDays;
|
|
9162
|
+
exports.getYearMonths = getYearMonths;
|
|
9163
|
+
exports.groupEvents = groupEvents;
|
|
9164
|
+
exports.isMultiDayEvent = isMultiDayEvent;
|
|
9165
|
+
exports.isWorkingHour = isWorkingHour;
|
|
9166
|
+
exports.navigateDate = navigateDate;
|
|
5782
9167
|
exports.navigationMenuTriggerStyle = navigationMenuTriggerStyle;
|
|
5783
9168
|
exports.playerCanvasPlayButtonVariants = playerCanvasPlayButtonVariants;
|
|
5784
9169
|
exports.playerCanvasSkipButtonVariants = playerCanvasSkipButtonVariants;
|
|
9170
|
+
exports.rangeText = rangeText;
|
|
5785
9171
|
exports.sectionVariants = sectionVariants;
|
|
9172
|
+
exports.snapToInterval = snapToInterval;
|
|
9173
|
+
exports.sortEvents = sortEvents;
|
|
9174
|
+
exports.splitEventsByDuration = splitEventsByDuration;
|
|
5786
9175
|
exports.toggleVariants = toggleVariants;
|
|
5787
9176
|
exports.toolBarCanvasButtonVariants = toolBarCanvasButtonVariants;
|
|
9177
|
+
exports.useDrag = useDrag;
|
|
9178
|
+
exports.useDraggable = useDraggable;
|
|
9179
|
+
exports.useDroppable = useDroppable;
|
|
9180
|
+
exports.useEventCalendar = useEventCalendar;
|
|
9181
|
+
exports.useEventsInRange = useEventsInRange;
|
|
9182
|
+
exports.useFilteredEvents = useFilteredEvents;
|
|
5788
9183
|
exports.useFormField = useFormField;
|
|
5789
9184
|
exports.useIsMobile = useIsMobile;
|
|
9185
|
+
exports.useSearchShortcut = useSearchShortcut;
|
|
5790
9186
|
exports.useSidebar = useSidebar;
|
|
5791
9187
|
//# sourceMappingURL=index.cjs.map
|
|
5792
9188
|
//# sourceMappingURL=index.cjs.map
|