@melony/react 0.1.24 → 0.1.26
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 +4 -2
- package/dist/index.cjs +772 -458
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +192 -42
- package/dist/index.d.ts +192 -42
- package/dist/index.js +702 -414
- package/dist/index.js.map +1 -1
- package/package.json +2 -2
package/dist/index.js
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
import * as
|
|
2
|
-
import
|
|
1
|
+
import * as React12 from 'react';
|
|
2
|
+
import React12__default, { createContext, useState, useCallback, useEffect, useMemo, useContext, useRef } from 'react';
|
|
3
3
|
import { NuqsAdapter } from 'nuqs/adapters/react';
|
|
4
4
|
import { QueryClient, QueryClientProvider, useQueryClient, useQuery, useMutation } from '@tanstack/react-query';
|
|
5
5
|
import { jsx, jsxs, Fragment } from 'react/jsx-runtime';
|
|
@@ -9,13 +9,13 @@ import { clsx } from 'clsx';
|
|
|
9
9
|
import { twMerge } from 'tailwind-merge';
|
|
10
10
|
import { Button as Button$1 } from '@base-ui/react/button';
|
|
11
11
|
import { cva } from 'class-variance-authority';
|
|
12
|
+
import { mergeProps } from '@base-ui/react/merge-props';
|
|
13
|
+
import { useRender } from '@base-ui/react/use-render';
|
|
12
14
|
import * as ICONS from '@tabler/icons-react';
|
|
13
|
-
import { IconX,
|
|
15
|
+
import { IconPaperclip, IconX, IconPlus, IconChevronDown, IconLoader2, IconArrowUp, IconMessage, IconDotsVertical, IconTrash, IconHistory, IconArrowLeft, IconBrandGoogle, IconLayoutSidebarLeftExpand, IconLayoutSidebarLeftCollapse, IconLayoutSidebarRightExpand, IconLayoutSidebarRightCollapse, IconUser, IconLogout, IconDeviceDesktop, IconMoon, IconSun, IconCheck, IconSelector, IconChevronUp } from '@tabler/icons-react';
|
|
14
16
|
import { Menu } from '@base-ui/react/menu';
|
|
15
17
|
import { Separator as Separator$1 } from '@base-ui/react/separator';
|
|
16
18
|
import { Dialog as Dialog$1 } from '@base-ui/react/dialog';
|
|
17
|
-
import { mergeProps } from '@base-ui/react/merge-props';
|
|
18
|
-
import { useRender } from '@base-ui/react/use-render';
|
|
19
19
|
import { Input as Input$1 } from '@base-ui/react/input';
|
|
20
20
|
import { Select as Select$1 } from '@base-ui/react/select';
|
|
21
21
|
import { createPortal } from 'react-dom';
|
|
@@ -63,14 +63,12 @@ var MelonyContextProviderInner = ({
|
|
|
63
63
|
children,
|
|
64
64
|
client,
|
|
65
65
|
initialEvents,
|
|
66
|
-
configApi,
|
|
67
66
|
setContextValue
|
|
68
67
|
}) => {
|
|
69
68
|
const [state, setState] = useState(client.getState());
|
|
70
69
|
const { data: config } = useQuery({
|
|
71
|
-
queryKey: ["melony-config",
|
|
72
|
-
queryFn: () => client.getConfig(
|
|
73
|
-
enabled: !!configApi,
|
|
70
|
+
queryKey: ["melony-config", client.url],
|
|
71
|
+
queryFn: () => client.getConfig(),
|
|
74
72
|
staleTime: Infinity
|
|
75
73
|
});
|
|
76
74
|
useEffect(() => {
|
|
@@ -85,17 +83,56 @@ var MelonyContextProviderInner = ({
|
|
|
85
83
|
unsubscribe();
|
|
86
84
|
};
|
|
87
85
|
}, [client]);
|
|
86
|
+
const reset = useCallback(
|
|
87
|
+
(events) => client.reset(events),
|
|
88
|
+
[client]
|
|
89
|
+
);
|
|
90
|
+
const dispatchClientAction = useCallback(
|
|
91
|
+
async (event) => {
|
|
92
|
+
if (!event.type.startsWith("client:")) return false;
|
|
93
|
+
switch (event.type) {
|
|
94
|
+
case "client:navigate": {
|
|
95
|
+
const url = event.data?.url;
|
|
96
|
+
if (url) {
|
|
97
|
+
window.history.pushState(null, "", url);
|
|
98
|
+
window.dispatchEvent(new PopStateEvent("popstate"));
|
|
99
|
+
}
|
|
100
|
+
return true;
|
|
101
|
+
}
|
|
102
|
+
case "client:open-url": {
|
|
103
|
+
const { url, target = "_blank" } = event.data || {};
|
|
104
|
+
if (url) {
|
|
105
|
+
window.open(url, target);
|
|
106
|
+
}
|
|
107
|
+
return true;
|
|
108
|
+
}
|
|
109
|
+
case "client:copy": {
|
|
110
|
+
const { text } = event.data || {};
|
|
111
|
+
if (text) {
|
|
112
|
+
await navigator.clipboard.writeText(text);
|
|
113
|
+
}
|
|
114
|
+
return true;
|
|
115
|
+
}
|
|
116
|
+
case "client:reset": {
|
|
117
|
+
reset([]);
|
|
118
|
+
return true;
|
|
119
|
+
}
|
|
120
|
+
default:
|
|
121
|
+
return false;
|
|
122
|
+
}
|
|
123
|
+
},
|
|
124
|
+
[client, reset]
|
|
125
|
+
);
|
|
88
126
|
const sendEvent = useCallback(
|
|
89
127
|
async (event, options) => {
|
|
128
|
+
const handled = await dispatchClientAction(event);
|
|
129
|
+
if (handled) return;
|
|
90
130
|
const generator = client.sendEvent(event, options);
|
|
91
|
-
for await (const
|
|
131
|
+
for await (const incomingEvent of generator) {
|
|
132
|
+
await dispatchClientAction(incomingEvent);
|
|
92
133
|
}
|
|
93
134
|
},
|
|
94
|
-
[client]
|
|
95
|
-
);
|
|
96
|
-
const reset = useCallback(
|
|
97
|
-
(events) => client.reset(events),
|
|
98
|
-
[client]
|
|
135
|
+
[client, dispatchClientAction]
|
|
99
136
|
);
|
|
100
137
|
const value = useMemo(
|
|
101
138
|
() => ({
|
|
@@ -117,8 +154,7 @@ var MelonyClientProvider = ({
|
|
|
117
154
|
children,
|
|
118
155
|
client,
|
|
119
156
|
initialEvents,
|
|
120
|
-
queryClient = defaultQueryClient
|
|
121
|
-
configApi
|
|
157
|
+
queryClient = defaultQueryClient
|
|
122
158
|
}) => {
|
|
123
159
|
const [contextValue, setContextValue] = useState(void 0);
|
|
124
160
|
return /* @__PURE__ */ jsx(MelonyContext.Provider, { value: contextValue, children: /* @__PURE__ */ jsx(QueryClientProvider, { client: queryClient, children: /* @__PURE__ */ jsx(
|
|
@@ -126,7 +162,6 @@ var MelonyClientProvider = ({
|
|
|
126
162
|
{
|
|
127
163
|
client,
|
|
128
164
|
initialEvents,
|
|
129
|
-
configApi,
|
|
130
165
|
setContextValue,
|
|
131
166
|
children
|
|
132
167
|
}
|
|
@@ -377,6 +412,47 @@ var useThreads = () => {
|
|
|
377
412
|
}
|
|
378
413
|
return context;
|
|
379
414
|
};
|
|
415
|
+
function useScreenSize(mobileBreakpoint = 768, tabletBreakpoint = 1024) {
|
|
416
|
+
const [screenSize, setScreenSize] = useState(() => {
|
|
417
|
+
if (typeof window === "undefined") {
|
|
418
|
+
return {
|
|
419
|
+
width: 1024,
|
|
420
|
+
height: 768,
|
|
421
|
+
isMobile: false,
|
|
422
|
+
isTablet: false,
|
|
423
|
+
isDesktop: true
|
|
424
|
+
};
|
|
425
|
+
}
|
|
426
|
+
const width = window.innerWidth;
|
|
427
|
+
return {
|
|
428
|
+
width,
|
|
429
|
+
height: window.innerHeight,
|
|
430
|
+
isMobile: width < mobileBreakpoint,
|
|
431
|
+
isTablet: width >= mobileBreakpoint && width < tabletBreakpoint,
|
|
432
|
+
isDesktop: width >= tabletBreakpoint
|
|
433
|
+
};
|
|
434
|
+
});
|
|
435
|
+
useEffect(() => {
|
|
436
|
+
if (typeof window === "undefined") return;
|
|
437
|
+
const updateScreenSize = () => {
|
|
438
|
+
const width = window.innerWidth;
|
|
439
|
+
const height = window.innerHeight;
|
|
440
|
+
setScreenSize({
|
|
441
|
+
width,
|
|
442
|
+
height,
|
|
443
|
+
isMobile: width < mobileBreakpoint,
|
|
444
|
+
isTablet: width >= mobileBreakpoint && width < tabletBreakpoint,
|
|
445
|
+
isDesktop: width >= tabletBreakpoint
|
|
446
|
+
});
|
|
447
|
+
};
|
|
448
|
+
updateScreenSize();
|
|
449
|
+
window.addEventListener("resize", updateScreenSize);
|
|
450
|
+
return () => {
|
|
451
|
+
window.removeEventListener("resize", updateScreenSize);
|
|
452
|
+
};
|
|
453
|
+
}, [mobileBreakpoint, tabletBreakpoint]);
|
|
454
|
+
return screenSize;
|
|
455
|
+
}
|
|
380
456
|
function cn(...inputs) {
|
|
381
457
|
return twMerge(clsx(inputs));
|
|
382
458
|
}
|
|
@@ -437,6 +513,45 @@ function Textarea({ className, ...props }) {
|
|
|
437
513
|
}
|
|
438
514
|
);
|
|
439
515
|
}
|
|
516
|
+
var badgeVariants = cva(
|
|
517
|
+
"h-5 gap-1 rounded-4xl border border-transparent px-2 py-0.5 text-xs font-medium transition-all has-data-[icon=inline-end]:pr-1.5 has-data-[icon=inline-start]:pl-1.5 [&>svg]:size-3! inline-flex items-center justify-center w-fit whitespace-nowrap shrink-0 [&>svg]:pointer-events-none focus-visible:border-ring focus-visible:ring-ring/50 focus-visible:ring-[3px] aria-invalid:ring-destructive/20 dark:aria-invalid:ring-destructive/40 aria-invalid:border-destructive transition-colors overflow-hidden group/badge",
|
|
518
|
+
{
|
|
519
|
+
variants: {
|
|
520
|
+
variant: {
|
|
521
|
+
default: "bg-primary text-primary-foreground [a]:hover:bg-primary/80",
|
|
522
|
+
secondary: "bg-secondary text-secondary-foreground [a]:hover:bg-secondary/80",
|
|
523
|
+
destructive: "bg-destructive/10 [a]:hover:bg-destructive/20 focus-visible:ring-destructive/20 dark:focus-visible:ring-destructive/40 text-destructive dark:bg-destructive/20",
|
|
524
|
+
outline: "border-border text-foreground [a]:hover:bg-muted [a]:hover:text-muted-foreground bg-input/30",
|
|
525
|
+
ghost: "hover:bg-muted hover:text-muted-foreground dark:hover:bg-muted/50",
|
|
526
|
+
link: "text-primary underline-offset-4 hover:underline"
|
|
527
|
+
}
|
|
528
|
+
},
|
|
529
|
+
defaultVariants: {
|
|
530
|
+
variant: "default"
|
|
531
|
+
}
|
|
532
|
+
}
|
|
533
|
+
);
|
|
534
|
+
function Badge({
|
|
535
|
+
className,
|
|
536
|
+
variant = "default",
|
|
537
|
+
render,
|
|
538
|
+
...props
|
|
539
|
+
}) {
|
|
540
|
+
return useRender({
|
|
541
|
+
defaultTagName: "span",
|
|
542
|
+
props: mergeProps(
|
|
543
|
+
{
|
|
544
|
+
className: cn(badgeVariants({ className, variant }))
|
|
545
|
+
},
|
|
546
|
+
props
|
|
547
|
+
),
|
|
548
|
+
render,
|
|
549
|
+
state: {
|
|
550
|
+
slot: "badge",
|
|
551
|
+
variant
|
|
552
|
+
}
|
|
553
|
+
});
|
|
554
|
+
}
|
|
440
555
|
function DropdownMenu({ ...props }) {
|
|
441
556
|
return /* @__PURE__ */ jsx(Menu.Root, { "data-slot": "dropdown-menu", ...props });
|
|
442
557
|
}
|
|
@@ -564,21 +679,17 @@ function Composer({
|
|
|
564
679
|
options = [],
|
|
565
680
|
autoFocus = false,
|
|
566
681
|
defaultSelectedIds = [],
|
|
567
|
-
fileAttachments
|
|
568
|
-
// Legacy props for backward compatibility
|
|
569
|
-
accept: legacyAccept,
|
|
570
|
-
maxFiles: legacyMaxFiles,
|
|
571
|
-
maxFileSize: legacyMaxFileSize
|
|
682
|
+
fileAttachments
|
|
572
683
|
}) {
|
|
573
|
-
const enabled = fileAttachments?.enabled
|
|
574
|
-
const accept = fileAttachments?.accept
|
|
575
|
-
const maxFiles = fileAttachments?.maxFiles ??
|
|
576
|
-
const maxFileSize = fileAttachments?.maxFileSize ??
|
|
577
|
-
const [selectedOptions, setSelectedOptions] =
|
|
684
|
+
const enabled = fileAttachments?.enabled || false;
|
|
685
|
+
const accept = fileAttachments?.accept;
|
|
686
|
+
const maxFiles = fileAttachments?.maxFiles ?? 10;
|
|
687
|
+
const maxFileSize = fileAttachments?.maxFileSize ?? 10 * 1024 * 1024;
|
|
688
|
+
const [selectedOptions, setSelectedOptions] = React12__default.useState(
|
|
578
689
|
() => new Set(defaultSelectedIds)
|
|
579
690
|
);
|
|
580
|
-
const [attachedFiles, setAttachedFiles] =
|
|
581
|
-
const fileInputRef =
|
|
691
|
+
const [attachedFiles, setAttachedFiles] = React12__default.useState([]);
|
|
692
|
+
const fileInputRef = React12__default.useRef(null);
|
|
582
693
|
const toggleOption = (id, groupOptions, type = "multiple") => {
|
|
583
694
|
const next = new Set(selectedOptions);
|
|
584
695
|
if (type === "single") {
|
|
@@ -602,7 +713,9 @@ function Composer({
|
|
|
602
713
|
const files = Array.from(e.target.files || []);
|
|
603
714
|
const validFiles = files.filter((file) => {
|
|
604
715
|
if (file.size > maxFileSize) {
|
|
605
|
-
console.warn(
|
|
716
|
+
console.warn(
|
|
717
|
+
`File ${file.name} exceeds maximum size of ${maxFileSize} bytes`
|
|
718
|
+
);
|
|
606
719
|
return false;
|
|
607
720
|
}
|
|
608
721
|
return true;
|
|
@@ -610,7 +723,9 @@ function Composer({
|
|
|
610
723
|
const remainingSlots = maxFiles - attachedFiles.length;
|
|
611
724
|
const filesToAdd = validFiles.slice(0, remainingSlots);
|
|
612
725
|
if (filesToAdd.length < validFiles.length) {
|
|
613
|
-
console.warn(
|
|
726
|
+
console.warn(
|
|
727
|
+
`Only ${filesToAdd.length} files can be added (max: ${maxFiles})`
|
|
728
|
+
);
|
|
614
729
|
}
|
|
615
730
|
setAttachedFiles((prev) => [...prev, ...filesToAdd]);
|
|
616
731
|
if (fileInputRef.current) {
|
|
@@ -653,12 +768,11 @@ function Composer({
|
|
|
653
768
|
reject(new Error("FileReader returned empty result"));
|
|
654
769
|
return;
|
|
655
770
|
}
|
|
656
|
-
const base64Data = base64.includes(",") ? base64.split(",")[1] : base64;
|
|
657
771
|
resolve({
|
|
658
772
|
name: file.name,
|
|
659
773
|
type: file.type,
|
|
660
774
|
size: file.size,
|
|
661
|
-
data:
|
|
775
|
+
data: base64
|
|
662
776
|
});
|
|
663
777
|
} catch (error) {
|
|
664
778
|
reject(error);
|
|
@@ -691,129 +805,189 @@ function Composer({
|
|
|
691
805
|
handleInternalSubmit().catch(console.error);
|
|
692
806
|
}
|
|
693
807
|
};
|
|
694
|
-
return /* @__PURE__ */
|
|
695
|
-
|
|
696
|
-
|
|
808
|
+
return /* @__PURE__ */ jsx("div", { className: cn("relative flex flex-col w-full", className), children: /* @__PURE__ */ jsxs("div", { className: "relative flex flex-col w-full border-input border-[1.5px] rounded-3xl bg-background shadow-sm focus-within:border-ring transition-all p-2", children: [
|
|
809
|
+
/* @__PURE__ */ jsx(
|
|
810
|
+
Textarea,
|
|
697
811
|
{
|
|
698
|
-
|
|
699
|
-
|
|
700
|
-
|
|
701
|
-
|
|
812
|
+
value,
|
|
813
|
+
onChange: (e) => onChange(e.target.value),
|
|
814
|
+
onKeyDown: handleKeyDown,
|
|
815
|
+
placeholder,
|
|
816
|
+
className: "min-h-[44px] max-h-[200px] border-none bg-transparent focus-visible:ring-0 focus-visible:ring-offset-0 px-3 py-2 text-[15px] resize-none",
|
|
817
|
+
autoFocus
|
|
818
|
+
}
|
|
819
|
+
),
|
|
820
|
+
/* @__PURE__ */ jsxs("div", { className: "flex justify-between items-center px-1", children: [
|
|
821
|
+
/* @__PURE__ */ jsxs("div", { className: "flex items-center gap-1", children: [
|
|
822
|
+
enabled && /* @__PURE__ */ jsxs(Fragment, { children: [
|
|
702
823
|
/* @__PURE__ */ jsx(
|
|
703
|
-
"
|
|
824
|
+
"input",
|
|
825
|
+
{
|
|
826
|
+
ref: fileInputRef,
|
|
827
|
+
type: "file",
|
|
828
|
+
multiple: true,
|
|
829
|
+
accept,
|
|
830
|
+
onChange: handleFileSelect,
|
|
831
|
+
className: "hidden",
|
|
832
|
+
disabled: isLoading || attachedFiles.length >= maxFiles
|
|
833
|
+
}
|
|
834
|
+
),
|
|
835
|
+
attachedFiles.length === 0 ? /* @__PURE__ */ jsx(
|
|
836
|
+
Button,
|
|
704
837
|
{
|
|
705
838
|
type: "button",
|
|
706
|
-
|
|
707
|
-
|
|
708
|
-
|
|
709
|
-
|
|
839
|
+
variant: "ghost",
|
|
840
|
+
size: "sm",
|
|
841
|
+
onClick: () => fileInputRef.current?.click(),
|
|
842
|
+
disabled: isLoading,
|
|
843
|
+
className: "text-muted-foreground",
|
|
844
|
+
title: "Attach file",
|
|
845
|
+
children: /* @__PURE__ */ jsx(IconPaperclip, { className: "h-4 w-4" })
|
|
710
846
|
}
|
|
711
|
-
)
|
|
712
|
-
]
|
|
713
|
-
},
|
|
714
|
-
index
|
|
715
|
-
)) }),
|
|
716
|
-
/* @__PURE__ */ jsxs("div", { className: "relative flex flex-col w-full border-input border-[1.5px] rounded-3xl bg-background shadow-sm focus-within:border-ring transition-all p-2", children: [
|
|
717
|
-
/* @__PURE__ */ jsx(
|
|
718
|
-
Textarea,
|
|
719
|
-
{
|
|
720
|
-
value,
|
|
721
|
-
onChange: (e) => onChange(e.target.value),
|
|
722
|
-
onKeyDown: handleKeyDown,
|
|
723
|
-
placeholder,
|
|
724
|
-
className: "min-h-[44px] max-h-[200px] border-none bg-transparent focus-visible:ring-0 focus-visible:ring-offset-0 px-3 py-2 text-[15px] resize-none",
|
|
725
|
-
autoFocus
|
|
726
|
-
}
|
|
727
|
-
),
|
|
728
|
-
/* @__PURE__ */ jsxs("div", { className: "flex justify-between items-center px-1", children: [
|
|
729
|
-
/* @__PURE__ */ jsxs("div", { className: "flex items-center gap-1", children: [
|
|
730
|
-
enabled && /* @__PURE__ */ jsxs(Fragment, { children: [
|
|
847
|
+
) : /* @__PURE__ */ jsxs(DropdownMenu, { children: [
|
|
731
848
|
/* @__PURE__ */ jsx(
|
|
732
|
-
|
|
849
|
+
DropdownMenuTrigger,
|
|
733
850
|
{
|
|
734
|
-
|
|
735
|
-
|
|
736
|
-
|
|
737
|
-
|
|
738
|
-
|
|
739
|
-
|
|
740
|
-
|
|
851
|
+
render: /* @__PURE__ */ jsxs(
|
|
852
|
+
Button,
|
|
853
|
+
{
|
|
854
|
+
type: "button",
|
|
855
|
+
variant: "ghost",
|
|
856
|
+
size: "sm",
|
|
857
|
+
className: "text-muted-foreground gap-2",
|
|
858
|
+
title: `${attachedFiles.length} files attached`,
|
|
859
|
+
children: [
|
|
860
|
+
/* @__PURE__ */ jsx(IconPaperclip, { className: "h-4 w-4" }),
|
|
861
|
+
/* @__PURE__ */ jsx(Badge, { className: "h-[18px] min-w-[18px] px-1.5 text-[10px]", children: attachedFiles.length })
|
|
862
|
+
]
|
|
863
|
+
}
|
|
864
|
+
)
|
|
741
865
|
}
|
|
742
866
|
),
|
|
743
|
-
/* @__PURE__ */
|
|
744
|
-
|
|
745
|
-
|
|
746
|
-
|
|
747
|
-
|
|
748
|
-
|
|
749
|
-
|
|
750
|
-
|
|
751
|
-
|
|
752
|
-
title: attachedFiles.length >= maxFiles ? `Maximum ${maxFiles} files allowed` : "Attach file",
|
|
753
|
-
children: /* @__PURE__ */ jsx(IconPaperclip, { className: "h-4 w-4" })
|
|
754
|
-
}
|
|
755
|
-
)
|
|
756
|
-
] }),
|
|
757
|
-
options.map((group) => {
|
|
758
|
-
const selectedInGroup = group.options.filter(
|
|
759
|
-
(o) => selectedOptions.has(o.id)
|
|
760
|
-
);
|
|
761
|
-
const label = selectedInGroup.length === 0 ? group.label : selectedInGroup.length === 1 ? selectedInGroup[0].label : `${group.label} (${selectedInGroup.length})`;
|
|
762
|
-
const isSingle = group.type === "single";
|
|
763
|
-
return /* @__PURE__ */ jsxs(DropdownMenu, { children: [
|
|
764
|
-
/* @__PURE__ */ jsx(
|
|
765
|
-
DropdownMenuTrigger,
|
|
766
|
-
{
|
|
767
|
-
render: /* @__PURE__ */ jsxs(
|
|
768
|
-
Button,
|
|
769
|
-
{
|
|
770
|
-
variant: "ghost",
|
|
771
|
-
size: "sm",
|
|
772
|
-
className: cn(
|
|
773
|
-
selectedInGroup.length > 0 ? "text-foreground bg-muted/50" : "text-muted-foreground"
|
|
774
|
-
),
|
|
775
|
-
children: [
|
|
776
|
-
label,
|
|
777
|
-
/* @__PURE__ */ jsx(IconChevronDown, { className: "h-3 w-3 opacity-50" })
|
|
778
|
-
]
|
|
779
|
-
}
|
|
780
|
-
)
|
|
781
|
-
}
|
|
782
|
-
),
|
|
783
|
-
/* @__PURE__ */ jsx(DropdownMenuContent, { align: "start", className: "w-56", children: /* @__PURE__ */ jsxs(DropdownMenuGroup, { children: [
|
|
784
|
-
/* @__PURE__ */ jsx(DropdownMenuLabel, { children: group.label }),
|
|
867
|
+
/* @__PURE__ */ jsxs(DropdownMenuContent, { align: "start", className: "w-64", children: [
|
|
868
|
+
/* @__PURE__ */ jsxs(DropdownMenuGroup, { children: [
|
|
869
|
+
/* @__PURE__ */ jsxs(DropdownMenuLabel, { children: [
|
|
870
|
+
"Attached Files (",
|
|
871
|
+
attachedFiles.length,
|
|
872
|
+
"/",
|
|
873
|
+
maxFiles,
|
|
874
|
+
")"
|
|
875
|
+
] }),
|
|
785
876
|
/* @__PURE__ */ jsx(DropdownMenuSeparator, {}),
|
|
786
|
-
|
|
787
|
-
|
|
877
|
+
attachedFiles.map((file, index) => /* @__PURE__ */ jsxs(
|
|
878
|
+
DropdownMenuItem,
|
|
788
879
|
{
|
|
789
|
-
|
|
790
|
-
onCheckedChange: () => toggleOption(
|
|
791
|
-
option.id,
|
|
792
|
-
group.options,
|
|
793
|
-
isSingle ? "single" : "multiple"
|
|
794
|
-
),
|
|
880
|
+
className: "flex items-center justify-between group",
|
|
795
881
|
onSelect: (e) => e.preventDefault(),
|
|
796
|
-
children:
|
|
882
|
+
children: [
|
|
883
|
+
/* @__PURE__ */ jsxs("div", { className: "flex flex-col min-w-0 flex-1", children: [
|
|
884
|
+
/* @__PURE__ */ jsx(
|
|
885
|
+
"span",
|
|
886
|
+
{
|
|
887
|
+
className: "truncate text-sm",
|
|
888
|
+
title: file.name,
|
|
889
|
+
children: file.name
|
|
890
|
+
}
|
|
891
|
+
),
|
|
892
|
+
/* @__PURE__ */ jsx("span", { className: "text-[10px] text-muted-foreground", children: formatFileSize(file.size) })
|
|
893
|
+
] }),
|
|
894
|
+
/* @__PURE__ */ jsx(
|
|
895
|
+
Button,
|
|
896
|
+
{
|
|
897
|
+
type: "button",
|
|
898
|
+
variant: "ghost",
|
|
899
|
+
size: "icon",
|
|
900
|
+
className: "h-6 w-6 opacity-0 group-hover:opacity-100 transition-opacity",
|
|
901
|
+
onClick: () => handleRemoveFile(index),
|
|
902
|
+
children: /* @__PURE__ */ jsx(IconX, { className: "h-3 w-3" })
|
|
903
|
+
}
|
|
904
|
+
)
|
|
905
|
+
]
|
|
797
906
|
},
|
|
798
|
-
|
|
907
|
+
index
|
|
799
908
|
))
|
|
800
|
-
] })
|
|
801
|
-
|
|
802
|
-
|
|
909
|
+
] }),
|
|
910
|
+
attachedFiles.length < maxFiles && /* @__PURE__ */ jsxs(Fragment, { children: [
|
|
911
|
+
/* @__PURE__ */ jsx(DropdownMenuSeparator, {}),
|
|
912
|
+
/* @__PURE__ */ jsxs(
|
|
913
|
+
DropdownMenuItem,
|
|
914
|
+
{
|
|
915
|
+
onSelect: (e) => {
|
|
916
|
+
e.preventDefault();
|
|
917
|
+
fileInputRef.current?.click();
|
|
918
|
+
},
|
|
919
|
+
className: "text-primary focus:text-primary",
|
|
920
|
+
children: [
|
|
921
|
+
/* @__PURE__ */ jsx(IconPlus, { className: "mr-2 h-4 w-4" }),
|
|
922
|
+
/* @__PURE__ */ jsx("span", { children: "Add more files" })
|
|
923
|
+
]
|
|
924
|
+
}
|
|
925
|
+
)
|
|
926
|
+
] })
|
|
927
|
+
] })
|
|
928
|
+
] })
|
|
803
929
|
] }),
|
|
804
|
-
|
|
805
|
-
|
|
806
|
-
|
|
807
|
-
|
|
808
|
-
|
|
809
|
-
|
|
810
|
-
|
|
811
|
-
|
|
812
|
-
|
|
813
|
-
|
|
814
|
-
|
|
930
|
+
options.map((group) => {
|
|
931
|
+
const selectedInGroup = group.options.filter(
|
|
932
|
+
(o) => selectedOptions.has(o.id)
|
|
933
|
+
);
|
|
934
|
+
const label = selectedInGroup.length === 0 ? group.label : selectedInGroup.length === 1 ? selectedInGroup[0].label : group.label;
|
|
935
|
+
const isSingle = group.type === "single";
|
|
936
|
+
return /* @__PURE__ */ jsxs(DropdownMenu, { children: [
|
|
937
|
+
/* @__PURE__ */ jsx(
|
|
938
|
+
DropdownMenuTrigger,
|
|
939
|
+
{
|
|
940
|
+
render: /* @__PURE__ */ jsxs(
|
|
941
|
+
Button,
|
|
942
|
+
{
|
|
943
|
+
variant: "ghost",
|
|
944
|
+
size: "sm",
|
|
945
|
+
className: cn(
|
|
946
|
+
"gap-2",
|
|
947
|
+
selectedInGroup.length > 0 ? "text-foreground bg-muted/50" : "text-muted-foreground"
|
|
948
|
+
),
|
|
949
|
+
children: [
|
|
950
|
+
label,
|
|
951
|
+
selectedInGroup.length > 1 && /* @__PURE__ */ jsx(Badge, { className: "h-[18px] min-w-[18px] px-1.5 text-[10px]", children: selectedInGroup.length }),
|
|
952
|
+
/* @__PURE__ */ jsx(IconChevronDown, { className: "h-3 w-3 opacity-50" })
|
|
953
|
+
]
|
|
954
|
+
}
|
|
955
|
+
)
|
|
956
|
+
}
|
|
957
|
+
),
|
|
958
|
+
/* @__PURE__ */ jsx(DropdownMenuContent, { align: "start", className: "w-56", children: /* @__PURE__ */ jsxs(DropdownMenuGroup, { children: [
|
|
959
|
+
/* @__PURE__ */ jsx(DropdownMenuLabel, { children: group.label }),
|
|
960
|
+
/* @__PURE__ */ jsx(DropdownMenuSeparator, {}),
|
|
961
|
+
group.options.map((option) => /* @__PURE__ */ jsx(
|
|
962
|
+
DropdownMenuCheckboxItem,
|
|
963
|
+
{
|
|
964
|
+
checked: selectedOptions.has(option.id),
|
|
965
|
+
onCheckedChange: () => toggleOption(
|
|
966
|
+
option.id,
|
|
967
|
+
group.options,
|
|
968
|
+
isSingle ? "single" : "multiple"
|
|
969
|
+
),
|
|
970
|
+
onSelect: (e) => e.preventDefault(),
|
|
971
|
+
children: option.label
|
|
972
|
+
},
|
|
973
|
+
option.id
|
|
974
|
+
))
|
|
975
|
+
] }) })
|
|
976
|
+
] }, group.id);
|
|
977
|
+
})
|
|
978
|
+
] }),
|
|
979
|
+
/* @__PURE__ */ jsx(
|
|
980
|
+
Button,
|
|
981
|
+
{
|
|
982
|
+
type: "submit",
|
|
983
|
+
disabled: !value.trim() && attachedFiles.length === 0 && !isLoading || isLoading,
|
|
984
|
+
size: "icon-lg",
|
|
985
|
+
onClick: () => handleInternalSubmit().catch(console.error),
|
|
986
|
+
children: isLoading ? /* @__PURE__ */ jsx(IconLoader2, { className: "h-5 w-5 animate-spin" }) : /* @__PURE__ */ jsx(IconArrowUp, { className: "h-5 w-5" })
|
|
987
|
+
}
|
|
988
|
+
)
|
|
815
989
|
] })
|
|
816
|
-
] });
|
|
990
|
+
] }) });
|
|
817
991
|
}
|
|
818
992
|
function Card({
|
|
819
993
|
className,
|
|
@@ -945,8 +1119,6 @@ var Col = ({
|
|
|
945
1119
|
gap = "sm",
|
|
946
1120
|
align = "start",
|
|
947
1121
|
justify = "start",
|
|
948
|
-
wrap = "nowrap",
|
|
949
|
-
flex = 1,
|
|
950
1122
|
width,
|
|
951
1123
|
height,
|
|
952
1124
|
padding,
|
|
@@ -996,13 +1168,11 @@ var Col = ({
|
|
|
996
1168
|
gapClasses[gap] || "gap-2",
|
|
997
1169
|
alignClasses[align] || "items-start",
|
|
998
1170
|
justifyClasses[justify] || "justify-start",
|
|
999
|
-
wrap === "wrap" ? "flex-wrap" : "flex-nowrap",
|
|
1000
1171
|
overflow && overflowClasses[overflow],
|
|
1001
1172
|
position && positionClasses[position],
|
|
1002
1173
|
className
|
|
1003
1174
|
),
|
|
1004
1175
|
style: {
|
|
1005
|
-
flex,
|
|
1006
1176
|
width,
|
|
1007
1177
|
height,
|
|
1008
1178
|
padding,
|
|
@@ -1436,45 +1606,6 @@ var Icon = ({
|
|
|
1436
1606
|
}
|
|
1437
1607
|
);
|
|
1438
1608
|
};
|
|
1439
|
-
var badgeVariants = cva(
|
|
1440
|
-
"h-5 gap-1 rounded-4xl border border-transparent px-2 py-0.5 text-xs font-medium transition-all has-data-[icon=inline-end]:pr-1.5 has-data-[icon=inline-start]:pl-1.5 [&>svg]:size-3! inline-flex items-center justify-center w-fit whitespace-nowrap shrink-0 [&>svg]:pointer-events-none focus-visible:border-ring focus-visible:ring-ring/50 focus-visible:ring-[3px] aria-invalid:ring-destructive/20 dark:aria-invalid:ring-destructive/40 aria-invalid:border-destructive transition-colors overflow-hidden group/badge",
|
|
1441
|
-
{
|
|
1442
|
-
variants: {
|
|
1443
|
-
variant: {
|
|
1444
|
-
default: "bg-primary text-primary-foreground [a]:hover:bg-primary/80",
|
|
1445
|
-
secondary: "bg-secondary text-secondary-foreground [a]:hover:bg-secondary/80",
|
|
1446
|
-
destructive: "bg-destructive/10 [a]:hover:bg-destructive/20 focus-visible:ring-destructive/20 dark:focus-visible:ring-destructive/40 text-destructive dark:bg-destructive/20",
|
|
1447
|
-
outline: "border-border text-foreground [a]:hover:bg-muted [a]:hover:text-muted-foreground bg-input/30",
|
|
1448
|
-
ghost: "hover:bg-muted hover:text-muted-foreground dark:hover:bg-muted/50",
|
|
1449
|
-
link: "text-primary underline-offset-4 hover:underline"
|
|
1450
|
-
}
|
|
1451
|
-
},
|
|
1452
|
-
defaultVariants: {
|
|
1453
|
-
variant: "default"
|
|
1454
|
-
}
|
|
1455
|
-
}
|
|
1456
|
-
);
|
|
1457
|
-
function Badge({
|
|
1458
|
-
className,
|
|
1459
|
-
variant = "default",
|
|
1460
|
-
render,
|
|
1461
|
-
...props
|
|
1462
|
-
}) {
|
|
1463
|
-
return useRender({
|
|
1464
|
-
defaultTagName: "span",
|
|
1465
|
-
props: mergeProps(
|
|
1466
|
-
{
|
|
1467
|
-
className: cn(badgeVariants({ className, variant }))
|
|
1468
|
-
},
|
|
1469
|
-
props
|
|
1470
|
-
),
|
|
1471
|
-
render,
|
|
1472
|
-
state: {
|
|
1473
|
-
slot: "badge",
|
|
1474
|
-
variant
|
|
1475
|
-
}
|
|
1476
|
-
});
|
|
1477
|
-
}
|
|
1478
1609
|
var Badge2 = ({
|
|
1479
1610
|
label,
|
|
1480
1611
|
variant = "primary",
|
|
@@ -2063,9 +2194,9 @@ var Select2 = ({
|
|
|
2063
2194
|
defaultValue,
|
|
2064
2195
|
value,
|
|
2065
2196
|
disabled,
|
|
2066
|
-
onValueChange: handleValueChange,
|
|
2197
|
+
onValueChange: (value2) => handleValueChange(value2 || ""),
|
|
2067
2198
|
children: [
|
|
2068
|
-
/* @__PURE__ */ jsx(SelectTrigger, { className: "w-full", children: /* @__PURE__ */ jsx(SelectValue, {
|
|
2199
|
+
/* @__PURE__ */ jsx(SelectTrigger, { className: "w-full", children: /* @__PURE__ */ jsx(SelectValue, {}) }),
|
|
2069
2200
|
/* @__PURE__ */ jsx(SelectContent, { children: options.map((option) => /* @__PURE__ */ jsx(SelectItem, { value: option.value, children: option.label }, option.value)) })
|
|
2070
2201
|
]
|
|
2071
2202
|
}
|
|
@@ -2095,7 +2226,6 @@ var Label2 = ({
|
|
|
2095
2226
|
var Checkbox = ({
|
|
2096
2227
|
label,
|
|
2097
2228
|
name,
|
|
2098
|
-
value = "on",
|
|
2099
2229
|
checked,
|
|
2100
2230
|
defaultChecked,
|
|
2101
2231
|
disabled,
|
|
@@ -2110,46 +2240,37 @@ var Checkbox = ({
|
|
|
2110
2240
|
...onChangeAction,
|
|
2111
2241
|
data: {
|
|
2112
2242
|
name: name || "",
|
|
2113
|
-
value,
|
|
2114
2243
|
checked: e.target.checked
|
|
2115
2244
|
}
|
|
2116
2245
|
});
|
|
2117
2246
|
}
|
|
2118
2247
|
};
|
|
2119
|
-
return /* @__PURE__ */ jsxs(
|
|
2120
|
-
|
|
2121
|
-
|
|
2122
|
-
|
|
2123
|
-
|
|
2124
|
-
|
|
2125
|
-
|
|
2126
|
-
|
|
2127
|
-
|
|
2128
|
-
|
|
2129
|
-
|
|
2130
|
-
|
|
2131
|
-
|
|
2132
|
-
|
|
2133
|
-
|
|
2134
|
-
|
|
2135
|
-
|
|
2136
|
-
|
|
2137
|
-
|
|
2138
|
-
|
|
2139
|
-
|
|
2140
|
-
|
|
2141
|
-
{
|
|
2142
|
-
htmlFor: name,
|
|
2143
|
-
value: label,
|
|
2144
|
-
className: cn(
|
|
2145
|
-
"cursor-pointer select-none text-sm font-medium leading-none",
|
|
2146
|
-
disabled && "cursor-not-allowed opacity-50"
|
|
2147
|
-
)
|
|
2148
|
-
}
|
|
2248
|
+
return /* @__PURE__ */ jsxs("div", { className: cn("flex items-center gap-2", className), style, children: [
|
|
2249
|
+
/* @__PURE__ */ jsx(
|
|
2250
|
+
"input",
|
|
2251
|
+
{
|
|
2252
|
+
type: "checkbox",
|
|
2253
|
+
name,
|
|
2254
|
+
id: name,
|
|
2255
|
+
checked,
|
|
2256
|
+
defaultChecked,
|
|
2257
|
+
disabled,
|
|
2258
|
+
onChange: handleChange,
|
|
2259
|
+
className: "h-4 w-4 rounded border-gray-300 text-primary focus:ring-primary disabled:cursor-not-allowed disabled:opacity-50"
|
|
2260
|
+
}
|
|
2261
|
+
),
|
|
2262
|
+
label && /* @__PURE__ */ jsx(
|
|
2263
|
+
Label2,
|
|
2264
|
+
{
|
|
2265
|
+
htmlFor: name,
|
|
2266
|
+
value: label,
|
|
2267
|
+
className: cn(
|
|
2268
|
+
"cursor-pointer select-none text-sm font-medium leading-none",
|
|
2269
|
+
disabled && "cursor-not-allowed opacity-50"
|
|
2149
2270
|
)
|
|
2150
|
-
|
|
2151
|
-
|
|
2152
|
-
);
|
|
2271
|
+
}
|
|
2272
|
+
)
|
|
2273
|
+
] });
|
|
2153
2274
|
};
|
|
2154
2275
|
var RadioGroup = ({
|
|
2155
2276
|
name,
|
|
@@ -2472,12 +2593,14 @@ function Thread({
|
|
|
2472
2593
|
});
|
|
2473
2594
|
const starterPrompts = localStarterPrompts ?? config?.starterPrompts;
|
|
2474
2595
|
const options = localOptions ?? config?.options;
|
|
2596
|
+
const fileAttachments = config?.fileAttachments;
|
|
2475
2597
|
const allDefaultSelectedIds = useMemo(() => {
|
|
2476
|
-
const defaultSelectedIdsFromOptions = options?.flatMap(
|
|
2477
|
-
(group) => group.defaultSelectedIds ?? []
|
|
2478
|
-
) ?? [];
|
|
2598
|
+
const defaultSelectedIdsFromOptions = options?.flatMap((group) => group.defaultSelectedIds ?? []) ?? [];
|
|
2479
2599
|
return [
|
|
2480
|
-
.../* @__PURE__ */ new Set([
|
|
2600
|
+
.../* @__PURE__ */ new Set([
|
|
2601
|
+
...defaultSelectedIdsFromOptions,
|
|
2602
|
+
...defaultSelectedIds ?? []
|
|
2603
|
+
])
|
|
2481
2604
|
];
|
|
2482
2605
|
}, [options, defaultSelectedIds]);
|
|
2483
2606
|
const [input, setInput] = useState("");
|
|
@@ -2553,7 +2676,7 @@ function Thread({
|
|
|
2553
2676
|
options,
|
|
2554
2677
|
autoFocus,
|
|
2555
2678
|
defaultSelectedIds: allDefaultSelectedIds,
|
|
2556
|
-
fileAttachments
|
|
2679
|
+
fileAttachments
|
|
2557
2680
|
}
|
|
2558
2681
|
) }) })
|
|
2559
2682
|
]
|
|
@@ -2561,20 +2684,36 @@ function Thread({
|
|
|
2561
2684
|
);
|
|
2562
2685
|
}
|
|
2563
2686
|
function ChatHeader({
|
|
2564
|
-
title,
|
|
2565
2687
|
leftContent,
|
|
2566
2688
|
rightContent,
|
|
2567
2689
|
className,
|
|
2568
|
-
titleClassName,
|
|
2569
2690
|
children
|
|
2570
2691
|
}) {
|
|
2571
2692
|
if (children) {
|
|
2572
|
-
return /* @__PURE__ */ jsx(
|
|
2693
|
+
return /* @__PURE__ */ jsx(
|
|
2694
|
+
"div",
|
|
2695
|
+
{
|
|
2696
|
+
className: cn(
|
|
2697
|
+
"px-2 border-b border-border h-14 flex items-center shrink-0",
|
|
2698
|
+
className
|
|
2699
|
+
),
|
|
2700
|
+
children
|
|
2701
|
+
}
|
|
2702
|
+
);
|
|
2573
2703
|
}
|
|
2574
|
-
return /* @__PURE__ */ jsxs(
|
|
2575
|
-
|
|
2576
|
-
|
|
2577
|
-
|
|
2704
|
+
return /* @__PURE__ */ jsxs(
|
|
2705
|
+
"div",
|
|
2706
|
+
{
|
|
2707
|
+
className: cn(
|
|
2708
|
+
"px-2 border-b border-border h-14 flex items-center justify-between shrink-0",
|
|
2709
|
+
className
|
|
2710
|
+
),
|
|
2711
|
+
children: [
|
|
2712
|
+
/* @__PURE__ */ jsx("div", { className: "flex items-center gap-2 flex-1 min-w-0", children: leftContent }),
|
|
2713
|
+
rightContent && /* @__PURE__ */ jsx("div", { className: "flex items-center gap-1 shrink-0 ml-2", children: rightContent })
|
|
2714
|
+
]
|
|
2715
|
+
}
|
|
2716
|
+
);
|
|
2578
2717
|
}
|
|
2579
2718
|
var ThreadList = ({
|
|
2580
2719
|
className,
|
|
@@ -2589,14 +2728,20 @@ var ThreadList = ({
|
|
|
2589
2728
|
deleteThread,
|
|
2590
2729
|
isLoading
|
|
2591
2730
|
} = useThreads();
|
|
2731
|
+
const sortedThreads = React12.useMemo(() => {
|
|
2732
|
+
return [...threads].sort((a, b) => {
|
|
2733
|
+
const dateA = a.updatedAt ? new Date(a.updatedAt).getTime() : 0;
|
|
2734
|
+
const dateB = b.updatedAt ? new Date(b.updatedAt).getTime() : 0;
|
|
2735
|
+
return dateB - dateA;
|
|
2736
|
+
});
|
|
2737
|
+
}, [threads]);
|
|
2592
2738
|
const handleThreadClick = (threadId) => {
|
|
2593
2739
|
if (threadId !== activeThreadId) {
|
|
2594
2740
|
selectThread(threadId);
|
|
2595
2741
|
}
|
|
2596
2742
|
onThreadSelect?.(threadId);
|
|
2597
2743
|
};
|
|
2598
|
-
const handleDelete = async (
|
|
2599
|
-
e.stopPropagation();
|
|
2744
|
+
const handleDelete = async (threadId) => {
|
|
2600
2745
|
try {
|
|
2601
2746
|
await deleteThread(threadId);
|
|
2602
2747
|
} catch (error) {
|
|
@@ -2610,32 +2755,16 @@ var ThreadList = ({
|
|
|
2610
2755
|
console.error("Failed to create thread:", error);
|
|
2611
2756
|
}
|
|
2612
2757
|
};
|
|
2613
|
-
const formatDate = (date) => {
|
|
2614
|
-
if (!date) return "";
|
|
2615
|
-
const d = typeof date === "string" ? new Date(date) : date;
|
|
2616
|
-
if (isNaN(d.getTime())) return "";
|
|
2617
|
-
const now = /* @__PURE__ */ new Date();
|
|
2618
|
-
const diffMs = now.getTime() - d.getTime();
|
|
2619
|
-
const diffMins = Math.floor(diffMs / 6e4);
|
|
2620
|
-
const diffHours = Math.floor(diffMs / 36e5);
|
|
2621
|
-
const diffDays = Math.floor(diffMs / 864e5);
|
|
2622
|
-
if (diffMins < 1) return "Just now";
|
|
2623
|
-
if (diffMins < 60) return `${diffMins}m ago`;
|
|
2624
|
-
if (diffHours < 24) return `${diffHours}h ago`;
|
|
2625
|
-
if (diffDays < 7) return `${diffDays}d ago`;
|
|
2626
|
-
return d.toLocaleDateString();
|
|
2627
|
-
};
|
|
2628
2758
|
return /* @__PURE__ */ jsxs("div", { className: cn("flex flex-col h-full", className), children: [
|
|
2629
2759
|
/* @__PURE__ */ jsx("div", { className: "p-2", children: /* @__PURE__ */ jsxs(
|
|
2630
2760
|
Button,
|
|
2631
2761
|
{
|
|
2632
|
-
variant: "
|
|
2633
|
-
|
|
2762
|
+
variant: "outline",
|
|
2763
|
+
className: "w-full justify-start gap-2 h-9 px-3 border-dashed hover:border-solid transition-all",
|
|
2634
2764
|
onClick: handleNewThread,
|
|
2635
|
-
className: "w-full justify-start",
|
|
2636
2765
|
children: [
|
|
2637
|
-
/* @__PURE__ */ jsx(IconPlus, { className: "
|
|
2638
|
-
"New
|
|
2766
|
+
/* @__PURE__ */ jsx(IconPlus, { className: "size-4" }),
|
|
2767
|
+
/* @__PURE__ */ jsx("span", { className: "text-sm font-medium", children: "New chat" })
|
|
2639
2768
|
]
|
|
2640
2769
|
}
|
|
2641
2770
|
) }),
|
|
@@ -2643,7 +2772,7 @@ var ThreadList = ({
|
|
|
2643
2772
|
/* @__PURE__ */ jsx(IconMessage, { className: "size-8 mx-auto opacity-50" }),
|
|
2644
2773
|
/* @__PURE__ */ jsx("p", { className: "text-sm", children: "No threads yet" }),
|
|
2645
2774
|
/* @__PURE__ */ jsx(Button, { variant: "ghost", size: "sm", onClick: handleNewThread, children: "Start a conversation" })
|
|
2646
|
-
] }) }) : /* @__PURE__ */ jsx("div", { className: "p-2 space-y-1", children:
|
|
2775
|
+
] }) }) : /* @__PURE__ */ jsx("div", { className: "p-2 space-y-1", children: sortedThreads.map((thread) => {
|
|
2647
2776
|
const isActive = thread.id === activeThreadId;
|
|
2648
2777
|
return /* @__PURE__ */ jsxs(
|
|
2649
2778
|
"div",
|
|
@@ -2651,26 +2780,44 @@ var ThreadList = ({
|
|
|
2651
2780
|
onClick: () => handleThreadClick(thread.id),
|
|
2652
2781
|
className: cn(
|
|
2653
2782
|
"group relative flex items-center gap-3 px-3 py-1.5 rounded-lg cursor-pointer transition-colors",
|
|
2654
|
-
isActive ? "bg-muted" : "hover:bg-muted"
|
|
2783
|
+
isActive ? "bg-muted text-foreground" : "hover:bg-muted/50 text-muted-foreground hover:text-foreground"
|
|
2655
2784
|
),
|
|
2656
2785
|
children: [
|
|
2657
|
-
/* @__PURE__ */ jsx("div", { className: "flex-1 min-w-0", children: /* @__PURE__ */
|
|
2658
|
-
|
|
2659
|
-
|
|
2660
|
-
|
|
2661
|
-
|
|
2662
|
-
|
|
2663
|
-
|
|
2664
|
-
|
|
2665
|
-
|
|
2666
|
-
|
|
2667
|
-
|
|
2668
|
-
|
|
2669
|
-
|
|
2670
|
-
|
|
2671
|
-
|
|
2672
|
-
|
|
2673
|
-
|
|
2786
|
+
/* @__PURE__ */ jsx("div", { className: "flex-1 min-w-0", children: /* @__PURE__ */ jsx("p", { className: "text-sm font-medium truncate", children: thread.title || `Thread ${thread.id.slice(0, 8)}` }) }),
|
|
2787
|
+
/* @__PURE__ */ jsx("div", { className: "shrink-0 flex items-center opacity-0 group-hover:opacity-100 transition-opacity", children: /* @__PURE__ */ jsxs(DropdownMenu, { children: [
|
|
2788
|
+
/* @__PURE__ */ jsx(
|
|
2789
|
+
DropdownMenuTrigger,
|
|
2790
|
+
{
|
|
2791
|
+
render: (props) => /* @__PURE__ */ jsx(
|
|
2792
|
+
Button,
|
|
2793
|
+
{
|
|
2794
|
+
variant: "ghost",
|
|
2795
|
+
size: "icon-xs",
|
|
2796
|
+
...props,
|
|
2797
|
+
onClick: (e) => {
|
|
2798
|
+
e.stopPropagation();
|
|
2799
|
+
props.onClick?.(e);
|
|
2800
|
+
},
|
|
2801
|
+
children: /* @__PURE__ */ jsx(IconDotsVertical, { className: "size-3.5" })
|
|
2802
|
+
}
|
|
2803
|
+
)
|
|
2804
|
+
}
|
|
2805
|
+
),
|
|
2806
|
+
/* @__PURE__ */ jsx(DropdownMenuContent, { align: "start", className: "w-32", children: /* @__PURE__ */ jsxs(
|
|
2807
|
+
DropdownMenuItem,
|
|
2808
|
+
{
|
|
2809
|
+
variant: "destructive",
|
|
2810
|
+
onClick: (e) => {
|
|
2811
|
+
e.stopPropagation();
|
|
2812
|
+
handleDelete(thread.id);
|
|
2813
|
+
},
|
|
2814
|
+
children: [
|
|
2815
|
+
/* @__PURE__ */ jsx(IconTrash, { className: "size-4 mr-2" }),
|
|
2816
|
+
/* @__PURE__ */ jsx("span", { children: "Delete" })
|
|
2817
|
+
]
|
|
2818
|
+
}
|
|
2819
|
+
) })
|
|
2820
|
+
] }) })
|
|
2674
2821
|
]
|
|
2675
2822
|
},
|
|
2676
2823
|
thread.id
|
|
@@ -2805,9 +2952,144 @@ function ChatSidebar({
|
|
|
2805
2952
|
) })
|
|
2806
2953
|
] });
|
|
2807
2954
|
}
|
|
2955
|
+
var ChatSidebarContext = createContext(
|
|
2956
|
+
void 0
|
|
2957
|
+
);
|
|
2958
|
+
function useChatSidebar() {
|
|
2959
|
+
const context = useContext(ChatSidebarContext);
|
|
2960
|
+
if (context === void 0) {
|
|
2961
|
+
throw new Error("useChatSidebar must be used within a ChatSidebarProvider");
|
|
2962
|
+
}
|
|
2963
|
+
return context;
|
|
2964
|
+
}
|
|
2965
|
+
function WelcomeScreen({
|
|
2966
|
+
title = "Welcome to Melony",
|
|
2967
|
+
description = "The most powerful AI agent framework for building modern applications. Connect your tools, build your brain, and ship faster.",
|
|
2968
|
+
features = [
|
|
2969
|
+
{
|
|
2970
|
+
title: "Context Aware",
|
|
2971
|
+
description: "Built-in state management for complex LLM flows."
|
|
2972
|
+
},
|
|
2973
|
+
{
|
|
2974
|
+
title: "Extensible",
|
|
2975
|
+
description: "Plugin architecture for easy integrations."
|
|
2976
|
+
},
|
|
2977
|
+
{
|
|
2978
|
+
title: "Real-time",
|
|
2979
|
+
description: "Streaming responses and live state updates."
|
|
2980
|
+
},
|
|
2981
|
+
{
|
|
2982
|
+
title: "Tool-ready",
|
|
2983
|
+
description: "Ready-to-use actions for common tasks."
|
|
2984
|
+
}
|
|
2985
|
+
],
|
|
2986
|
+
className,
|
|
2987
|
+
onLoginClick,
|
|
2988
|
+
termsUrl = "#",
|
|
2989
|
+
privacyUrl = "#",
|
|
2990
|
+
imageUrl,
|
|
2991
|
+
imageAlt = "Product screenshot"
|
|
2992
|
+
}) {
|
|
2993
|
+
const { login, isLoading } = useAuth();
|
|
2994
|
+
const handleLogin = () => {
|
|
2995
|
+
if (onLoginClick) {
|
|
2996
|
+
onLoginClick();
|
|
2997
|
+
} else {
|
|
2998
|
+
login();
|
|
2999
|
+
}
|
|
3000
|
+
};
|
|
3001
|
+
return /* @__PURE__ */ jsxs(
|
|
3002
|
+
"div",
|
|
3003
|
+
{
|
|
3004
|
+
className: cn(
|
|
3005
|
+
"flex min-h-[600px] h-full w-full flex-col md:flex-row bg-background overflow-hidden",
|
|
3006
|
+
className
|
|
3007
|
+
),
|
|
3008
|
+
children: [
|
|
3009
|
+
/* @__PURE__ */ jsxs("div", { className: "flex flex-1 flex-col bg-sidebar text-foreground relative overflow-hidden", children: [
|
|
3010
|
+
/* @__PURE__ */ jsx("div", { className: "absolute -top-24 -left-24 size-96 bg-primary/5 rounded-full blur-3xl" }),
|
|
3011
|
+
/* @__PURE__ */ jsx("div", { className: "absolute -bottom-24 -right-24 size-96 bg-primary/5 rounded-full blur-3xl" }),
|
|
3012
|
+
/* @__PURE__ */ jsx("div", { className: "flex-1 overflow-y-auto overflow-x-hidden relative z-10 flex flex-col p-8 md:p-12 lg:p-20", children: /* @__PURE__ */ jsxs("div", { className: "max-w-xl mx-auto w-full", children: [
|
|
3013
|
+
/* @__PURE__ */ jsx("h1", { className: "mb-6 text-4xl font-bold tracking-tight md:text-5xl lg:text-6xl text-foreground", children: title }),
|
|
3014
|
+
/* @__PURE__ */ jsx("p", { className: "mb-12 text-lg text-muted-foreground md:text-xl leading-relaxed", children: description }),
|
|
3015
|
+
imageUrl && /* @__PURE__ */ jsxs("div", { className: "mb-12 relative group", children: [
|
|
3016
|
+
/* @__PURE__ */ jsx("div", { className: "absolute -inset-1 bg-gradient-to-r from-primary/20 to-primary/10 rounded-xl blur opacity-25 group-hover:opacity-50 transition duration-1000 group-hover:duration-200" }),
|
|
3017
|
+
/* @__PURE__ */ jsx(
|
|
3018
|
+
"img",
|
|
3019
|
+
{
|
|
3020
|
+
src: imageUrl,
|
|
3021
|
+
alt: imageAlt,
|
|
3022
|
+
className: "relative rounded-xl border border-border/50 shadow-2xl transition-transform duration-500 hover:scale-[1.02] w-full"
|
|
3023
|
+
}
|
|
3024
|
+
)
|
|
3025
|
+
] }),
|
|
3026
|
+
/* @__PURE__ */ jsx("div", { className: "grid grid-cols-1 gap-x-8 gap-y-10 sm:grid-cols-2", children: features.map((feature, i) => /* @__PURE__ */ jsxs("div", { className: "space-y-2", children: [
|
|
3027
|
+
/* @__PURE__ */ jsx("h3", { className: "font-bold text-lg text-foreground", children: feature.title }),
|
|
3028
|
+
/* @__PURE__ */ jsx("p", { className: "text-sm text-muted-foreground leading-relaxed", children: feature.description })
|
|
3029
|
+
] }, i)) })
|
|
3030
|
+
] }) })
|
|
3031
|
+
] }),
|
|
3032
|
+
/* @__PURE__ */ jsx("div", { className: "flex flex-1 flex-col items-center justify-center p-8 md:p-12 lg:p-20 bg-background transition-colors duration-300", children: /* @__PURE__ */ jsxs("div", { className: "w-full max-w-sm space-y-8", children: [
|
|
3033
|
+
/* @__PURE__ */ jsxs("div", { className: "space-y-3 text-center md:text-left", children: [
|
|
3034
|
+
/* @__PURE__ */ jsx("h2", { className: "text-3xl font-bold tracking-tight text-foreground", children: "Get Started" }),
|
|
3035
|
+
/* @__PURE__ */ jsx("p", { className: "text-muted-foreground text-lg", children: "Sign in to your account to continue" })
|
|
3036
|
+
] }),
|
|
3037
|
+
/* @__PURE__ */ jsxs("div", { className: "space-y-4", children: [
|
|
3038
|
+
/* @__PURE__ */ jsxs(
|
|
3039
|
+
Button,
|
|
3040
|
+
{
|
|
3041
|
+
size: "lg",
|
|
3042
|
+
variant: "outline",
|
|
3043
|
+
className: "w-full h-16 text-lg shadow-sm hover:shadow-md transition-all flex items-center justify-center gap-3 border-2 font-medium bg-background text-foreground hover:bg-accent",
|
|
3044
|
+
onClick: handleLogin,
|
|
3045
|
+
disabled: isLoading,
|
|
3046
|
+
children: [
|
|
3047
|
+
/* @__PURE__ */ jsx(IconBrandGoogle, { className: "size-6" }),
|
|
3048
|
+
isLoading ? "Signing in..." : "Continue with Google"
|
|
3049
|
+
]
|
|
3050
|
+
}
|
|
3051
|
+
),
|
|
3052
|
+
/* @__PURE__ */ jsxs("div", { className: "relative py-4", children: [
|
|
3053
|
+
/* @__PURE__ */ jsx("div", { className: "absolute inset-0 flex items-center", children: /* @__PURE__ */ jsx("span", { className: "w-full border-t border-border" }) }),
|
|
3054
|
+
/* @__PURE__ */ jsx("div", { className: "relative flex justify-center text-xs uppercase", children: /* @__PURE__ */ jsx("span", { className: "bg-background px-3 text-muted-foreground tracking-widest font-medium", children: "Secure access" }) })
|
|
3055
|
+
] })
|
|
3056
|
+
] }),
|
|
3057
|
+
/* @__PURE__ */ jsxs("p", { className: "text-sm text-muted-foreground leading-relaxed text-center md:text-left", children: [
|
|
3058
|
+
"By continuing, you agree to our ",
|
|
3059
|
+
/* @__PURE__ */ jsx("br", { className: "hidden md:block" }),
|
|
3060
|
+
/* @__PURE__ */ jsx(
|
|
3061
|
+
"a",
|
|
3062
|
+
{
|
|
3063
|
+
href: termsUrl,
|
|
3064
|
+
target: "_blank",
|
|
3065
|
+
rel: "noopener noreferrer",
|
|
3066
|
+
className: "underline underline-offset-4 hover:text-primary transition-colors font-medium",
|
|
3067
|
+
children: "Terms of Service"
|
|
3068
|
+
}
|
|
3069
|
+
),
|
|
3070
|
+
" ",
|
|
3071
|
+
"and",
|
|
3072
|
+
" ",
|
|
3073
|
+
/* @__PURE__ */ jsx(
|
|
3074
|
+
"a",
|
|
3075
|
+
{
|
|
3076
|
+
href: privacyUrl,
|
|
3077
|
+
target: "_blank",
|
|
3078
|
+
rel: "noopener noreferrer",
|
|
3079
|
+
className: "underline underline-offset-4 hover:text-primary transition-colors font-medium",
|
|
3080
|
+
children: "Privacy Policy"
|
|
3081
|
+
}
|
|
3082
|
+
),
|
|
3083
|
+
"."
|
|
3084
|
+
] })
|
|
3085
|
+
] }) })
|
|
3086
|
+
]
|
|
3087
|
+
}
|
|
3088
|
+
);
|
|
3089
|
+
}
|
|
2808
3090
|
function ChatFull({
|
|
2809
3091
|
title = "Chat",
|
|
2810
|
-
placeholder
|
|
3092
|
+
placeholder,
|
|
2811
3093
|
starterPrompts,
|
|
2812
3094
|
options,
|
|
2813
3095
|
className,
|
|
@@ -2816,134 +3098,140 @@ function ChatFull({
|
|
|
2816
3098
|
rightSidebar,
|
|
2817
3099
|
leftSidebarClassName,
|
|
2818
3100
|
rightSidebarClassName,
|
|
2819
|
-
leftSidebarCollapsible = false,
|
|
2820
|
-
rightSidebarCollapsible = false,
|
|
2821
|
-
defaultLeftSidebarCollapsed = false,
|
|
2822
|
-
defaultRightSidebarCollapsed = false,
|
|
2823
|
-
leftSidebarCollapsed: controlledLeftCollapsed,
|
|
2824
|
-
rightSidebarCollapsed: controlledRightCollapsed,
|
|
2825
|
-
onLeftSidebarCollapseChange,
|
|
2826
|
-
onRightSidebarCollapseChange,
|
|
2827
3101
|
autoFocus = false,
|
|
2828
|
-
defaultSelectedIds
|
|
3102
|
+
defaultSelectedIds,
|
|
3103
|
+
showWelcomeScreen = false,
|
|
3104
|
+
welcomeScreenProps
|
|
2829
3105
|
}) {
|
|
2830
|
-
const
|
|
2831
|
-
|
|
2832
|
-
|
|
2833
|
-
const [
|
|
2834
|
-
|
|
2835
|
-
|
|
2836
|
-
const leftCollapsed = controlledLeftCollapsed !== void 0 ? controlledLeftCollapsed : internalLeftCollapsed;
|
|
2837
|
-
const rightCollapsed = controlledRightCollapsed !== void 0 ? controlledRightCollapsed : internalRightCollapsed;
|
|
2838
|
-
const handleLeftToggle = () => {
|
|
2839
|
-
const newCollapsed = !leftCollapsed;
|
|
2840
|
-
if (controlledLeftCollapsed === void 0) {
|
|
2841
|
-
setInternalLeftCollapsed(newCollapsed);
|
|
3106
|
+
const { isMobile, isTablet } = useScreenSize();
|
|
3107
|
+
const { isAuthenticated, isLoading } = useAuth();
|
|
3108
|
+
const isSmallScreen = isMobile || isTablet;
|
|
3109
|
+
const [internalLeftCollapsed, setInternalLeftCollapsed] = useState(() => {
|
|
3110
|
+
if (typeof window !== "undefined") {
|
|
3111
|
+
return window.innerWidth < 1024;
|
|
2842
3112
|
}
|
|
2843
|
-
|
|
2844
|
-
};
|
|
2845
|
-
const
|
|
2846
|
-
|
|
2847
|
-
|
|
2848
|
-
setInternalRightCollapsed(newCollapsed);
|
|
3113
|
+
return false;
|
|
3114
|
+
});
|
|
3115
|
+
const [internalRightCollapsed, setInternalRightCollapsed] = useState(() => {
|
|
3116
|
+
if (typeof window !== "undefined") {
|
|
3117
|
+
return window.innerWidth < 1024;
|
|
2849
3118
|
}
|
|
2850
|
-
|
|
2851
|
-
};
|
|
2852
|
-
|
|
2853
|
-
|
|
2854
|
-
|
|
2855
|
-
|
|
2856
|
-
|
|
2857
|
-
|
|
2858
|
-
|
|
2859
|
-
|
|
2860
|
-
|
|
2861
|
-
|
|
2862
|
-
|
|
2863
|
-
|
|
2864
|
-
|
|
2865
|
-
|
|
2866
|
-
|
|
2867
|
-
|
|
2868
|
-
|
|
2869
|
-
|
|
2870
|
-
|
|
2871
|
-
|
|
2872
|
-
|
|
2873
|
-
|
|
2874
|
-
|
|
2875
|
-
|
|
2876
|
-
|
|
2877
|
-
|
|
2878
|
-
|
|
2879
|
-
|
|
2880
|
-
|
|
2881
|
-
|
|
2882
|
-
|
|
2883
|
-
|
|
2884
|
-
|
|
2885
|
-
|
|
2886
|
-
|
|
2887
|
-
|
|
2888
|
-
|
|
2889
|
-
|
|
2890
|
-
|
|
2891
|
-
|
|
2892
|
-
|
|
2893
|
-
|
|
2894
|
-
|
|
2895
|
-
|
|
2896
|
-
|
|
2897
|
-
|
|
2898
|
-
|
|
2899
|
-
|
|
2900
|
-
|
|
2901
|
-
|
|
2902
|
-
|
|
2903
|
-
|
|
2904
|
-
|
|
2905
|
-
|
|
2906
|
-
|
|
2907
|
-
|
|
2908
|
-
|
|
2909
|
-
"
|
|
2910
|
-
|
|
2911
|
-
|
|
2912
|
-
|
|
2913
|
-
|
|
2914
|
-
|
|
2915
|
-
|
|
2916
|
-
|
|
2917
|
-
|
|
2918
|
-
|
|
2919
|
-
|
|
2920
|
-
|
|
2921
|
-
|
|
2922
|
-
|
|
2923
|
-
|
|
2924
|
-
|
|
2925
|
-
|
|
2926
|
-
|
|
2927
|
-
|
|
2928
|
-
|
|
2929
|
-
|
|
2930
|
-
|
|
2931
|
-
|
|
2932
|
-
|
|
2933
|
-
|
|
2934
|
-
|
|
2935
|
-
|
|
2936
|
-
|
|
2937
|
-
|
|
2938
|
-
|
|
2939
|
-
|
|
2940
|
-
|
|
3119
|
+
return false;
|
|
3120
|
+
});
|
|
3121
|
+
useEffect(() => {
|
|
3122
|
+
if (isSmallScreen) {
|
|
3123
|
+
setInternalLeftCollapsed(true);
|
|
3124
|
+
setInternalRightCollapsed(true);
|
|
3125
|
+
}
|
|
3126
|
+
}, [isSmallScreen]);
|
|
3127
|
+
const leftCollapsed = internalLeftCollapsed;
|
|
3128
|
+
const rightCollapsed = internalRightCollapsed;
|
|
3129
|
+
const handleLeftToggle = useCallback((collapsed) => {
|
|
3130
|
+
setInternalLeftCollapsed(collapsed);
|
|
3131
|
+
}, []);
|
|
3132
|
+
const handleRightToggle = useCallback((collapsed) => {
|
|
3133
|
+
setInternalRightCollapsed(collapsed);
|
|
3134
|
+
}, []);
|
|
3135
|
+
const contextValue = useMemo(
|
|
3136
|
+
() => ({
|
|
3137
|
+
leftCollapsed,
|
|
3138
|
+
rightCollapsed,
|
|
3139
|
+
setLeftCollapsed: handleLeftToggle,
|
|
3140
|
+
setRightCollapsed: handleRightToggle,
|
|
3141
|
+
leftCollapsible: true,
|
|
3142
|
+
rightCollapsible: true
|
|
3143
|
+
}),
|
|
3144
|
+
[leftCollapsed, rightCollapsed, handleLeftToggle, handleRightToggle]
|
|
3145
|
+
);
|
|
3146
|
+
if (showWelcomeScreen && !isAuthenticated && !isLoading) {
|
|
3147
|
+
return /* @__PURE__ */ jsx(WelcomeScreen, { ...welcomeScreenProps });
|
|
3148
|
+
}
|
|
3149
|
+
return /* @__PURE__ */ jsx(ChatSidebarContext.Provider, { value: contextValue, children: /* @__PURE__ */ jsxs(
|
|
3150
|
+
"div",
|
|
3151
|
+
{
|
|
3152
|
+
className: cn("flex flex-col h-full w-full bg-background", className),
|
|
3153
|
+
children: [
|
|
3154
|
+
title && /* @__PURE__ */ jsx(ChatHeader, { title, ...headerProps }),
|
|
3155
|
+
/* @__PURE__ */ jsxs("div", { className: "flex-1 overflow-hidden flex relative", children: [
|
|
3156
|
+
leftSidebar && /* @__PURE__ */ jsx(
|
|
3157
|
+
"div",
|
|
3158
|
+
{
|
|
3159
|
+
className: cn(
|
|
3160
|
+
"flex-shrink-0 border-r border-border bg-background transition-all duration-300 ease-in-out overflow-hidden flex flex-col",
|
|
3161
|
+
leftCollapsed ? "w-0 border-r-0 min-w-0" : "",
|
|
3162
|
+
!leftCollapsed && leftSidebarClassName
|
|
3163
|
+
),
|
|
3164
|
+
children: /* @__PURE__ */ jsx("div", { className: "flex-1 overflow-hidden min-h-0", children: leftSidebar })
|
|
3165
|
+
}
|
|
3166
|
+
),
|
|
3167
|
+
/* @__PURE__ */ jsx("div", { className: "flex-1 overflow-hidden min-w-0", children: /* @__PURE__ */ jsx(
|
|
3168
|
+
Thread,
|
|
3169
|
+
{
|
|
3170
|
+
placeholder,
|
|
3171
|
+
starterPrompts,
|
|
3172
|
+
options,
|
|
3173
|
+
autoFocus,
|
|
3174
|
+
defaultSelectedIds
|
|
3175
|
+
}
|
|
3176
|
+
) }),
|
|
3177
|
+
rightSidebar && /* @__PURE__ */ jsx(
|
|
3178
|
+
"div",
|
|
3179
|
+
{
|
|
3180
|
+
className: cn(
|
|
3181
|
+
"flex-shrink-0 border-l border-border bg-background transition-all duration-300 ease-in-out overflow-hidden flex flex-col",
|
|
3182
|
+
rightCollapsed ? "w-0 border-l-0 min-w-0" : "",
|
|
3183
|
+
!rightCollapsed && rightSidebarClassName
|
|
3184
|
+
),
|
|
3185
|
+
children: /* @__PURE__ */ jsx("div", { className: "flex-1 overflow-hidden min-h-0", children: rightSidebar })
|
|
3186
|
+
}
|
|
3187
|
+
)
|
|
3188
|
+
] })
|
|
3189
|
+
]
|
|
3190
|
+
}
|
|
3191
|
+
) });
|
|
3192
|
+
}
|
|
3193
|
+
function SidebarToggle({ side, className }) {
|
|
3194
|
+
const {
|
|
3195
|
+
leftCollapsed,
|
|
3196
|
+
rightCollapsed,
|
|
3197
|
+
setLeftCollapsed,
|
|
3198
|
+
setRightCollapsed,
|
|
3199
|
+
leftCollapsible,
|
|
3200
|
+
rightCollapsible
|
|
3201
|
+
} = useChatSidebar();
|
|
3202
|
+
if (side === "left") {
|
|
3203
|
+
if (!leftCollapsible) return null;
|
|
3204
|
+
return /* @__PURE__ */ jsx(
|
|
3205
|
+
Button,
|
|
3206
|
+
{
|
|
3207
|
+
variant: "ghost",
|
|
3208
|
+
onClick: () => setLeftCollapsed(!leftCollapsed),
|
|
3209
|
+
"aria-label": leftCollapsed ? "Expand left sidebar" : "Collapse left sidebar",
|
|
3210
|
+
className: cn("", className),
|
|
3211
|
+
children: leftCollapsed ? /* @__PURE__ */ jsx(IconLayoutSidebarLeftExpand, { className: "h-4 w-4" }) : /* @__PURE__ */ jsx(IconLayoutSidebarLeftCollapse, { className: "h-4 w-4" })
|
|
3212
|
+
}
|
|
3213
|
+
);
|
|
3214
|
+
}
|
|
3215
|
+
if (side === "right") {
|
|
3216
|
+
if (!rightCollapsible) return null;
|
|
3217
|
+
return /* @__PURE__ */ jsx(
|
|
3218
|
+
Button,
|
|
3219
|
+
{
|
|
3220
|
+
variant: "ghost",
|
|
3221
|
+
onClick: () => setRightCollapsed(!rightCollapsed),
|
|
3222
|
+
"aria-label": rightCollapsed ? "Expand right sidebar" : "Collapse right sidebar",
|
|
3223
|
+
className: cn("", className),
|
|
3224
|
+
children: rightCollapsed ? /* @__PURE__ */ jsx(IconLayoutSidebarRightExpand, { className: "h-4 w-4" }) : /* @__PURE__ */ jsx(IconLayoutSidebarRightCollapse, { className: "h-4 w-4" })
|
|
3225
|
+
}
|
|
3226
|
+
);
|
|
3227
|
+
}
|
|
3228
|
+
return null;
|
|
2941
3229
|
}
|
|
2942
|
-
var PopoverContext =
|
|
3230
|
+
var PopoverContext = React12.createContext(
|
|
2943
3231
|
void 0
|
|
2944
3232
|
);
|
|
2945
3233
|
function usePopoverContext() {
|
|
2946
|
-
const context =
|
|
3234
|
+
const context = React12.useContext(PopoverContext);
|
|
2947
3235
|
if (!context) {
|
|
2948
3236
|
throw new Error("Popover components must be used within a Popover");
|
|
2949
3237
|
}
|
|
@@ -2955,10 +3243,10 @@ function Popover({
|
|
|
2955
3243
|
open: controlledOpen,
|
|
2956
3244
|
onOpenChange
|
|
2957
3245
|
}) {
|
|
2958
|
-
const [internalOpen, setInternalOpen] =
|
|
2959
|
-
const triggerRef =
|
|
3246
|
+
const [internalOpen, setInternalOpen] = React12.useState(defaultOpen);
|
|
3247
|
+
const triggerRef = React12.useRef(null);
|
|
2960
3248
|
const open = controlledOpen ?? internalOpen;
|
|
2961
|
-
const setOpen =
|
|
3249
|
+
const setOpen = React12.useCallback(
|
|
2962
3250
|
(newOpen) => {
|
|
2963
3251
|
if (controlledOpen === void 0) {
|
|
2964
3252
|
setInternalOpen(newOpen);
|
|
@@ -2967,7 +3255,7 @@ function Popover({
|
|
|
2967
3255
|
},
|
|
2968
3256
|
[controlledOpen, onOpenChange]
|
|
2969
3257
|
);
|
|
2970
|
-
const value =
|
|
3258
|
+
const value = React12.useMemo(
|
|
2971
3259
|
() => ({
|
|
2972
3260
|
open,
|
|
2973
3261
|
setOpen,
|
|
@@ -2977,15 +3265,15 @@ function Popover({
|
|
|
2977
3265
|
);
|
|
2978
3266
|
return /* @__PURE__ */ jsx(PopoverContext.Provider, { value, children });
|
|
2979
3267
|
}
|
|
2980
|
-
var PopoverTrigger =
|
|
3268
|
+
var PopoverTrigger = React12.forwardRef(
|
|
2981
3269
|
({ asChild, className, children, ...props }, ref) => {
|
|
2982
3270
|
const { setOpen, triggerRef } = usePopoverContext();
|
|
2983
3271
|
const handleClick = (e) => {
|
|
2984
3272
|
setOpen(true);
|
|
2985
3273
|
props.onClick?.(e);
|
|
2986
3274
|
};
|
|
2987
|
-
if (asChild &&
|
|
2988
|
-
return
|
|
3275
|
+
if (asChild && React12.isValidElement(children)) {
|
|
3276
|
+
return React12.cloneElement(children, {
|
|
2989
3277
|
ref: (node) => {
|
|
2990
3278
|
triggerRef.current = node;
|
|
2991
3279
|
if (typeof children.ref === "function") {
|
|
@@ -3017,7 +3305,7 @@ var PopoverTrigger = React10.forwardRef(
|
|
|
3017
3305
|
}
|
|
3018
3306
|
);
|
|
3019
3307
|
PopoverTrigger.displayName = "PopoverTrigger";
|
|
3020
|
-
var PopoverContent =
|
|
3308
|
+
var PopoverContent = React12.forwardRef(
|
|
3021
3309
|
({
|
|
3022
3310
|
className,
|
|
3023
3311
|
side = "bottom",
|
|
@@ -3028,9 +3316,9 @@ var PopoverContent = React10.forwardRef(
|
|
|
3028
3316
|
...props
|
|
3029
3317
|
}, ref) => {
|
|
3030
3318
|
const { open, setOpen, triggerRef } = usePopoverContext();
|
|
3031
|
-
const [position, setPosition] =
|
|
3032
|
-
const contentRef =
|
|
3033
|
-
|
|
3319
|
+
const [position, setPosition] = React12.useState({ top: 0, left: 0 });
|
|
3320
|
+
const contentRef = React12.useRef(null);
|
|
3321
|
+
React12.useEffect(() => {
|
|
3034
3322
|
if (!open || !triggerRef.current) return;
|
|
3035
3323
|
const updatePosition = () => {
|
|
3036
3324
|
if (!triggerRef.current || !contentRef.current) return;
|
|
@@ -3091,7 +3379,7 @@ var PopoverContent = React10.forwardRef(
|
|
|
3091
3379
|
window.removeEventListener("scroll", updatePosition, true);
|
|
3092
3380
|
};
|
|
3093
3381
|
}, [open, side, align, sideOffset, alignOffset, triggerRef]);
|
|
3094
|
-
|
|
3382
|
+
React12.useEffect(() => {
|
|
3095
3383
|
if (!open) return;
|
|
3096
3384
|
const handleClickOutside = (event) => {
|
|
3097
3385
|
if (contentRef.current && !contentRef.current.contains(event.target) && triggerRef.current && !triggerRef.current.contains(event.target)) {
|
|
@@ -3147,7 +3435,7 @@ var ThreadPopover = ({
|
|
|
3147
3435
|
emptyState,
|
|
3148
3436
|
onThreadSelect
|
|
3149
3437
|
}) => {
|
|
3150
|
-
const [isOpen, setIsOpen] =
|
|
3438
|
+
const [isOpen, setIsOpen] = React12.useState(false);
|
|
3151
3439
|
useHotkeys(
|
|
3152
3440
|
"h",
|
|
3153
3441
|
(e) => {
|
|
@@ -3202,7 +3490,7 @@ var CreateThreadButton = ({
|
|
|
3202
3490
|
onThreadCreated
|
|
3203
3491
|
}) => {
|
|
3204
3492
|
const { createThread } = useThreads();
|
|
3205
|
-
const [isCreating, setIsCreating] =
|
|
3493
|
+
const [isCreating, setIsCreating] = React12.useState(false);
|
|
3206
3494
|
const handleCreateThread = async () => {
|
|
3207
3495
|
if (isCreating) return;
|
|
3208
3496
|
try {
|
|
@@ -3328,10 +3616,10 @@ var AccountDialog = ({
|
|
|
3328
3616
|
size
|
|
3329
3617
|
}) => {
|
|
3330
3618
|
const { isLoading, isAuthenticated, user, login, logout } = useAuth();
|
|
3331
|
-
const [open, setOpen] =
|
|
3332
|
-
const [accountInfoOpen, setAccountInfoOpen] =
|
|
3333
|
-
const [error, setError] =
|
|
3334
|
-
const initials =
|
|
3619
|
+
const [open, setOpen] = React12.useState(false);
|
|
3620
|
+
const [accountInfoOpen, setAccountInfoOpen] = React12.useState(false);
|
|
3621
|
+
const [error, setError] = React12.useState(null);
|
|
3622
|
+
const initials = React12.useMemo(() => {
|
|
3335
3623
|
const name = user?.displayName || user?.name;
|
|
3336
3624
|
if (!name) return "";
|
|
3337
3625
|
return name.split(" ").map((n) => n[0]).join("").toUpperCase().slice(0, 2);
|
|
@@ -3504,6 +3792,6 @@ function ThemeToggle() {
|
|
|
3504
3792
|
);
|
|
3505
3793
|
}
|
|
3506
3794
|
|
|
3507
|
-
export { AccountDialog, AuthContext, AuthProvider, ChatFull, ChatHeader, ChatPopup, ChatSidebar, Composer, CreateThreadButton, MelonyClientProvider, MelonyContext, ThemeProvider, ThemeToggle, Thread, ThreadContext, ThreadList, ThreadPopover, ThreadProvider, UIRenderer, groupEventsToMessages, useAuth, useMelony, useTheme, useThreads };
|
|
3795
|
+
export { AccountDialog, AuthContext, AuthProvider, Badge2 as Badge, Box, Button2 as Button, Card2 as Card, Chart, ChatFull, ChatHeader, ChatPopup, ChatSidebar, ChatSidebarContext, Checkbox, Col, Composer, CreateThreadButton, Divider, Form, Heading, Image, Input2 as Input, Label2 as Label, List, ListItem, MelonyClientProvider, MelonyContext, RadioGroup, Row, Select2 as Select, SidebarToggle, Spacer, Text, Textarea2 as Textarea, ThemeProvider, ThemeToggle, Thread, ThreadContext, ThreadList, ThreadPopover, ThreadProvider, UIRenderer, WelcomeScreen, groupEventsToMessages, useAuth, useChatSidebar, useMelony, useScreenSize, useTheme, useThreads };
|
|
3508
3796
|
//# sourceMappingURL=index.js.map
|
|
3509
3797
|
//# sourceMappingURL=index.js.map
|