@lukeashford/aurelius 3.9.0 → 4.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.d.mts +15 -36
- package/dist/index.d.ts +15 -36
- package/dist/index.js +1082 -1289
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +470 -674
- package/dist/index.mjs.map +1 -1
- package/llms.md +8 -6
- package/package.json +1 -1
package/dist/index.mjs
CHANGED
|
@@ -92,6 +92,147 @@ Input.displayName = "Input";
|
|
|
92
92
|
import React4, { createContext, useContext } from "react";
|
|
93
93
|
import { Check } from "lucide-react";
|
|
94
94
|
|
|
95
|
+
// src/utils/clipboard.ts
|
|
96
|
+
async function copyToClipboard(text) {
|
|
97
|
+
if (typeof navigator !== "undefined" && navigator.clipboard) {
|
|
98
|
+
try {
|
|
99
|
+
await navigator.clipboard.writeText(text);
|
|
100
|
+
return true;
|
|
101
|
+
} catch {
|
|
102
|
+
}
|
|
103
|
+
}
|
|
104
|
+
if (typeof document === "undefined") {
|
|
105
|
+
return false;
|
|
106
|
+
}
|
|
107
|
+
const textArea = document.createElement("textarea");
|
|
108
|
+
textArea.value = text;
|
|
109
|
+
textArea.setAttribute("readonly", "");
|
|
110
|
+
textArea.setAttribute("aria-hidden", "true");
|
|
111
|
+
textArea.style.position = "fixed";
|
|
112
|
+
textArea.style.opacity = "0";
|
|
113
|
+
textArea.style.pointerEvents = "none";
|
|
114
|
+
document.body.appendChild(textArea);
|
|
115
|
+
try {
|
|
116
|
+
textArea.select();
|
|
117
|
+
return document.execCommand("copy");
|
|
118
|
+
} catch {
|
|
119
|
+
return false;
|
|
120
|
+
} finally {
|
|
121
|
+
document.body.removeChild(textArea);
|
|
122
|
+
}
|
|
123
|
+
}
|
|
124
|
+
|
|
125
|
+
// src/utils/hooks.ts
|
|
126
|
+
import { useCallback, useEffect, useRef, useState } from "react";
|
|
127
|
+
function composeRefs(...refs) {
|
|
128
|
+
return (node) => {
|
|
129
|
+
for (const ref of refs) {
|
|
130
|
+
if (!ref) {
|
|
131
|
+
continue;
|
|
132
|
+
}
|
|
133
|
+
if (typeof ref === "function") {
|
|
134
|
+
ref(node);
|
|
135
|
+
} else {
|
|
136
|
+
;
|
|
137
|
+
ref.current = node;
|
|
138
|
+
}
|
|
139
|
+
}
|
|
140
|
+
};
|
|
141
|
+
}
|
|
142
|
+
var scrollLockCount = 0;
|
|
143
|
+
var scrollLockOriginalOverflow = null;
|
|
144
|
+
var scrollLockOriginalPaddingRight = null;
|
|
145
|
+
function useScrollLock(isLocked) {
|
|
146
|
+
useEffect(() => {
|
|
147
|
+
if (!isLocked || typeof document === "undefined") {
|
|
148
|
+
return;
|
|
149
|
+
}
|
|
150
|
+
if (scrollLockCount === 0) {
|
|
151
|
+
scrollLockOriginalOverflow = document.body.style.overflow;
|
|
152
|
+
scrollLockOriginalPaddingRight = document.body.style.paddingRight;
|
|
153
|
+
const scrollbarWidth = window.innerWidth - document.documentElement.clientWidth;
|
|
154
|
+
document.body.style.overflow = "hidden";
|
|
155
|
+
if (scrollbarWidth > 0) {
|
|
156
|
+
document.body.style.paddingRight = `${scrollbarWidth}px`;
|
|
157
|
+
}
|
|
158
|
+
}
|
|
159
|
+
scrollLockCount++;
|
|
160
|
+
return () => {
|
|
161
|
+
scrollLockCount--;
|
|
162
|
+
if (scrollLockCount === 0) {
|
|
163
|
+
document.body.style.overflow = scrollLockOriginalOverflow ?? "";
|
|
164
|
+
document.body.style.paddingRight = scrollLockOriginalPaddingRight ?? "";
|
|
165
|
+
scrollLockOriginalOverflow = null;
|
|
166
|
+
scrollLockOriginalPaddingRight = null;
|
|
167
|
+
}
|
|
168
|
+
};
|
|
169
|
+
}, [isLocked]);
|
|
170
|
+
}
|
|
171
|
+
function useEscapeKey(onEscape, isActive = true) {
|
|
172
|
+
useEffect(() => {
|
|
173
|
+
if (!isActive || typeof window === "undefined") {
|
|
174
|
+
return;
|
|
175
|
+
}
|
|
176
|
+
const handler = (e) => {
|
|
177
|
+
if (e.key === "Escape") {
|
|
178
|
+
onEscape();
|
|
179
|
+
}
|
|
180
|
+
};
|
|
181
|
+
window.addEventListener("keydown", handler);
|
|
182
|
+
return () => window.removeEventListener("keydown", handler);
|
|
183
|
+
}, [onEscape, isActive]);
|
|
184
|
+
}
|
|
185
|
+
function useClickOutside(ref, handler, isActive = true) {
|
|
186
|
+
useEffect(() => {
|
|
187
|
+
if (!isActive || typeof document === "undefined") {
|
|
188
|
+
return;
|
|
189
|
+
}
|
|
190
|
+
const listener = (event) => {
|
|
191
|
+
const node = ref.current;
|
|
192
|
+
if (node && !node.contains(event.target)) {
|
|
193
|
+
handler(event);
|
|
194
|
+
}
|
|
195
|
+
};
|
|
196
|
+
document.addEventListener("mousedown", listener);
|
|
197
|
+
return () => document.removeEventListener("mousedown", listener);
|
|
198
|
+
}, [ref, handler, isActive]);
|
|
199
|
+
}
|
|
200
|
+
function useCopyToClipboard(resetMs = 2e3) {
|
|
201
|
+
const [copied, setCopied] = useState(false);
|
|
202
|
+
const timerRef = useRef(null);
|
|
203
|
+
const mountedRef = useRef(true);
|
|
204
|
+
useEffect(() => {
|
|
205
|
+
mountedRef.current = true;
|
|
206
|
+
return () => {
|
|
207
|
+
mountedRef.current = false;
|
|
208
|
+
if (timerRef.current !== null) {
|
|
209
|
+
clearTimeout(timerRef.current);
|
|
210
|
+
timerRef.current = null;
|
|
211
|
+
}
|
|
212
|
+
};
|
|
213
|
+
}, []);
|
|
214
|
+
const copy = useCallback(async (text) => {
|
|
215
|
+
const ok = await copyToClipboard(text);
|
|
216
|
+
if (!mountedRef.current) {
|
|
217
|
+
return ok;
|
|
218
|
+
}
|
|
219
|
+
if (ok) {
|
|
220
|
+
setCopied(true);
|
|
221
|
+
if (timerRef.current !== null) {
|
|
222
|
+
clearTimeout(timerRef.current);
|
|
223
|
+
}
|
|
224
|
+
timerRef.current = setTimeout(() => {
|
|
225
|
+
timerRef.current = null;
|
|
226
|
+
if (mountedRef.current) {
|
|
227
|
+
setCopied(false);
|
|
228
|
+
}
|
|
229
|
+
}, resetMs);
|
|
230
|
+
}
|
|
231
|
+
return ok;
|
|
232
|
+
}, [resetMs]);
|
|
233
|
+
return { copied, copy };
|
|
234
|
+
}
|
|
235
|
+
|
|
95
236
|
// src/components/Skeleton.tsx
|
|
96
237
|
import React3 from "react";
|
|
97
238
|
var Skeleton = React3.forwardRef(
|
|
@@ -116,8 +257,7 @@ function slotLoading(loading, path) {
|
|
|
116
257
|
return false;
|
|
117
258
|
}
|
|
118
259
|
if (Array.isArray(path)) {
|
|
119
|
-
|
|
120
|
-
return !!loading[section]?.[field];
|
|
260
|
+
return !!loading.header?.[path[1]];
|
|
121
261
|
}
|
|
122
262
|
return !!loading[path];
|
|
123
263
|
}
|
|
@@ -1393,29 +1533,28 @@ var Select = React20.forwardRef(
|
|
|
1393
1533
|
Select.displayName = "Select";
|
|
1394
1534
|
|
|
1395
1535
|
// src/components/Checkbox.tsx
|
|
1396
|
-
import React21, { useCallback } from "react";
|
|
1536
|
+
import React21, { useCallback as useCallback2, useId } from "react";
|
|
1397
1537
|
var checkmarkSvg = `url("data:image/svg+xml,%3csvg viewBox='0 0 16 16' fill='%231A1A1A' xmlns='http://www.w3.org/2000/svg'%3e%3cpath d='M12.207 4.793a1 1 0 010 1.414l-5 5a1 1 0 01-1.414 0l-2-2a1 1 0 011.414-1.414L6.5 9.086l4.293-4.293a1 1 0 011.414 0z'/%3e%3c/svg%3e")`;
|
|
1398
1538
|
var Checkbox = React21.forwardRef(
|
|
1399
|
-
({ className, label, id, ...rest }, ref) => {
|
|
1400
|
-
const
|
|
1401
|
-
const
|
|
1402
|
-
|
|
1403
|
-
|
|
1404
|
-
|
|
1405
|
-
}
|
|
1539
|
+
({ className, label, id, onChange, ...rest }, ref) => {
|
|
1540
|
+
const generatedId = useId();
|
|
1541
|
+
const inputId = id || rest.name || generatedId;
|
|
1542
|
+
const initBackground = useCallback2((node) => {
|
|
1543
|
+
if (node && node.checked) {
|
|
1544
|
+
node.style.backgroundImage = checkmarkSvg;
|
|
1406
1545
|
}
|
|
1407
|
-
|
|
1408
|
-
|
|
1409
|
-
|
|
1410
|
-
|
|
1411
|
-
|
|
1412
|
-
}, [ref]);
|
|
1546
|
+
}, []);
|
|
1547
|
+
const handleChange = useCallback2((e) => {
|
|
1548
|
+
e.currentTarget.style.backgroundImage = e.currentTarget.checked ? checkmarkSvg : "none";
|
|
1549
|
+
onChange?.(e);
|
|
1550
|
+
}, [onChange]);
|
|
1413
1551
|
return /* @__PURE__ */ React21.createElement("div", { className: "flex items-center" }, /* @__PURE__ */ React21.createElement(
|
|
1414
1552
|
"input",
|
|
1415
1553
|
{
|
|
1554
|
+
...rest,
|
|
1416
1555
|
type: "checkbox",
|
|
1417
1556
|
id: inputId,
|
|
1418
|
-
ref:
|
|
1557
|
+
ref: composeRefs(initBackground, ref),
|
|
1419
1558
|
className: cx(
|
|
1420
1559
|
"appearance-none h-4 w-4 border border-ash bg-graphite",
|
|
1421
1560
|
"checked:bg-gold checked:border-gold",
|
|
@@ -1429,16 +1568,7 @@ var Checkbox = React21.forwardRef(
|
|
|
1429
1568
|
backgroundSize: "contain",
|
|
1430
1569
|
backgroundRepeat: "no-repeat"
|
|
1431
1570
|
},
|
|
1432
|
-
onChange:
|
|
1433
|
-
const input = e.currentTarget;
|
|
1434
|
-
if (input.checked) {
|
|
1435
|
-
input.style.backgroundImage = checkmarkSvg;
|
|
1436
|
-
} else {
|
|
1437
|
-
input.style.backgroundImage = "none";
|
|
1438
|
-
}
|
|
1439
|
-
rest.onChange?.(e);
|
|
1440
|
-
},
|
|
1441
|
-
...rest
|
|
1571
|
+
onChange: handleChange
|
|
1442
1572
|
}
|
|
1443
1573
|
), label && /* @__PURE__ */ React21.createElement(
|
|
1444
1574
|
"label",
|
|
@@ -1453,29 +1583,44 @@ var Checkbox = React21.forwardRef(
|
|
|
1453
1583
|
Checkbox.displayName = "Checkbox";
|
|
1454
1584
|
|
|
1455
1585
|
// src/components/Radio.tsx
|
|
1456
|
-
import React22, { useCallback as
|
|
1586
|
+
import React22, { useCallback as useCallback3, useId as useId2 } from "react";
|
|
1457
1587
|
var radioDotSvg = `url("data:image/svg+xml,%3csvg viewBox='0 0 16 16' fill='%231A1A1A' xmlns='http://www.w3.org/2000/svg'%3e%3ccircle cx='8' cy='8' r='3'/%3e%3c/svg%3e")`;
|
|
1458
1588
|
var Radio = React22.forwardRef(
|
|
1459
|
-
({ className, label, id, ...rest }, ref) => {
|
|
1460
|
-
const
|
|
1461
|
-
const
|
|
1462
|
-
|
|
1463
|
-
|
|
1464
|
-
|
|
1465
|
-
}
|
|
1589
|
+
({ className, label, id, onChange, ...rest }, ref) => {
|
|
1590
|
+
const generatedId = useId2();
|
|
1591
|
+
const inputId = id || rest.name || generatedId;
|
|
1592
|
+
const initBackground = useCallback3((node) => {
|
|
1593
|
+
if (node && node.checked) {
|
|
1594
|
+
node.style.backgroundImage = radioDotSvg;
|
|
1466
1595
|
}
|
|
1467
|
-
|
|
1468
|
-
|
|
1469
|
-
|
|
1470
|
-
|
|
1596
|
+
}, []);
|
|
1597
|
+
const handleChange = useCallback3((e) => {
|
|
1598
|
+
const input = e.currentTarget;
|
|
1599
|
+
if (input.checked) {
|
|
1600
|
+
input.style.backgroundImage = radioDotSvg;
|
|
1601
|
+
if (input.name) {
|
|
1602
|
+
const escaped = typeof CSS !== "undefined" && typeof CSS.escape === "function" ? CSS.escape(input.name) : input.name.replace(/["\\\]]/g, "\\$&");
|
|
1603
|
+
const radios = input.ownerDocument.querySelectorAll(
|
|
1604
|
+
`input[type="radio"][name="${escaped}"]`
|
|
1605
|
+
);
|
|
1606
|
+
radios.forEach((radio) => {
|
|
1607
|
+
if (radio !== input) {
|
|
1608
|
+
radio.style.backgroundImage = "none";
|
|
1609
|
+
}
|
|
1610
|
+
});
|
|
1611
|
+
}
|
|
1612
|
+
} else {
|
|
1613
|
+
input.style.backgroundImage = "none";
|
|
1471
1614
|
}
|
|
1472
|
-
|
|
1615
|
+
onChange?.(e);
|
|
1616
|
+
}, [onChange]);
|
|
1473
1617
|
return /* @__PURE__ */ React22.createElement("div", { className: "flex items-center" }, /* @__PURE__ */ React22.createElement(
|
|
1474
1618
|
"input",
|
|
1475
1619
|
{
|
|
1620
|
+
...rest,
|
|
1476
1621
|
type: "radio",
|
|
1477
1622
|
id: inputId,
|
|
1478
|
-
ref:
|
|
1623
|
+
ref: composeRefs(initBackground, ref),
|
|
1479
1624
|
className: cx(
|
|
1480
1625
|
"appearance-none h-4 w-4 border border-ash rounded-full bg-graphite",
|
|
1481
1626
|
"checked:bg-gold checked:border-gold",
|
|
@@ -1489,26 +1634,7 @@ var Radio = React22.forwardRef(
|
|
|
1489
1634
|
backgroundSize: "contain",
|
|
1490
1635
|
backgroundRepeat: "no-repeat"
|
|
1491
1636
|
},
|
|
1492
|
-
onChange:
|
|
1493
|
-
const input = e.currentTarget;
|
|
1494
|
-
if (input.checked) {
|
|
1495
|
-
input.style.backgroundImage = radioDotSvg;
|
|
1496
|
-
if (input.name) {
|
|
1497
|
-
const radios = document.querySelectorAll(
|
|
1498
|
-
`input[type="radio"][name="${input.name}"]`
|
|
1499
|
-
);
|
|
1500
|
-
radios.forEach((radio) => {
|
|
1501
|
-
if (radio !== input) {
|
|
1502
|
-
radio.style.backgroundImage = "none";
|
|
1503
|
-
}
|
|
1504
|
-
});
|
|
1505
|
-
}
|
|
1506
|
-
} else {
|
|
1507
|
-
input.style.backgroundImage = "none";
|
|
1508
|
-
}
|
|
1509
|
-
rest.onChange?.(e);
|
|
1510
|
-
},
|
|
1511
|
-
...rest
|
|
1637
|
+
onChange: handleChange
|
|
1512
1638
|
}
|
|
1513
1639
|
), label && /* @__PURE__ */ React22.createElement(
|
|
1514
1640
|
"label",
|
|
@@ -1523,7 +1649,7 @@ var Radio = React22.forwardRef(
|
|
|
1523
1649
|
Radio.displayName = "Radio";
|
|
1524
1650
|
|
|
1525
1651
|
// src/components/Switch.tsx
|
|
1526
|
-
import React23, { useCallback as
|
|
1652
|
+
import React23, { useCallback as useCallback4, useRef as useRef2, useState as useState2 } from "react";
|
|
1527
1653
|
var Switch = React23.forwardRef(
|
|
1528
1654
|
({
|
|
1529
1655
|
checked: controlledChecked,
|
|
@@ -1534,11 +1660,11 @@ var Switch = React23.forwardRef(
|
|
|
1534
1660
|
label,
|
|
1535
1661
|
...rest
|
|
1536
1662
|
}, ref) => {
|
|
1537
|
-
const [internalChecked, setInternalChecked] =
|
|
1663
|
+
const [internalChecked, setInternalChecked] = useState2(defaultChecked);
|
|
1538
1664
|
const isControlled = controlledChecked !== void 0;
|
|
1539
1665
|
const checked = isControlled ? controlledChecked : internalChecked;
|
|
1540
|
-
const buttonRef =
|
|
1541
|
-
const setRefs =
|
|
1666
|
+
const buttonRef = useRef2(null);
|
|
1667
|
+
const setRefs = useCallback4(
|
|
1542
1668
|
(node) => {
|
|
1543
1669
|
buttonRef.current = node;
|
|
1544
1670
|
if (typeof ref === "function") {
|
|
@@ -1608,7 +1734,7 @@ var Switch = React23.forwardRef(
|
|
|
1608
1734
|
Switch.displayName = "Switch";
|
|
1609
1735
|
|
|
1610
1736
|
// src/components/Slider.tsx
|
|
1611
|
-
import React24, { useCallback as
|
|
1737
|
+
import React24, { useCallback as useCallback5, useRef as useRef3, useState as useState3 } from "react";
|
|
1612
1738
|
var SIZE_TRACK = {
|
|
1613
1739
|
sm: "h-1",
|
|
1614
1740
|
md: "h-2",
|
|
@@ -1635,13 +1761,13 @@ var Slider = React24.forwardRef(
|
|
|
1635
1761
|
className,
|
|
1636
1762
|
...props
|
|
1637
1763
|
}, ref) => {
|
|
1638
|
-
const [internalValue, setInternalValue] =
|
|
1639
|
-
const [isDragging, setIsDragging] =
|
|
1640
|
-
const trackRef =
|
|
1764
|
+
const [internalValue, setInternalValue] = useState3(defaultValue);
|
|
1765
|
+
const [isDragging, setIsDragging] = useState3(false);
|
|
1766
|
+
const trackRef = useRef3(null);
|
|
1641
1767
|
const isControlled = controlledValue !== void 0;
|
|
1642
1768
|
const value = isControlled ? controlledValue : internalValue;
|
|
1643
1769
|
const percentage = (value - min) / (max - min) * 100;
|
|
1644
|
-
const updateValue =
|
|
1770
|
+
const updateValue = useCallback5(
|
|
1645
1771
|
(clientX) => {
|
|
1646
1772
|
if (!trackRef.current || disabled) {
|
|
1647
1773
|
return;
|
|
@@ -1997,16 +2123,21 @@ var Progress = React28.forwardRef(
|
|
|
1997
2123
|
Progress.displayName = "Progress";
|
|
1998
2124
|
|
|
1999
2125
|
// src/components/Toast.tsx
|
|
2000
|
-
import React29, { createContext as createContext2, useCallback as
|
|
2126
|
+
import React29, { createContext as createContext2, useCallback as useCallback6, useContext as useContext2, useEffect as useEffect2, useState as useState4 } from "react";
|
|
2001
2127
|
import { createPortal } from "react-dom";
|
|
2002
2128
|
import { AlertCircle, AlertTriangle as AlertTriangle2, CheckCircle as CheckCircle2, Info as Info2, X as X2 } from "lucide-react";
|
|
2129
|
+
var toastCounter = 0;
|
|
2130
|
+
function createToastId() {
|
|
2131
|
+
toastCounter += 1;
|
|
2132
|
+
return `toast-${Date.now().toString(36)}-${toastCounter}`;
|
|
2133
|
+
}
|
|
2003
2134
|
var ToastContext = createContext2(null);
|
|
2004
2135
|
function useToast() {
|
|
2005
2136
|
const context = useContext2(ToastContext);
|
|
2006
2137
|
if (!context) {
|
|
2007
2138
|
throw new Error("useToast must be used within a ToastProvider");
|
|
2008
2139
|
}
|
|
2009
|
-
const toast =
|
|
2140
|
+
const toast = useCallback6(
|
|
2010
2141
|
(options) => {
|
|
2011
2142
|
return context.addToast(options);
|
|
2012
2143
|
},
|
|
@@ -2022,14 +2153,14 @@ var ToastProvider = ({
|
|
|
2022
2153
|
position = "bottom-right",
|
|
2023
2154
|
defaultDuration = 5e3
|
|
2024
2155
|
}) => {
|
|
2025
|
-
const [toasts, setToasts] =
|
|
2026
|
-
const [mounted, setMounted] =
|
|
2027
|
-
|
|
2156
|
+
const [toasts, setToasts] = useState4([]);
|
|
2157
|
+
const [mounted, setMounted] = useState4(false);
|
|
2158
|
+
useEffect2(() => {
|
|
2028
2159
|
setMounted(true);
|
|
2029
2160
|
}, []);
|
|
2030
|
-
const addToast =
|
|
2161
|
+
const addToast = useCallback6(
|
|
2031
2162
|
(toast) => {
|
|
2032
|
-
const id =
|
|
2163
|
+
const id = createToastId();
|
|
2033
2164
|
const newToast = {
|
|
2034
2165
|
...toast,
|
|
2035
2166
|
id,
|
|
@@ -2040,33 +2171,33 @@ var ToastProvider = ({
|
|
|
2040
2171
|
},
|
|
2041
2172
|
[defaultDuration]
|
|
2042
2173
|
);
|
|
2043
|
-
const removeToast =
|
|
2174
|
+
const removeToast = useCallback6((id) => {
|
|
2044
2175
|
setToasts((prev) => prev.filter((t) => t.id !== id));
|
|
2045
2176
|
}, []);
|
|
2046
2177
|
return /* @__PURE__ */ React29.createElement(ToastContext.Provider, { value: { toasts, addToast, removeToast, position } }, children, mounted && /* @__PURE__ */ React29.createElement(ToastViewport, null));
|
|
2047
2178
|
};
|
|
2048
2179
|
ToastProvider.displayName = "ToastProvider";
|
|
2180
|
+
var POSITION_CLASSES = {
|
|
2181
|
+
"top-right": "top-4 right-4",
|
|
2182
|
+
"top-left": "top-4 left-4",
|
|
2183
|
+
"bottom-right": "bottom-4 right-4",
|
|
2184
|
+
"bottom-left": "bottom-4 left-4",
|
|
2185
|
+
"top-center": "top-4 left-1/2 -translate-x-1/2",
|
|
2186
|
+
"bottom-center": "bottom-4 left-1/2 -translate-x-1/2"
|
|
2187
|
+
};
|
|
2049
2188
|
var ToastViewport = () => {
|
|
2050
2189
|
const context = useContext2(ToastContext);
|
|
2051
2190
|
if (!context) {
|
|
2052
2191
|
return null;
|
|
2053
2192
|
}
|
|
2054
2193
|
const { toasts, position } = context;
|
|
2055
|
-
const positionClasses = {
|
|
2056
|
-
"top-right": "top-4 right-4",
|
|
2057
|
-
"top-left": "top-4 left-4",
|
|
2058
|
-
"bottom-right": "bottom-4 right-4",
|
|
2059
|
-
"bottom-left": "bottom-4 left-4",
|
|
2060
|
-
"top-center": "top-4 left-1/2 -translate-x-1/2",
|
|
2061
|
-
"bottom-center": "bottom-4 left-1/2 -translate-x-1/2"
|
|
2062
|
-
};
|
|
2063
2194
|
return createPortal(
|
|
2064
2195
|
/* @__PURE__ */ React29.createElement(
|
|
2065
2196
|
"div",
|
|
2066
2197
|
{
|
|
2067
2198
|
className: cx(
|
|
2068
2199
|
"fixed z-50 flex flex-col gap-2 pointer-events-none",
|
|
2069
|
-
|
|
2200
|
+
POSITION_CLASSES[position]
|
|
2070
2201
|
)
|
|
2071
2202
|
},
|
|
2072
2203
|
toasts.map((toast) => /* @__PURE__ */ React29.createElement(Toast, { key: toast.id, ...toast }))
|
|
@@ -2097,7 +2228,7 @@ var Toast = ({
|
|
|
2097
2228
|
action
|
|
2098
2229
|
}) => {
|
|
2099
2230
|
const context = useContext2(ToastContext);
|
|
2100
|
-
|
|
2231
|
+
useEffect2(() => {
|
|
2101
2232
|
if (duration && duration > 0) {
|
|
2102
2233
|
const timer = setTimeout(() => {
|
|
2103
2234
|
context?.removeToast(id);
|
|
@@ -2129,41 +2260,17 @@ var Toast = ({
|
|
|
2129
2260
|
Toast.displayName = "Toast";
|
|
2130
2261
|
|
|
2131
2262
|
// src/components/Modal.tsx
|
|
2132
|
-
import React30, { useEffect as
|
|
2263
|
+
import React30, { useEffect as useEffect3, useState as useState5 } from "react";
|
|
2133
2264
|
import { createPortal as createPortal2 } from "react-dom";
|
|
2134
2265
|
import { X as X3 } from "lucide-react";
|
|
2135
2266
|
var Modal = ({ isOpen, onClose, title, children, className }) => {
|
|
2136
|
-
const [mounted, setMounted] =
|
|
2137
|
-
|
|
2267
|
+
const [mounted, setMounted] = useState5(false);
|
|
2268
|
+
useEffect3(() => {
|
|
2138
2269
|
setMounted(true);
|
|
2139
2270
|
}, []);
|
|
2140
|
-
|
|
2141
|
-
|
|
2142
|
-
|
|
2143
|
-
document.body.style.overflow = "hidden";
|
|
2144
|
-
document.body.style.paddingRight = `${scrollbarWidth}px`;
|
|
2145
|
-
} else {
|
|
2146
|
-
document.body.style.overflow = "unset";
|
|
2147
|
-
document.body.style.paddingRight = "0px";
|
|
2148
|
-
}
|
|
2149
|
-
return () => {
|
|
2150
|
-
document.body.style.overflow = "unset";
|
|
2151
|
-
document.body.style.paddingRight = "0px";
|
|
2152
|
-
};
|
|
2153
|
-
}, [isOpen]);
|
|
2154
|
-
useEffect2(() => {
|
|
2155
|
-
const handleEsc = (e) => {
|
|
2156
|
-
if (e.key === "Escape") {
|
|
2157
|
-
onClose();
|
|
2158
|
-
}
|
|
2159
|
-
};
|
|
2160
|
-
window.addEventListener("keydown", handleEsc);
|
|
2161
|
-
return () => window.removeEventListener("keydown", handleEsc);
|
|
2162
|
-
}, [onClose]);
|
|
2163
|
-
if (!mounted) {
|
|
2164
|
-
return null;
|
|
2165
|
-
}
|
|
2166
|
-
if (!isOpen) {
|
|
2271
|
+
useScrollLock(isOpen);
|
|
2272
|
+
useEscapeKey(onClose, isOpen);
|
|
2273
|
+
if (!mounted || !isOpen) {
|
|
2167
2274
|
return null;
|
|
2168
2275
|
}
|
|
2169
2276
|
const content = /* @__PURE__ */ React30.createElement(
|
|
@@ -2202,7 +2309,7 @@ var Modal = ({ isOpen, onClose, title, children, className }) => {
|
|
|
2202
2309
|
Modal.displayName = "Modal";
|
|
2203
2310
|
|
|
2204
2311
|
// src/components/Drawer.tsx
|
|
2205
|
-
import React31, { useEffect as
|
|
2312
|
+
import React31, { useEffect as useEffect4, useState as useState6 } from "react";
|
|
2206
2313
|
import { createPortal as createPortal3 } from "react-dom";
|
|
2207
2314
|
import { X as X4 } from "lucide-react";
|
|
2208
2315
|
var SIZE_MAP2 = {
|
|
@@ -2237,7 +2344,7 @@ var SIZE_MAP2 = {
|
|
|
2237
2344
|
bottom: "h-full"
|
|
2238
2345
|
}
|
|
2239
2346
|
};
|
|
2240
|
-
var
|
|
2347
|
+
var POSITION_CLASSES2 = {
|
|
2241
2348
|
left: "left-0 top-0 h-full",
|
|
2242
2349
|
right: "right-0 top-0 h-full",
|
|
2243
2350
|
top: "top-0 left-0 w-full",
|
|
@@ -2258,33 +2365,12 @@ var Drawer = ({
|
|
|
2258
2365
|
children,
|
|
2259
2366
|
className
|
|
2260
2367
|
}) => {
|
|
2261
|
-
const [mounted, setMounted] =
|
|
2262
|
-
|
|
2368
|
+
const [mounted, setMounted] = useState6(false);
|
|
2369
|
+
useEffect4(() => {
|
|
2263
2370
|
setMounted(true);
|
|
2264
2371
|
}, []);
|
|
2265
|
-
|
|
2266
|
-
|
|
2267
|
-
const scrollbarWidth = window.innerWidth - document.documentElement.clientWidth;
|
|
2268
|
-
document.body.style.overflow = "hidden";
|
|
2269
|
-
document.body.style.paddingRight = `${scrollbarWidth}px`;
|
|
2270
|
-
} else {
|
|
2271
|
-
document.body.style.overflow = "unset";
|
|
2272
|
-
document.body.style.paddingRight = "0px";
|
|
2273
|
-
}
|
|
2274
|
-
return () => {
|
|
2275
|
-
document.body.style.overflow = "unset";
|
|
2276
|
-
document.body.style.paddingRight = "0px";
|
|
2277
|
-
};
|
|
2278
|
-
}, [isOpen]);
|
|
2279
|
-
useEffect3(() => {
|
|
2280
|
-
const handleEsc = (e) => {
|
|
2281
|
-
if (e.key === "Escape") {
|
|
2282
|
-
onClose();
|
|
2283
|
-
}
|
|
2284
|
-
};
|
|
2285
|
-
window.addEventListener("keydown", handleEsc);
|
|
2286
|
-
return () => window.removeEventListener("keydown", handleEsc);
|
|
2287
|
-
}, [onClose]);
|
|
2372
|
+
useScrollLock(isOpen);
|
|
2373
|
+
useEscapeKey(onClose, isOpen);
|
|
2288
2374
|
if (!mounted) {
|
|
2289
2375
|
return null;
|
|
2290
2376
|
}
|
|
@@ -2315,7 +2401,7 @@ var Drawer = ({
|
|
|
2315
2401
|
className: cx(
|
|
2316
2402
|
"fixed bg-charcoal border-ash shadow-2xl flex flex-col",
|
|
2317
2403
|
"transition-transform duration-300 ease-out",
|
|
2318
|
-
|
|
2404
|
+
POSITION_CLASSES2[position],
|
|
2319
2405
|
SIZE_MAP2[size][position],
|
|
2320
2406
|
position === "left" && "border-r",
|
|
2321
2407
|
position === "right" && "border-l",
|
|
@@ -2342,8 +2428,8 @@ var Drawer = ({
|
|
|
2342
2428
|
Drawer.displayName = "Drawer";
|
|
2343
2429
|
|
|
2344
2430
|
// src/components/Popover.tsx
|
|
2345
|
-
import React32, { useCallback as
|
|
2346
|
-
var
|
|
2431
|
+
import React32, { useCallback as useCallback7, useId as useId3, useRef as useRef4, useState as useState7 } from "react";
|
|
2432
|
+
var POSITION_CLASSES3 = {
|
|
2347
2433
|
top: {
|
|
2348
2434
|
start: "bottom-full left-0 mb-2",
|
|
2349
2435
|
center: "bottom-full left-1/2 -translate-x-1/2 mb-2",
|
|
@@ -2374,12 +2460,12 @@ var Popover = ({
|
|
|
2374
2460
|
onOpenChange,
|
|
2375
2461
|
closeOnClickOutside = true
|
|
2376
2462
|
}) => {
|
|
2377
|
-
const [internalOpen, setInternalOpen] =
|
|
2463
|
+
const [internalOpen, setInternalOpen] = useState7(false);
|
|
2378
2464
|
const isControlled = controlledOpen !== void 0;
|
|
2379
2465
|
const isOpen = isControlled ? controlledOpen : internalOpen;
|
|
2380
|
-
const containerRef =
|
|
2381
|
-
const baseId =
|
|
2382
|
-
const setIsOpen =
|
|
2466
|
+
const containerRef = useRef4(null);
|
|
2467
|
+
const baseId = useId3();
|
|
2468
|
+
const setIsOpen = useCallback7(
|
|
2383
2469
|
(newOpen) => {
|
|
2384
2470
|
if (!isControlled) {
|
|
2385
2471
|
setInternalOpen(newOpen);
|
|
@@ -2388,30 +2474,9 @@ var Popover = ({
|
|
|
2388
2474
|
},
|
|
2389
2475
|
[isControlled, onOpenChange]
|
|
2390
2476
|
);
|
|
2391
|
-
|
|
2392
|
-
|
|
2393
|
-
|
|
2394
|
-
}
|
|
2395
|
-
const handleClickOutside = (e) => {
|
|
2396
|
-
if (containerRef.current && !containerRef.current.contains(e.target)) {
|
|
2397
|
-
setIsOpen(false);
|
|
2398
|
-
}
|
|
2399
|
-
};
|
|
2400
|
-
document.addEventListener("mousedown", handleClickOutside);
|
|
2401
|
-
return () => document.removeEventListener("mousedown", handleClickOutside);
|
|
2402
|
-
}, [isOpen, closeOnClickOutside, setIsOpen]);
|
|
2403
|
-
useEffect4(() => {
|
|
2404
|
-
if (!isOpen) {
|
|
2405
|
-
return;
|
|
2406
|
-
}
|
|
2407
|
-
const handleEscape = (e) => {
|
|
2408
|
-
if (e.key === "Escape") {
|
|
2409
|
-
setIsOpen(false);
|
|
2410
|
-
}
|
|
2411
|
-
};
|
|
2412
|
-
document.addEventListener("keydown", handleEscape);
|
|
2413
|
-
return () => document.removeEventListener("keydown", handleEscape);
|
|
2414
|
-
}, [isOpen, setIsOpen]);
|
|
2477
|
+
const close = useCallback7(() => setIsOpen(false), [setIsOpen]);
|
|
2478
|
+
useClickOutside(containerRef, close, isOpen && closeOnClickOutside);
|
|
2479
|
+
useEscapeKey(close, isOpen);
|
|
2415
2480
|
const handleTriggerClick = () => {
|
|
2416
2481
|
setIsOpen(!isOpen);
|
|
2417
2482
|
};
|
|
@@ -2432,7 +2497,7 @@ var Popover = ({
|
|
|
2432
2497
|
"absolute z-50 min-w-48 p-4",
|
|
2433
2498
|
"bg-charcoal border border-ash shadow-lg",
|
|
2434
2499
|
"animate-fade-in",
|
|
2435
|
-
|
|
2500
|
+
POSITION_CLASSES3[position][align]
|
|
2436
2501
|
)
|
|
2437
2502
|
},
|
|
2438
2503
|
children
|
|
@@ -2441,7 +2506,7 @@ var Popover = ({
|
|
|
2441
2506
|
Popover.displayName = "Popover";
|
|
2442
2507
|
|
|
2443
2508
|
// src/components/Dialog.tsx
|
|
2444
|
-
import React33, { useCallback as
|
|
2509
|
+
import React33, { useCallback as useCallback8 } from "react";
|
|
2445
2510
|
var ConfirmDialog = ({
|
|
2446
2511
|
title = "Confirm",
|
|
2447
2512
|
description,
|
|
@@ -2454,11 +2519,11 @@ var ConfirmDialog = ({
|
|
|
2454
2519
|
isLoading = false,
|
|
2455
2520
|
...props
|
|
2456
2521
|
}) => {
|
|
2457
|
-
const handleCancel =
|
|
2522
|
+
const handleCancel = useCallback8(() => {
|
|
2458
2523
|
onCancel?.();
|
|
2459
2524
|
onClose();
|
|
2460
2525
|
}, [onCancel, onClose]);
|
|
2461
|
-
const handleConfirm =
|
|
2526
|
+
const handleConfirm = useCallback8(async () => {
|
|
2462
2527
|
await onConfirm();
|
|
2463
2528
|
onClose();
|
|
2464
2529
|
}, [onConfirm, onClose]);
|
|
@@ -2502,11 +2567,11 @@ var PromptDialog = ({
|
|
|
2502
2567
|
...props
|
|
2503
2568
|
}) => {
|
|
2504
2569
|
const [value, setValue] = React33.useState(defaultValue);
|
|
2505
|
-
const handleCancel =
|
|
2570
|
+
const handleCancel = useCallback8(() => {
|
|
2506
2571
|
onCancel?.();
|
|
2507
2572
|
onClose();
|
|
2508
2573
|
}, [onCancel, onClose]);
|
|
2509
|
-
const handleSubmit =
|
|
2574
|
+
const handleSubmit = useCallback8(
|
|
2510
2575
|
async (e) => {
|
|
2511
2576
|
e.preventDefault();
|
|
2512
2577
|
await onSubmit(value);
|
|
@@ -2543,7 +2608,7 @@ var PromptDialog = ({
|
|
|
2543
2608
|
PromptDialog.displayName = "PromptDialog";
|
|
2544
2609
|
|
|
2545
2610
|
// src/components/Tabs.tsx
|
|
2546
|
-
import React34, { createContext as createContext3, useCallback as
|
|
2611
|
+
import React34, { createContext as createContext3, useCallback as useCallback9, useContext as useContext3, useId as useId4, useState as useState8 } from "react";
|
|
2547
2612
|
var TabsContext = createContext3(null);
|
|
2548
2613
|
function useTabsContext() {
|
|
2549
2614
|
const context = useContext3(TabsContext);
|
|
@@ -2554,11 +2619,11 @@ function useTabsContext() {
|
|
|
2554
2619
|
}
|
|
2555
2620
|
var Tabs = React34.forwardRef(
|
|
2556
2621
|
({ defaultValue, value, onValueChange, children, className, ...props }, ref) => {
|
|
2557
|
-
const [internalValue, setInternalValue] =
|
|
2622
|
+
const [internalValue, setInternalValue] = useState8(defaultValue ?? "");
|
|
2558
2623
|
const isControlled = value !== void 0;
|
|
2559
2624
|
const activeTab = isControlled ? value : internalValue;
|
|
2560
|
-
const baseId =
|
|
2561
|
-
const setActiveTab =
|
|
2625
|
+
const baseId = useId4();
|
|
2626
|
+
const setActiveTab = useCallback9(
|
|
2562
2627
|
(id) => {
|
|
2563
2628
|
if (!isControlled) {
|
|
2564
2629
|
setInternalValue(id);
|
|
@@ -2654,7 +2719,7 @@ var TabPanel = React34.forwardRef(
|
|
|
2654
2719
|
TabPanel.displayName = "TabPanel";
|
|
2655
2720
|
|
|
2656
2721
|
// src/components/Accordion.tsx
|
|
2657
|
-
import React35, { createContext as createContext4, useCallback as
|
|
2722
|
+
import React35, { createContext as createContext4, useCallback as useCallback10, useContext as useContext4, useId as useId5, useState as useState9 } from "react";
|
|
2658
2723
|
import { ChevronDown } from "lucide-react";
|
|
2659
2724
|
var AccordionContext = createContext4(null);
|
|
2660
2725
|
function useAccordionContext() {
|
|
@@ -2666,7 +2731,7 @@ function useAccordionContext() {
|
|
|
2666
2731
|
}
|
|
2667
2732
|
var Accordion = React35.forwardRef(
|
|
2668
2733
|
({ type = "single", defaultValue, value, onValueChange, children, className, ...props }, ref) => {
|
|
2669
|
-
const [internalValue, setInternalValue] =
|
|
2734
|
+
const [internalValue, setInternalValue] = useState9(() => {
|
|
2670
2735
|
if (defaultValue) {
|
|
2671
2736
|
return new Set(Array.isArray(defaultValue) ? defaultValue : [defaultValue]);
|
|
2672
2737
|
}
|
|
@@ -2674,7 +2739,7 @@ var Accordion = React35.forwardRef(
|
|
|
2674
2739
|
});
|
|
2675
2740
|
const isControlled = value !== void 0;
|
|
2676
2741
|
const expandedItems = isControlled ? new Set(Array.isArray(value) ? value : [value]) : internalValue;
|
|
2677
|
-
const toggleItem =
|
|
2742
|
+
const toggleItem = useCallback10(
|
|
2678
2743
|
(id) => {
|
|
2679
2744
|
const newSet = new Set(expandedItems);
|
|
2680
2745
|
if (newSet.has(id)) {
|
|
@@ -2725,7 +2790,7 @@ var AccordionTrigger = React35.forwardRef(
|
|
|
2725
2790
|
({ children, className, ...props }, ref) => {
|
|
2726
2791
|
const { expandedItems, toggleItem } = useAccordionContext();
|
|
2727
2792
|
const itemContext = useContext4(AccordionItemContext);
|
|
2728
|
-
const baseId =
|
|
2793
|
+
const baseId = useId5();
|
|
2729
2794
|
if (!itemContext) {
|
|
2730
2795
|
throw new Error("AccordionTrigger must be used within an AccordionItem");
|
|
2731
2796
|
}
|
|
@@ -2770,7 +2835,7 @@ var AccordionContent = React35.forwardRef(
|
|
|
2770
2835
|
({ children, className, ...props }, ref) => {
|
|
2771
2836
|
const { expandedItems } = useAccordionContext();
|
|
2772
2837
|
const itemContext = useContext4(AccordionItemContext);
|
|
2773
|
-
const baseId =
|
|
2838
|
+
const baseId = useId5();
|
|
2774
2839
|
if (!itemContext) {
|
|
2775
2840
|
throw new Error("AccordionContent must be used within an AccordionItem");
|
|
2776
2841
|
}
|
|
@@ -2800,12 +2865,12 @@ AccordionContent.displayName = "AccordionContent";
|
|
|
2800
2865
|
// src/components/Menu.tsx
|
|
2801
2866
|
import React36, {
|
|
2802
2867
|
createContext as createContext5,
|
|
2803
|
-
useCallback as
|
|
2868
|
+
useCallback as useCallback11,
|
|
2804
2869
|
useContext as useContext5,
|
|
2805
2870
|
useEffect as useEffect5,
|
|
2806
|
-
useId as
|
|
2807
|
-
useRef as
|
|
2808
|
-
useState as
|
|
2871
|
+
useId as useId6,
|
|
2872
|
+
useRef as useRef5,
|
|
2873
|
+
useState as useState10
|
|
2809
2874
|
} from "react";
|
|
2810
2875
|
var MenuContext = createContext5(null);
|
|
2811
2876
|
function useMenuContext() {
|
|
@@ -2816,11 +2881,11 @@ function useMenuContext() {
|
|
|
2816
2881
|
return context;
|
|
2817
2882
|
}
|
|
2818
2883
|
var Menu = ({ children, open, onOpenChange }) => {
|
|
2819
|
-
const [internalOpen, setInternalOpen] =
|
|
2884
|
+
const [internalOpen, setInternalOpen] = useState10(false);
|
|
2820
2885
|
const isControlled = open !== void 0;
|
|
2821
2886
|
const isOpen = isControlled ? open : internalOpen;
|
|
2822
|
-
const baseId =
|
|
2823
|
-
const setIsOpen =
|
|
2887
|
+
const baseId = useId6();
|
|
2888
|
+
const setIsOpen = useCallback11(
|
|
2824
2889
|
(newOpen) => {
|
|
2825
2890
|
if (!isControlled) {
|
|
2826
2891
|
setInternalOpen(newOpen);
|
|
@@ -2872,55 +2937,42 @@ var MenuTrigger = React36.forwardRef(
|
|
|
2872
2937
|
}
|
|
2873
2938
|
);
|
|
2874
2939
|
MenuTrigger.displayName = "MenuTrigger";
|
|
2940
|
+
var MENU_ALIGN_CLASSES = {
|
|
2941
|
+
start: "left-0",
|
|
2942
|
+
center: "left-1/2 -translate-x-1/2",
|
|
2943
|
+
end: "right-0"
|
|
2944
|
+
};
|
|
2945
|
+
var MENU_SIDE_CLASSES = {
|
|
2946
|
+
top: "bottom-full mb-1",
|
|
2947
|
+
bottom: "top-full mt-1"
|
|
2948
|
+
};
|
|
2875
2949
|
var MenuContent = React36.forwardRef(
|
|
2876
2950
|
({ children, className, align = "start", side = "bottom", ...props }, ref) => {
|
|
2877
2951
|
const { isOpen, setIsOpen, triggerId, menuId } = useMenuContext();
|
|
2878
|
-
const menuRef =
|
|
2952
|
+
const menuRef = useRef5(null);
|
|
2953
|
+
const close = useCallback11(() => setIsOpen(false), [setIsOpen]);
|
|
2954
|
+
useEscapeKey(close, isOpen);
|
|
2879
2955
|
useEffect5(() => {
|
|
2880
2956
|
if (!isOpen) {
|
|
2881
2957
|
return;
|
|
2882
2958
|
}
|
|
2883
2959
|
const handleClickOutside = (e) => {
|
|
2960
|
+
const target = e.target;
|
|
2884
2961
|
const trigger = document.getElementById(triggerId);
|
|
2885
|
-
if (menuRef.current && !menuRef.current.contains(
|
|
2886
|
-
setIsOpen(false);
|
|
2887
|
-
}
|
|
2888
|
-
};
|
|
2889
|
-
const handleEscape = (e) => {
|
|
2890
|
-
if (e.key === "Escape") {
|
|
2962
|
+
if (menuRef.current && !menuRef.current.contains(target) && !trigger?.contains(target)) {
|
|
2891
2963
|
setIsOpen(false);
|
|
2892
2964
|
}
|
|
2893
2965
|
};
|
|
2894
2966
|
document.addEventListener("mousedown", handleClickOutside);
|
|
2895
|
-
document.
|
|
2896
|
-
return () => {
|
|
2897
|
-
document.removeEventListener("mousedown", handleClickOutside);
|
|
2898
|
-
document.removeEventListener("keydown", handleEscape);
|
|
2899
|
-
};
|
|
2967
|
+
return () => document.removeEventListener("mousedown", handleClickOutside);
|
|
2900
2968
|
}, [isOpen, setIsOpen, triggerId]);
|
|
2901
2969
|
if (!isOpen) {
|
|
2902
2970
|
return null;
|
|
2903
2971
|
}
|
|
2904
|
-
const alignmentClasses = {
|
|
2905
|
-
start: "left-0",
|
|
2906
|
-
center: "left-1/2 -translate-x-1/2",
|
|
2907
|
-
end: "right-0"
|
|
2908
|
-
};
|
|
2909
|
-
const sideClasses = {
|
|
2910
|
-
top: "bottom-full mb-1",
|
|
2911
|
-
bottom: "top-full mt-1"
|
|
2912
|
-
};
|
|
2913
2972
|
return /* @__PURE__ */ React36.createElement(
|
|
2914
2973
|
"div",
|
|
2915
2974
|
{
|
|
2916
|
-
ref: (
|
|
2917
|
-
menuRef.current = node;
|
|
2918
|
-
if (typeof ref === "function") {
|
|
2919
|
-
ref(node);
|
|
2920
|
-
} else if (ref) {
|
|
2921
|
-
ref.current = node;
|
|
2922
|
-
}
|
|
2923
|
-
},
|
|
2975
|
+
ref: composeRefs(menuRef, ref),
|
|
2924
2976
|
id: menuId,
|
|
2925
2977
|
role: "menu",
|
|
2926
2978
|
"aria-labelledby": triggerId,
|
|
@@ -2928,8 +2980,8 @@ var MenuContent = React36.forwardRef(
|
|
|
2928
2980
|
"absolute z-50 min-w-40 py-1",
|
|
2929
2981
|
"bg-charcoal border border-ash shadow-lg",
|
|
2930
2982
|
"animate-fade-in",
|
|
2931
|
-
|
|
2932
|
-
|
|
2983
|
+
MENU_ALIGN_CLASSES[align],
|
|
2984
|
+
MENU_SIDE_CLASSES[side],
|
|
2933
2985
|
className
|
|
2934
2986
|
),
|
|
2935
2987
|
...props
|
|
@@ -3653,12 +3705,19 @@ function SquareLoaderIcon({ className, ...props }) {
|
|
|
3653
3705
|
}
|
|
3654
3706
|
|
|
3655
3707
|
// src/components/Message.tsx
|
|
3656
|
-
import React55, { useEffect as useEffect6, useRef as
|
|
3708
|
+
import React55, { useCallback as useCallback12, useEffect as useEffect6, useRef as useRef6, useState as useState11 } from "react";
|
|
3709
|
+
import { Check as Check3, ChevronLeft as ChevronLeft2, ChevronRight as ChevronRight3, Copy, GitBranch, Pencil, RotateCcw, Send, X as X5 } from "lucide-react";
|
|
3657
3710
|
|
|
3658
3711
|
// src/components/MarkdownContent.tsx
|
|
3659
3712
|
import React54, { useMemo } from "react";
|
|
3660
3713
|
import DOMPurify from "dompurify";
|
|
3661
3714
|
import { marked } from "marked";
|
|
3715
|
+
DOMPurify.addHook("afterSanitizeAttributes", (node) => {
|
|
3716
|
+
if (node.tagName === "A") {
|
|
3717
|
+
node.setAttribute("target", "_blank");
|
|
3718
|
+
node.setAttribute("rel", "noopener noreferrer");
|
|
3719
|
+
}
|
|
3720
|
+
});
|
|
3662
3721
|
var DEFAULT_SANITIZE_CONFIG = {
|
|
3663
3722
|
ALLOWED_TAGS: [
|
|
3664
3723
|
"h1",
|
|
@@ -3726,16 +3785,6 @@ var DEFAULT_SANITIZE_CONFIG = {
|
|
|
3726
3785
|
ADD_ATTR: ["target", "rel"],
|
|
3727
3786
|
ALLOWED_URI_REGEXP: /^(?:(?:https?|mailto|tel):|[^a-z]|[a-z+.-]+(?:[^a-z+.\-:]|$))/i
|
|
3728
3787
|
};
|
|
3729
|
-
function useDOMPurifySetup() {
|
|
3730
|
-
useMemo(() => {
|
|
3731
|
-
DOMPurify.addHook("afterSanitizeAttributes", (node) => {
|
|
3732
|
-
if (node.tagName === "A") {
|
|
3733
|
-
node.setAttribute("target", "_blank");
|
|
3734
|
-
node.setAttribute("rel", "noopener noreferrer");
|
|
3735
|
-
}
|
|
3736
|
-
});
|
|
3737
|
-
}, []);
|
|
3738
|
-
}
|
|
3739
3788
|
var CURSOR_BASE_CLASSES = "inline-block bg-current animate-cursor-blink w-0.5 h-cursor translate-y-cursor-offset";
|
|
3740
3789
|
function injectStreamingCursor(html, cursorClassName) {
|
|
3741
3790
|
if (!html.trim()) {
|
|
@@ -3765,7 +3814,6 @@ function injectStreamingCursor(html, cursorClassName) {
|
|
|
3765
3814
|
}
|
|
3766
3815
|
var MarkdownContent = React54.forwardRef(
|
|
3767
3816
|
({ className, content, isMarkdown = true, sanitizeConfig, isStreaming, cursorClassName, ...rest }, ref) => {
|
|
3768
|
-
useDOMPurifySetup();
|
|
3769
3817
|
const sanitizedHtml = useMemo(() => {
|
|
3770
3818
|
if (!content && !isStreaming) {
|
|
3771
3819
|
return "";
|
|
@@ -3787,7 +3835,7 @@ var MarkdownContent = React54.forwardRef(
|
|
|
3787
3835
|
return injectStreamingCursor(sanitized, cursorClassName);
|
|
3788
3836
|
}
|
|
3789
3837
|
return sanitized;
|
|
3790
|
-
}, [content, sanitizeConfig, isStreaming, cursorClassName]);
|
|
3838
|
+
}, [content, isMarkdown, sanitizeConfig, isStreaming, cursorClassName]);
|
|
3791
3839
|
return /* @__PURE__ */ React54.createElement(
|
|
3792
3840
|
"div",
|
|
3793
3841
|
{
|
|
@@ -3802,162 +3850,32 @@ var MarkdownContent = React54.forwardRef(
|
|
|
3802
3850
|
MarkdownContent.displayName = "MarkdownContent";
|
|
3803
3851
|
|
|
3804
3852
|
// src/components/Message.tsx
|
|
3805
|
-
var
|
|
3853
|
+
var VARIANT_STYLES3 = {
|
|
3806
3854
|
user: "bg-gold text-obsidian ml-auto",
|
|
3807
3855
|
assistant: "bg-charcoal border border-ash text-white mr-auto"
|
|
3808
3856
|
};
|
|
3809
|
-
var
|
|
3810
|
-
"
|
|
3811
|
-
|
|
3812
|
-
|
|
3813
|
-
onClick,
|
|
3814
|
-
disabled,
|
|
3815
|
-
className: cx(
|
|
3816
|
-
"p-1.5 text-silver/60 hover:text-silver transition-colors duration-150",
|
|
3817
|
-
"hover:bg-white/5",
|
|
3818
|
-
"disabled:opacity-50 disabled:cursor-not-allowed disabled:hover:bg-transparent",
|
|
3819
|
-
className
|
|
3820
|
-
),
|
|
3821
|
-
"aria-label": label
|
|
3822
|
-
},
|
|
3823
|
-
children
|
|
3824
|
-
);
|
|
3825
|
-
var CopyIcon = () => /* @__PURE__ */ React55.createElement(
|
|
3826
|
-
"svg",
|
|
3827
|
-
{
|
|
3828
|
-
xmlns: "http://www.w3.org/2000/svg",
|
|
3829
|
-
viewBox: "0 0 24 24",
|
|
3830
|
-
fill: "none",
|
|
3831
|
-
stroke: "currentColor",
|
|
3832
|
-
strokeWidth: "2",
|
|
3833
|
-
strokeLinecap: "round",
|
|
3834
|
-
strokeLinejoin: "round",
|
|
3835
|
-
className: "w-3.5 h-3.5"
|
|
3836
|
-
},
|
|
3837
|
-
/* @__PURE__ */ React55.createElement("rect", { width: "14", height: "14", x: "8", y: "8", rx: "2", ry: "2" }),
|
|
3838
|
-
/* @__PURE__ */ React55.createElement("path", { d: "M4 16c-1.1 0-2-.9-2-2V4c0-1.1.9-2 2-2h10c1.1 0 2 .9 2 2" })
|
|
3839
|
-
);
|
|
3840
|
-
var CheckIcon = () => /* @__PURE__ */ React55.createElement(
|
|
3841
|
-
"svg",
|
|
3842
|
-
{
|
|
3843
|
-
xmlns: "http://www.w3.org/2000/svg",
|
|
3844
|
-
viewBox: "0 0 24 24",
|
|
3845
|
-
fill: "none",
|
|
3846
|
-
stroke: "currentColor",
|
|
3847
|
-
strokeWidth: "2",
|
|
3848
|
-
strokeLinecap: "round",
|
|
3849
|
-
strokeLinejoin: "round",
|
|
3850
|
-
className: "w-3.5 h-3.5 text-success"
|
|
3851
|
-
},
|
|
3852
|
-
/* @__PURE__ */ React55.createElement("polyline", { points: "20 6 9 17 4 12" })
|
|
3853
|
-
);
|
|
3854
|
-
var PencilIcon = () => /* @__PURE__ */ React55.createElement(
|
|
3855
|
-
"svg",
|
|
3856
|
-
{
|
|
3857
|
-
xmlns: "http://www.w3.org/2000/svg",
|
|
3858
|
-
viewBox: "0 0 24 24",
|
|
3859
|
-
fill: "none",
|
|
3860
|
-
stroke: "currentColor",
|
|
3861
|
-
strokeWidth: "2",
|
|
3862
|
-
strokeLinecap: "round",
|
|
3863
|
-
strokeLinejoin: "round",
|
|
3864
|
-
className: "w-3.5 h-3.5"
|
|
3865
|
-
},
|
|
3866
|
-
/* @__PURE__ */ React55.createElement("path", { d: "M17 3a2.85 2.83 0 1 1 4 4L7.5 20.5 2 22l1.5-5.5Z" }),
|
|
3867
|
-
/* @__PURE__ */ React55.createElement("path", { d: "m15 5 4 4" })
|
|
3857
|
+
var ACTION_BUTTON_CLASSES = cx(
|
|
3858
|
+
"p-1.5 text-silver/60 hover:text-silver transition-colors duration-150",
|
|
3859
|
+
"hover:bg-white/5",
|
|
3860
|
+
"disabled:opacity-50 disabled:cursor-not-allowed disabled:hover:bg-transparent"
|
|
3868
3861
|
);
|
|
3869
|
-
var
|
|
3870
|
-
"
|
|
3871
|
-
|
|
3872
|
-
xmlns: "http://www.w3.org/2000/svg",
|
|
3873
|
-
viewBox: "0 0 24 24",
|
|
3874
|
-
fill: "none",
|
|
3875
|
-
stroke: "currentColor",
|
|
3876
|
-
strokeWidth: "2",
|
|
3877
|
-
strokeLinecap: "round",
|
|
3878
|
-
strokeLinejoin: "round",
|
|
3879
|
-
className: "w-3.5 h-3.5"
|
|
3880
|
-
},
|
|
3881
|
-
/* @__PURE__ */ React55.createElement("path", { d: "M3 12a9 9 0 0 1 9-9 9.75 9.75 0 0 1 6.74 2.74L21 8" }),
|
|
3882
|
-
/* @__PURE__ */ React55.createElement("path", { d: "M21 3v5h-5" }),
|
|
3883
|
-
/* @__PURE__ */ React55.createElement("path", { d: "M21 12a9 9 0 0 1-9 9 9.75 9.75 0 0 1-6.74-2.74L3 16" }),
|
|
3884
|
-
/* @__PURE__ */ React55.createElement("path", { d: "M8 16H3v5" })
|
|
3885
|
-
);
|
|
3886
|
-
var ChevronLeftIcon2 = () => /* @__PURE__ */ React55.createElement(
|
|
3887
|
-
"svg",
|
|
3888
|
-
{
|
|
3889
|
-
xmlns: "http://www.w3.org/2000/svg",
|
|
3890
|
-
viewBox: "0 0 24 24",
|
|
3891
|
-
fill: "none",
|
|
3892
|
-
stroke: "currentColor",
|
|
3893
|
-
strokeWidth: "2",
|
|
3894
|
-
strokeLinecap: "round",
|
|
3895
|
-
strokeLinejoin: "round",
|
|
3896
|
-
className: "w-3 h-3"
|
|
3897
|
-
},
|
|
3898
|
-
/* @__PURE__ */ React55.createElement("path", { d: "m15 18-6-6 6-6" })
|
|
3899
|
-
);
|
|
3900
|
-
var ChevronRightIcon2 = () => /* @__PURE__ */ React55.createElement(
|
|
3901
|
-
"svg",
|
|
3902
|
-
{
|
|
3903
|
-
xmlns: "http://www.w3.org/2000/svg",
|
|
3904
|
-
viewBox: "0 0 24 24",
|
|
3905
|
-
fill: "none",
|
|
3906
|
-
stroke: "currentColor",
|
|
3907
|
-
strokeWidth: "2",
|
|
3908
|
-
strokeLinecap: "round",
|
|
3909
|
-
strokeLinejoin: "round",
|
|
3910
|
-
className: "w-3 h-3"
|
|
3911
|
-
},
|
|
3912
|
-
/* @__PURE__ */ React55.createElement("path", { d: "m9 18 6-6-6-6" })
|
|
3913
|
-
);
|
|
3914
|
-
var GitBranchIcon = () => /* @__PURE__ */ React55.createElement(
|
|
3915
|
-
"svg",
|
|
3916
|
-
{
|
|
3917
|
-
xmlns: "http://www.w3.org/2000/svg",
|
|
3918
|
-
viewBox: "0 0 24 24",
|
|
3919
|
-
fill: "none",
|
|
3920
|
-
stroke: "currentColor",
|
|
3921
|
-
strokeWidth: "2",
|
|
3922
|
-
strokeLinecap: "round",
|
|
3923
|
-
strokeLinejoin: "round",
|
|
3924
|
-
className: "w-3 h-3 mr-0.5 text-silver/50"
|
|
3925
|
-
},
|
|
3926
|
-
/* @__PURE__ */ React55.createElement("line", { x1: "6", x2: "6", y1: "3", y2: "15" }),
|
|
3927
|
-
/* @__PURE__ */ React55.createElement("circle", { cx: "18", cy: "6", r: "3" }),
|
|
3928
|
-
/* @__PURE__ */ React55.createElement("circle", { cx: "6", cy: "18", r: "3" }),
|
|
3929
|
-
/* @__PURE__ */ React55.createElement("path", { d: "M18 9a9 9 0 0 1-9 9" })
|
|
3930
|
-
);
|
|
3931
|
-
var XIcon = () => /* @__PURE__ */ React55.createElement(
|
|
3932
|
-
"svg",
|
|
3933
|
-
{
|
|
3934
|
-
xmlns: "http://www.w3.org/2000/svg",
|
|
3935
|
-
viewBox: "0 0 24 24",
|
|
3936
|
-
fill: "none",
|
|
3937
|
-
stroke: "currentColor",
|
|
3938
|
-
strokeWidth: "2",
|
|
3939
|
-
strokeLinecap: "round",
|
|
3940
|
-
strokeLinejoin: "round",
|
|
3941
|
-
className: "w-4 h-4"
|
|
3942
|
-
},
|
|
3943
|
-
/* @__PURE__ */ React55.createElement("path", { d: "M18 6 6 18" }),
|
|
3944
|
-
/* @__PURE__ */ React55.createElement("path", { d: "m6 6 12 12" })
|
|
3945
|
-
);
|
|
3946
|
-
var SendIcon = () => /* @__PURE__ */ React55.createElement(
|
|
3947
|
-
"svg",
|
|
3948
|
-
{
|
|
3949
|
-
xmlns: "http://www.w3.org/2000/svg",
|
|
3950
|
-
viewBox: "0 0 24 24",
|
|
3951
|
-
fill: "none",
|
|
3952
|
-
stroke: "currentColor",
|
|
3953
|
-
strokeWidth: "2",
|
|
3954
|
-
strokeLinecap: "round",
|
|
3955
|
-
strokeLinejoin: "round",
|
|
3956
|
-
className: "w-4 h-4"
|
|
3957
|
-
},
|
|
3958
|
-
/* @__PURE__ */ React55.createElement("path", { d: "m22 2-7 20-4-9-9-4Z" }),
|
|
3959
|
-
/* @__PURE__ */ React55.createElement("path", { d: "M22 2 11 13" })
|
|
3862
|
+
var BRANCH_BUTTON_CLASSES = cx(
|
|
3863
|
+
"p-0.5 hover:text-white hover:bg-white/10 transition-colors",
|
|
3864
|
+
"disabled:opacity-30 disabled:cursor-not-allowed disabled:hover:bg-transparent disabled:hover:text-silver/70"
|
|
3960
3865
|
);
|
|
3866
|
+
function ActionButton({ onClick, label, children, disabled }) {
|
|
3867
|
+
return /* @__PURE__ */ React55.createElement(
|
|
3868
|
+
"button",
|
|
3869
|
+
{
|
|
3870
|
+
type: "button",
|
|
3871
|
+
onClick,
|
|
3872
|
+
disabled,
|
|
3873
|
+
className: ACTION_BUTTON_CLASSES,
|
|
3874
|
+
"aria-label": label
|
|
3875
|
+
},
|
|
3876
|
+
children
|
|
3877
|
+
);
|
|
3878
|
+
}
|
|
3961
3879
|
var Message = React55.forwardRef(
|
|
3962
3880
|
({
|
|
3963
3881
|
variant = "assistant",
|
|
@@ -3970,10 +3888,10 @@ var Message = React55.forwardRef(
|
|
|
3970
3888
|
...rest
|
|
3971
3889
|
}, ref) => {
|
|
3972
3890
|
const isUser = variant === "user";
|
|
3973
|
-
const
|
|
3974
|
-
const [isEditing, setIsEditing] =
|
|
3975
|
-
const [editValue, setEditValue] =
|
|
3976
|
-
const textareaRef =
|
|
3891
|
+
const { copied, copy } = useCopyToClipboard();
|
|
3892
|
+
const [isEditing, setIsEditing] = useState11(false);
|
|
3893
|
+
const [editValue, setEditValue] = useState11(typeof content === "string" ? content : "");
|
|
3894
|
+
const textareaRef = useRef6(null);
|
|
3977
3895
|
const showBranchNav = branchInfo && branchInfo.total > 1;
|
|
3978
3896
|
const showActions = actions && !hideActions && !isStreaming;
|
|
3979
3897
|
useEffect6(() => {
|
|
@@ -3985,25 +3903,11 @@ var Message = React55.forwardRef(
|
|
|
3985
3903
|
textarea.setSelectionRange(textarea.value.length, textarea.value.length);
|
|
3986
3904
|
}
|
|
3987
3905
|
}, [isEditing]);
|
|
3988
|
-
const handleCopy =
|
|
3989
|
-
if (typeof content
|
|
3990
|
-
|
|
3991
|
-
}
|
|
3992
|
-
try {
|
|
3993
|
-
await navigator.clipboard.writeText(content);
|
|
3994
|
-
setCopied(true);
|
|
3995
|
-
setTimeout(() => setCopied(false), 2e3);
|
|
3996
|
-
} catch {
|
|
3997
|
-
const textArea = document.createElement("textarea");
|
|
3998
|
-
textArea.value = content;
|
|
3999
|
-
document.body.appendChild(textArea);
|
|
4000
|
-
textArea.select();
|
|
4001
|
-
document.execCommand("copy");
|
|
4002
|
-
document.body.removeChild(textArea);
|
|
4003
|
-
setCopied(true);
|
|
4004
|
-
setTimeout(() => setCopied(false), 2e3);
|
|
3906
|
+
const handleCopy = useCallback12(() => {
|
|
3907
|
+
if (typeof content === "string") {
|
|
3908
|
+
void copy(content);
|
|
4005
3909
|
}
|
|
4006
|
-
};
|
|
3910
|
+
}, [copy, content]);
|
|
4007
3911
|
const handleStartEdit = () => {
|
|
4008
3912
|
if (typeof content === "string") {
|
|
4009
3913
|
setEditValue(content);
|
|
@@ -4066,7 +3970,7 @@ var Message = React55.forwardRef(
|
|
|
4066
3970
|
className: "p-1.5 text-obsidian/60 hover:text-obsidian transition-colors",
|
|
4067
3971
|
"aria-label": "Cancel edit"
|
|
4068
3972
|
},
|
|
4069
|
-
/* @__PURE__ */ React55.createElement(
|
|
3973
|
+
/* @__PURE__ */ React55.createElement(X5, { className: "w-4 h-4" })
|
|
4070
3974
|
), /* @__PURE__ */ React55.createElement(
|
|
4071
3975
|
"button",
|
|
4072
3976
|
{
|
|
@@ -4076,13 +3980,13 @@ var Message = React55.forwardRef(
|
|
|
4076
3980
|
className: "p-1.5 text-obsidian/60 hover:text-obsidian transition-colors disabled:opacity-30",
|
|
4077
3981
|
"aria-label": "Submit edit"
|
|
4078
3982
|
},
|
|
4079
|
-
/* @__PURE__ */ React55.createElement(
|
|
3983
|
+
/* @__PURE__ */ React55.createElement(Send, { className: "w-4 h-4" })
|
|
4080
3984
|
)))) : /* @__PURE__ */ React55.createElement(
|
|
4081
3985
|
"div",
|
|
4082
3986
|
{
|
|
4083
3987
|
className: cx(
|
|
4084
3988
|
"px-3 py-2 w-fit max-w-11/12",
|
|
4085
|
-
|
|
3989
|
+
VARIANT_STYLES3[variant]
|
|
4086
3990
|
)
|
|
4087
3991
|
},
|
|
4088
3992
|
typeof content === "string" ? /* @__PURE__ */ React55.createElement(
|
|
@@ -4104,33 +4008,27 @@ var Message = React55.forwardRef(
|
|
|
4104
4008
|
onClick: handleCopy,
|
|
4105
4009
|
label: copied ? "Copied!" : "Copy message"
|
|
4106
4010
|
},
|
|
4107
|
-
copied ? /* @__PURE__ */ React55.createElement(
|
|
4108
|
-
), isUser && actions.onEdit && typeof content === "string" && /* @__PURE__ */ React55.createElement(ActionButton, { onClick: handleStartEdit, label: "Edit message" }, /* @__PURE__ */ React55.createElement(
|
|
4011
|
+
copied ? /* @__PURE__ */ React55.createElement(Check3, { className: "w-3.5 h-3.5 text-success" }) : /* @__PURE__ */ React55.createElement(Copy, { className: "w-3.5 h-3.5" })
|
|
4012
|
+
), isUser && actions.onEdit && typeof content === "string" && /* @__PURE__ */ React55.createElement(ActionButton, { onClick: handleStartEdit, label: "Edit message" }, /* @__PURE__ */ React55.createElement(Pencil, { className: "w-3.5 h-3.5" })), !isUser && actions.onRetry && /* @__PURE__ */ React55.createElement(ActionButton, { onClick: actions.onRetry, label: "Regenerate response" }, /* @__PURE__ */ React55.createElement(RotateCcw, { className: "w-3.5 h-3.5" })), showBranchNav && /* @__PURE__ */ React55.createElement(React55.Fragment, null, /* @__PURE__ */ React55.createElement("div", { className: "w-px h-4 bg-ash/40 mx-1" }), /* @__PURE__ */ React55.createElement("div", { className: "flex items-center gap-0.5 text-silver/70" }, /* @__PURE__ */ React55.createElement(GitBranch, { className: "w-3 h-3 mr-0.5 text-silver/50" }), /* @__PURE__ */ React55.createElement(
|
|
4109
4013
|
"button",
|
|
4110
4014
|
{
|
|
4111
4015
|
type: "button",
|
|
4112
4016
|
onClick: branchInfo.onPrevious,
|
|
4113
4017
|
disabled: branchInfo.current <= 1,
|
|
4114
|
-
className:
|
|
4115
|
-
"p-0.5 hover:text-white hover:bg-white/10 transition-colors",
|
|
4116
|
-
"disabled:opacity-30 disabled:cursor-not-allowed disabled:hover:bg-transparent disabled:hover:text-silver/70"
|
|
4117
|
-
),
|
|
4018
|
+
className: BRANCH_BUTTON_CLASSES,
|
|
4118
4019
|
"aria-label": "Previous branch"
|
|
4119
4020
|
},
|
|
4120
|
-
/* @__PURE__ */ React55.createElement(
|
|
4021
|
+
/* @__PURE__ */ React55.createElement(ChevronLeft2, { className: "w-3 h-3" })
|
|
4121
4022
|
), /* @__PURE__ */ React55.createElement("span", { className: "text-xs tabular-nums min-w-6 text-center" }, branchInfo.current, "/", branchInfo.total), /* @__PURE__ */ React55.createElement(
|
|
4122
4023
|
"button",
|
|
4123
4024
|
{
|
|
4124
4025
|
type: "button",
|
|
4125
4026
|
onClick: branchInfo.onNext,
|
|
4126
4027
|
disabled: branchInfo.current >= branchInfo.total,
|
|
4127
|
-
className:
|
|
4128
|
-
"p-0.5 hover:text-white hover:bg-white/10 transition-colors",
|
|
4129
|
-
"disabled:opacity-30 disabled:cursor-not-allowed disabled:hover:bg-transparent disabled:hover:text-silver/70"
|
|
4130
|
-
),
|
|
4028
|
+
className: BRANCH_BUTTON_CLASSES,
|
|
4131
4029
|
"aria-label": "Next branch"
|
|
4132
4030
|
},
|
|
4133
|
-
/* @__PURE__ */ React55.createElement(
|
|
4031
|
+
/* @__PURE__ */ React55.createElement(ChevronRight3, { className: "w-3 h-3" })
|
|
4134
4032
|
))))
|
|
4135
4033
|
);
|
|
4136
4034
|
}
|
|
@@ -4141,7 +4039,7 @@ Message.displayName = "Message";
|
|
|
4141
4039
|
import React56 from "react";
|
|
4142
4040
|
var StreamingCursor = React56.forwardRef(
|
|
4143
4041
|
({ className, variant = "line", ...rest }, ref) => {
|
|
4144
|
-
const
|
|
4042
|
+
const variantStyles2 = {
|
|
4145
4043
|
block: "w-2.5 h-cursor translate-y-cursor-offset",
|
|
4146
4044
|
line: "w-0.5 h-cursor translate-y-cursor-offset",
|
|
4147
4045
|
underscore: "w-2.5 h-0.5 self-end mb-0.5"
|
|
@@ -4152,7 +4050,7 @@ var StreamingCursor = React56.forwardRef(
|
|
|
4152
4050
|
ref,
|
|
4153
4051
|
className: cx(
|
|
4154
4052
|
"inline-block bg-current animate-cursor-blink",
|
|
4155
|
-
|
|
4053
|
+
variantStyles2[variant],
|
|
4156
4054
|
className
|
|
4157
4055
|
),
|
|
4158
4056
|
"aria-hidden": "true",
|
|
@@ -4164,18 +4062,18 @@ var StreamingCursor = React56.forwardRef(
|
|
|
4164
4062
|
StreamingCursor.displayName = "StreamingCursor";
|
|
4165
4063
|
|
|
4166
4064
|
// src/components/chat/ChatInterface.tsx
|
|
4167
|
-
import React74, { useCallback as
|
|
4065
|
+
import React74, { useCallback as useCallback22, useEffect as useEffect16, useMemo as useMemo5, useRef as useRef15, useState as useState22 } from "react";
|
|
4168
4066
|
|
|
4169
4067
|
// src/components/chat/ChatView.tsx
|
|
4170
4068
|
import React58, { useEffect as useEffect9 } from "react";
|
|
4171
4069
|
|
|
4172
4070
|
// src/components/chat/hooks/useScrollAnchor.ts
|
|
4173
|
-
import { useCallback as
|
|
4071
|
+
import { useCallback as useCallback13, useRef as useRef7 } from "react";
|
|
4174
4072
|
function useScrollAnchor(options = {}) {
|
|
4175
4073
|
const { behavior = "smooth", block = "start" } = options;
|
|
4176
|
-
const containerRef =
|
|
4177
|
-
const anchorRef =
|
|
4178
|
-
const scrollToAnchor =
|
|
4074
|
+
const containerRef = useRef7(null);
|
|
4075
|
+
const anchorRef = useRef7(null);
|
|
4076
|
+
const scrollToAnchor = useCallback13(() => {
|
|
4179
4077
|
const el = anchorRef.current;
|
|
4180
4078
|
if (!el) {
|
|
4181
4079
|
return;
|
|
@@ -4186,7 +4084,7 @@ function useScrollAnchor(options = {}) {
|
|
|
4186
4084
|
});
|
|
4187
4085
|
});
|
|
4188
4086
|
}, [behavior, block]);
|
|
4189
|
-
const scrollToBottom =
|
|
4087
|
+
const scrollToBottom = useCallback13(() => {
|
|
4190
4088
|
const container = containerRef.current;
|
|
4191
4089
|
if (!container) {
|
|
4192
4090
|
return;
|
|
@@ -4197,7 +4095,7 @@ function useScrollAnchor(options = {}) {
|
|
|
4197
4095
|
container.scrollTop = container.scrollHeight;
|
|
4198
4096
|
}
|
|
4199
4097
|
}, [behavior]);
|
|
4200
|
-
const isScrolledToBottom =
|
|
4098
|
+
const isScrolledToBottom = useCallback13(() => {
|
|
4201
4099
|
const container = containerRef.current;
|
|
4202
4100
|
if (!container) {
|
|
4203
4101
|
return true;
|
|
@@ -4216,15 +4114,15 @@ function useScrollAnchor(options = {}) {
|
|
|
4216
4114
|
}
|
|
4217
4115
|
|
|
4218
4116
|
// src/components/chat/hooks/useAdaptiveSpacer.ts
|
|
4219
|
-
import { useCallback as
|
|
4117
|
+
import { useCallback as useCallback14, useEffect as useEffect7, useRef as useRef8, useState as useState12 } from "react";
|
|
4220
4118
|
function useAdaptiveSpacer(options = {}) {
|
|
4221
4119
|
const { minHeight = 0, containerRef: externalContainerRef, anchorRef } = options;
|
|
4222
|
-
const internalContainerRef =
|
|
4120
|
+
const internalContainerRef = useRef8(null);
|
|
4223
4121
|
const containerRef = externalContainerRef ?? internalContainerRef;
|
|
4224
|
-
const contentRef =
|
|
4225
|
-
const spacerRef =
|
|
4226
|
-
const [spacerHeight, setSpacerHeight] =
|
|
4227
|
-
const recalculate =
|
|
4122
|
+
const contentRef = useRef8(null);
|
|
4123
|
+
const spacerRef = useRef8(null);
|
|
4124
|
+
const [spacerHeight, setSpacerHeight] = useState12(0);
|
|
4125
|
+
const recalculate = useCallback14(() => {
|
|
4228
4126
|
const container = containerRef.current;
|
|
4229
4127
|
const content = contentRef.current;
|
|
4230
4128
|
if (!container || !content) {
|
|
@@ -4283,7 +4181,7 @@ function useAdaptiveSpacer(options = {}) {
|
|
|
4283
4181
|
}
|
|
4284
4182
|
|
|
4285
4183
|
// src/components/chat/ThinkingIndicator.tsx
|
|
4286
|
-
import React57, { useEffect as useEffect8, useState as
|
|
4184
|
+
import React57, { useEffect as useEffect8, useState as useState13 } from "react";
|
|
4287
4185
|
var THINKING_PHRASES = [
|
|
4288
4186
|
"Consulting the ancient tomes...",
|
|
4289
4187
|
"Parsing the ineffable...",
|
|
@@ -4307,22 +4205,29 @@ var ThinkingIndicator = React57.forwardRef(
|
|
|
4307
4205
|
className,
|
|
4308
4206
|
...rest
|
|
4309
4207
|
}, ref) => {
|
|
4310
|
-
const [currentIndex, setCurrentIndex] =
|
|
4208
|
+
const [currentIndex, setCurrentIndex] = useState13(
|
|
4311
4209
|
() => Math.floor(Math.random() * phrases.length)
|
|
4312
4210
|
);
|
|
4313
|
-
const [isTransitioning, setIsTransitioning] =
|
|
4211
|
+
const [isTransitioning, setIsTransitioning] = useState13(false);
|
|
4314
4212
|
useEffect8(() => {
|
|
4315
4213
|
if (!isVisible || phrases.length <= 1) {
|
|
4316
4214
|
return;
|
|
4317
4215
|
}
|
|
4216
|
+
let fadeTimeout = null;
|
|
4318
4217
|
const interval = setInterval(() => {
|
|
4319
4218
|
setIsTransitioning(true);
|
|
4320
|
-
setTimeout(() => {
|
|
4219
|
+
fadeTimeout = setTimeout(() => {
|
|
4321
4220
|
setCurrentIndex((prev) => (prev + 1) % phrases.length);
|
|
4322
4221
|
setIsTransitioning(false);
|
|
4222
|
+
fadeTimeout = null;
|
|
4323
4223
|
}, 200);
|
|
4324
4224
|
}, phraseInterval);
|
|
4325
|
-
return () =>
|
|
4225
|
+
return () => {
|
|
4226
|
+
clearInterval(interval);
|
|
4227
|
+
if (fadeTimeout !== null) {
|
|
4228
|
+
clearTimeout(fadeTimeout);
|
|
4229
|
+
}
|
|
4230
|
+
};
|
|
4326
4231
|
}, [isVisible, phrases.length, phraseInterval]);
|
|
4327
4232
|
if (!isVisible) {
|
|
4328
4233
|
return null;
|
|
@@ -4401,15 +4306,7 @@ var ChatView = React58.forwardRef(
|
|
|
4401
4306
|
return /* @__PURE__ */ React58.createElement(
|
|
4402
4307
|
"div",
|
|
4403
4308
|
{
|
|
4404
|
-
ref: (
|
|
4405
|
-
;
|
|
4406
|
-
containerRef.current = node;
|
|
4407
|
-
if (typeof ref === "function") {
|
|
4408
|
-
ref(node);
|
|
4409
|
-
} else if (ref) {
|
|
4410
|
-
ref.current = node;
|
|
4411
|
-
}
|
|
4412
|
-
},
|
|
4309
|
+
ref: composeRefs(containerRef, ref),
|
|
4413
4310
|
onScroll,
|
|
4414
4311
|
className: cx(
|
|
4415
4312
|
"flex flex-col w-full h-full overflow-y-auto scroll-smooth",
|
|
@@ -4467,8 +4364,8 @@ var ChatView = React58.forwardRef(
|
|
|
4467
4364
|
ChatView.displayName = "ChatView";
|
|
4468
4365
|
|
|
4469
4366
|
// src/components/chat/ChatInput.tsx
|
|
4470
|
-
import React59, { useCallback as
|
|
4471
|
-
import { Paperclip, Send, Square, X as
|
|
4367
|
+
import React59, { useCallback as useCallback15, useEffect as useEffect10, useRef as useRef9, useState as useState14 } from "react";
|
|
4368
|
+
import { Paperclip, Send as Send2, Square, X as X6 } from "lucide-react";
|
|
4472
4369
|
|
|
4473
4370
|
// src/components/chat/types.ts
|
|
4474
4371
|
function isImageFile(file) {
|
|
@@ -4480,13 +4377,11 @@ function createPreviewUrl(file) {
|
|
|
4480
4377
|
}
|
|
4481
4378
|
return void 0;
|
|
4482
4379
|
}
|
|
4483
|
-
function revokePreviewUrl(url) {
|
|
4484
|
-
if (url) {
|
|
4485
|
-
URL.revokeObjectURL(url);
|
|
4486
|
-
}
|
|
4487
|
-
}
|
|
4488
4380
|
function generateId() {
|
|
4489
|
-
|
|
4381
|
+
if (typeof crypto !== "undefined" && typeof crypto.randomUUID === "function") {
|
|
4382
|
+
return crypto.randomUUID();
|
|
4383
|
+
}
|
|
4384
|
+
return `${Date.now()}-${Math.random().toString(36).slice(2, 11)}`;
|
|
4490
4385
|
}
|
|
4491
4386
|
function createEmptyTree() {
|
|
4492
4387
|
return {
|
|
@@ -4656,13 +4551,13 @@ var ChatInput = React59.forwardRef(
|
|
|
4656
4551
|
className,
|
|
4657
4552
|
...rest
|
|
4658
4553
|
}, ref) => {
|
|
4659
|
-
const [value, setValue] =
|
|
4660
|
-
const [localAttachments, setLocalAttachments] =
|
|
4661
|
-
const [isDragOver, setIsDragOver] =
|
|
4662
|
-
const textareaRef =
|
|
4663
|
-
const fileInputRef =
|
|
4554
|
+
const [value, setValue] = useState14(initialInputValue);
|
|
4555
|
+
const [localAttachments, setLocalAttachments] = useState14([]);
|
|
4556
|
+
const [isDragOver, setIsDragOver] = useState14(false);
|
|
4557
|
+
const textareaRef = useRef9(null);
|
|
4558
|
+
const fileInputRef = useRef9(null);
|
|
4664
4559
|
const attachments = controlledAttachments ?? localAttachments;
|
|
4665
|
-
const setAttachments =
|
|
4560
|
+
const setAttachments = useCallback15(
|
|
4666
4561
|
(newAttachments) => {
|
|
4667
4562
|
if (onAttachmentsChange) {
|
|
4668
4563
|
if (typeof newAttachments === "function") {
|
|
@@ -4676,7 +4571,7 @@ var ChatInput = React59.forwardRef(
|
|
|
4676
4571
|
},
|
|
4677
4572
|
[attachments, onAttachmentsChange]
|
|
4678
4573
|
);
|
|
4679
|
-
const handleSubmit =
|
|
4574
|
+
const handleSubmit = useCallback15(() => {
|
|
4680
4575
|
const trimmed = value.trim();
|
|
4681
4576
|
if (!trimmed || disabled || isStreaming) {
|
|
4682
4577
|
return;
|
|
@@ -4688,7 +4583,7 @@ var ChatInput = React59.forwardRef(
|
|
|
4688
4583
|
textareaRef.current.style.height = "auto";
|
|
4689
4584
|
}
|
|
4690
4585
|
}, [value, disabled, isStreaming, onSubmit, attachments, setAttachments]);
|
|
4691
|
-
const handleKeyDown =
|
|
4586
|
+
const handleKeyDown = useCallback15(
|
|
4692
4587
|
(e) => {
|
|
4693
4588
|
if (e.key === "Enter" && !e.shiftKey) {
|
|
4694
4589
|
e.preventDefault();
|
|
@@ -4697,7 +4592,7 @@ var ChatInput = React59.forwardRef(
|
|
|
4697
4592
|
},
|
|
4698
4593
|
[handleSubmit]
|
|
4699
4594
|
);
|
|
4700
|
-
const handleChange =
|
|
4595
|
+
const handleChange = useCallback15((e) => {
|
|
4701
4596
|
setValue(e.target.value);
|
|
4702
4597
|
onInputChange?.(e.target.value);
|
|
4703
4598
|
const textarea = e.target;
|
|
@@ -4709,7 +4604,7 @@ var ChatInput = React59.forwardRef(
|
|
|
4709
4604
|
textareaRef.current.focus();
|
|
4710
4605
|
}
|
|
4711
4606
|
}, [disabled, isStreaming, autoFocus]);
|
|
4712
|
-
const addFiles =
|
|
4607
|
+
const addFiles = useCallback15(
|
|
4713
4608
|
(files) => {
|
|
4714
4609
|
const newAttachments = Array.from(files).map((file) => ({
|
|
4715
4610
|
id: generateId(),
|
|
@@ -4721,7 +4616,7 @@ var ChatInput = React59.forwardRef(
|
|
|
4721
4616
|
},
|
|
4722
4617
|
[setAttachments]
|
|
4723
4618
|
);
|
|
4724
|
-
const handleFileSelect =
|
|
4619
|
+
const handleFileSelect = useCallback15(
|
|
4725
4620
|
(e) => {
|
|
4726
4621
|
const files = e.target.files;
|
|
4727
4622
|
if (files && files.length > 0) {
|
|
@@ -4731,7 +4626,7 @@ var ChatInput = React59.forwardRef(
|
|
|
4731
4626
|
},
|
|
4732
4627
|
[addFiles]
|
|
4733
4628
|
);
|
|
4734
|
-
const handleRemoveAttachment =
|
|
4629
|
+
const handleRemoveAttachment = useCallback15(
|
|
4735
4630
|
(id) => {
|
|
4736
4631
|
const attachment = attachments.find((a) => a.id === id);
|
|
4737
4632
|
if (attachment && onAttachmentRemove) {
|
|
@@ -4747,23 +4642,23 @@ var ChatInput = React59.forwardRef(
|
|
|
4747
4642
|
},
|
|
4748
4643
|
[attachments, onAttachmentRemove, setAttachments]
|
|
4749
4644
|
);
|
|
4750
|
-
const handleDragEnter =
|
|
4645
|
+
const handleDragEnter = useCallback15((e) => {
|
|
4751
4646
|
e.preventDefault();
|
|
4752
4647
|
e.stopPropagation();
|
|
4753
4648
|
setIsDragOver(true);
|
|
4754
4649
|
}, []);
|
|
4755
|
-
const handleDragLeave =
|
|
4650
|
+
const handleDragLeave = useCallback15((e) => {
|
|
4756
4651
|
e.preventDefault();
|
|
4757
4652
|
e.stopPropagation();
|
|
4758
4653
|
if (!e.currentTarget.contains(e.relatedTarget)) {
|
|
4759
4654
|
setIsDragOver(false);
|
|
4760
4655
|
}
|
|
4761
4656
|
}, []);
|
|
4762
|
-
const handleDragOver =
|
|
4657
|
+
const handleDragOver = useCallback15((e) => {
|
|
4763
4658
|
e.preventDefault();
|
|
4764
4659
|
e.stopPropagation();
|
|
4765
4660
|
}, []);
|
|
4766
|
-
const handleDrop =
|
|
4661
|
+
const handleDrop = useCallback15(
|
|
4767
4662
|
(e) => {
|
|
4768
4663
|
e.preventDefault();
|
|
4769
4664
|
e.stopPropagation();
|
|
@@ -4807,7 +4702,7 @@ var ChatInput = React59.forwardRef(
|
|
|
4807
4702
|
notice.variant === "warning" ? "text-gold" : "text-error"
|
|
4808
4703
|
)
|
|
4809
4704
|
},
|
|
4810
|
-
/* @__PURE__ */ React59.createElement(
|
|
4705
|
+
/* @__PURE__ */ React59.createElement(X6, { className: "w-3 h-3" })
|
|
4811
4706
|
)),
|
|
4812
4707
|
/* @__PURE__ */ React59.createElement(
|
|
4813
4708
|
"div",
|
|
@@ -4906,7 +4801,7 @@ var ChatInput = React59.forwardRef(
|
|
|
4906
4801
|
),
|
|
4907
4802
|
"aria-label": "Send message"
|
|
4908
4803
|
},
|
|
4909
|
-
/* @__PURE__ */ React59.createElement(
|
|
4804
|
+
/* @__PURE__ */ React59.createElement(Send2, { className: "w-5 h-5" })
|
|
4910
4805
|
))
|
|
4911
4806
|
)
|
|
4912
4807
|
);
|
|
@@ -4915,7 +4810,8 @@ var ChatInput = React59.forwardRef(
|
|
|
4915
4810
|
ChatInput.displayName = "ChatInput";
|
|
4916
4811
|
|
|
4917
4812
|
// src/components/chat/ArtifactsPanel.tsx
|
|
4918
|
-
import React69, { useCallback as
|
|
4813
|
+
import React69, { useCallback as useCallback17, useEffect as useEffect12, useRef as useRef11, useState as useState17 } from "react";
|
|
4814
|
+
import { Image } from "lucide-react";
|
|
4919
4815
|
|
|
4920
4816
|
// src/components/ArtifactCard.tsx
|
|
4921
4817
|
import React66 from "react";
|
|
@@ -5119,15 +5015,7 @@ var AudioCard = React62.forwardRef(
|
|
|
5119
5015
|
loop,
|
|
5120
5016
|
width: "100%",
|
|
5121
5017
|
height,
|
|
5122
|
-
style: { backgroundColor: "transparent" },
|
|
5123
|
-
config: {
|
|
5124
|
-
file: {
|
|
5125
|
-
forceAudio: true,
|
|
5126
|
-
attributes: {
|
|
5127
|
-
style: { width: "100%", height }
|
|
5128
|
-
}
|
|
5129
|
-
}
|
|
5130
|
-
},
|
|
5018
|
+
style: { backgroundColor: "transparent", width: "100%", height },
|
|
5131
5019
|
...playerProps
|
|
5132
5020
|
}
|
|
5133
5021
|
))),
|
|
@@ -5411,8 +5299,10 @@ var ArtifactCard = React66.forwardRef(
|
|
|
5411
5299
|
)
|
|
5412
5300
|
}
|
|
5413
5301
|
);
|
|
5414
|
-
default:
|
|
5415
|
-
|
|
5302
|
+
default: {
|
|
5303
|
+
const _exhaustive = artifact.type;
|
|
5304
|
+
return _exhaustive;
|
|
5305
|
+
}
|
|
5416
5306
|
}
|
|
5417
5307
|
};
|
|
5418
5308
|
const isCardExpandable = !!onExpand && (artifact.type === "IMAGE" || artifact.type === "PDF" || artifact.type === "SCRIPT" || artifact.type === "TEXT");
|
|
@@ -5449,7 +5339,7 @@ var ArtifactCard = React66.forwardRef(
|
|
|
5449
5339
|
ArtifactCard.displayName = "ArtifactCard";
|
|
5450
5340
|
|
|
5451
5341
|
// src/components/ArtifactGroup.tsx
|
|
5452
|
-
import React67, { useEffect as useEffect11, useRef as
|
|
5342
|
+
import React67, { useEffect as useEffect11, useRef as useRef10, useState as useState15 } from "react";
|
|
5453
5343
|
var LAYER_OFFSET = "8px";
|
|
5454
5344
|
var LAYER_OFFSET_2X = "16px";
|
|
5455
5345
|
var ArtifactGroup = React67.forwardRef(
|
|
@@ -5457,8 +5347,8 @@ var ArtifactGroup = React67.forwardRef(
|
|
|
5457
5347
|
const children = node.children;
|
|
5458
5348
|
const count = children.length;
|
|
5459
5349
|
const frontChild = children[0];
|
|
5460
|
-
const prevCountRef =
|
|
5461
|
-
const [badgePing, setBadgePing] =
|
|
5350
|
+
const prevCountRef = useRef10(count);
|
|
5351
|
+
const [badgePing, setBadgePing] = useState15(false);
|
|
5462
5352
|
useEffect11(() => {
|
|
5463
5353
|
if (count !== prevCountRef.current) {
|
|
5464
5354
|
prevCountRef.current = count;
|
|
@@ -5579,9 +5469,9 @@ var ArtifactVariantStack = React68.forwardRef(
|
|
|
5579
5469
|
ArtifactVariantStack.displayName = "ArtifactVariantStack";
|
|
5580
5470
|
|
|
5581
5471
|
// src/components/chat/hooks/useArtifactTreeNavigation.ts
|
|
5582
|
-
import { useCallback as
|
|
5472
|
+
import { useCallback as useCallback16, useMemo as useMemo2, useState as useState16 } from "react";
|
|
5583
5473
|
function useArtifactTreeNavigation(rootNodes) {
|
|
5584
|
-
const [stack, setStack] =
|
|
5474
|
+
const [stack, setStack] = useState16([]);
|
|
5585
5475
|
const currentNodes = useMemo2(() => {
|
|
5586
5476
|
if (stack.length === 0) return rootNodes;
|
|
5587
5477
|
return stack[stack.length - 1].children;
|
|
@@ -5594,13 +5484,13 @@ function useArtifactTreeNavigation(rootNodes) {
|
|
|
5594
5484
|
return entries;
|
|
5595
5485
|
}, [stack]);
|
|
5596
5486
|
const isAtRoot = stack.length === 0;
|
|
5597
|
-
const navigateInto =
|
|
5487
|
+
const navigateInto = useCallback16((node) => {
|
|
5598
5488
|
setStack((prev) => [...prev, node]);
|
|
5599
5489
|
}, []);
|
|
5600
|
-
const navigateTo =
|
|
5490
|
+
const navigateTo = useCallback16((index) => {
|
|
5601
5491
|
setStack((prev) => prev.slice(0, index));
|
|
5602
5492
|
}, []);
|
|
5603
|
-
const navigateBack =
|
|
5493
|
+
const navigateBack = useCallback16(() => {
|
|
5604
5494
|
setStack((prev) => prev.slice(0, -1));
|
|
5605
5495
|
}, []);
|
|
5606
5496
|
return {
|
|
@@ -5619,16 +5509,8 @@ function ArtifactModal({
|
|
|
5619
5509
|
artifact,
|
|
5620
5510
|
onClose
|
|
5621
5511
|
}) {
|
|
5622
|
-
|
|
5623
|
-
|
|
5624
|
-
if (e.key === "Escape") {
|
|
5625
|
-
onClose();
|
|
5626
|
-
}
|
|
5627
|
-
};
|
|
5628
|
-
document.addEventListener("keydown", handleKeyDown);
|
|
5629
|
-
return () => document.removeEventListener("keydown", handleKeyDown);
|
|
5630
|
-
}, [onClose]);
|
|
5631
|
-
const handleBackdropClick = useCallback15((e) => {
|
|
5512
|
+
useEscapeKey(onClose);
|
|
5513
|
+
const handleBackdropClick = useCallback17((e) => {
|
|
5632
5514
|
if (e.target === e.currentTarget) {
|
|
5633
5515
|
onClose();
|
|
5634
5516
|
}
|
|
@@ -5747,25 +5629,25 @@ var ArtifactsPanel = React69.forwardRef(
|
|
|
5747
5629
|
className,
|
|
5748
5630
|
...rest
|
|
5749
5631
|
}, ref) => {
|
|
5750
|
-
const [expandedArtifact, setExpandedArtifact] =
|
|
5751
|
-
const [zoomIndex, setZoomIndex] =
|
|
5632
|
+
const [expandedArtifact, setExpandedArtifact] = useState17(null);
|
|
5633
|
+
const [zoomIndex, setZoomIndex] = useState17(ZOOM_LEVELS.length - 1);
|
|
5752
5634
|
const treeNav = useArtifactTreeNavigation(nodes || []);
|
|
5753
5635
|
const hasNodes = !!nodes && nodes.length > 0;
|
|
5754
|
-
const handleExpandArtifact =
|
|
5636
|
+
const handleExpandArtifact = useCallback17((artifact) => {
|
|
5755
5637
|
setExpandedArtifact(artifact);
|
|
5756
5638
|
}, []);
|
|
5757
|
-
const handleGroupClick =
|
|
5639
|
+
const handleGroupClick = useCallback17((node) => {
|
|
5758
5640
|
treeNav.navigateInto(node);
|
|
5759
5641
|
}, [treeNav]);
|
|
5760
|
-
const zoomIn =
|
|
5642
|
+
const zoomIn = useCallback17(() => {
|
|
5761
5643
|
setZoomIndex((prev) => Math.min(prev + 1, ZOOM_LEVELS.length - 1));
|
|
5762
5644
|
}, []);
|
|
5763
|
-
const zoomOut =
|
|
5645
|
+
const zoomOut = useCallback17(() => {
|
|
5764
5646
|
setZoomIndex((prev) => Math.max(prev - 1, 0));
|
|
5765
5647
|
}, []);
|
|
5766
5648
|
const currentZoom = ZOOM_LEVELS[zoomIndex];
|
|
5767
|
-
const contentRef =
|
|
5768
|
-
const [contentHeight, setContentHeight] =
|
|
5649
|
+
const contentRef = useRef11(null);
|
|
5650
|
+
const [contentHeight, setContentHeight] = useState17(void 0);
|
|
5769
5651
|
useEffect12(() => {
|
|
5770
5652
|
const el = contentRef.current;
|
|
5771
5653
|
if (!el) return;
|
|
@@ -5911,23 +5793,7 @@ var ArtifactsPanelToggle = React69.forwardRef(({ artifactCount = 0, onExpand, cl
|
|
|
5911
5793
|
"aria-label": "Expand artifacts panel",
|
|
5912
5794
|
...rest
|
|
5913
5795
|
},
|
|
5914
|
-
/* @__PURE__ */ React69.createElement(
|
|
5915
|
-
"svg",
|
|
5916
|
-
{
|
|
5917
|
-
xmlns: "http://www.w3.org/2000/svg",
|
|
5918
|
-
viewBox: "0 0 20 20",
|
|
5919
|
-
fill: "currentColor",
|
|
5920
|
-
className: "w-5 h-5"
|
|
5921
|
-
},
|
|
5922
|
-
/* @__PURE__ */ React69.createElement(
|
|
5923
|
-
"path",
|
|
5924
|
-
{
|
|
5925
|
-
fillRule: "evenodd",
|
|
5926
|
-
d: "M2 4.5A1.5 1.5 0 013.5 3h13A1.5 1.5 0 0118 4.5v11a1.5 1.5 0 01-1.5 1.5h-13A1.5 1.5 0 012 15.5v-11zM4 5v1h1V5H4zm2 0v1h1V5H6zm7 0v1h1V5h-1zm2 0v1h1V5h-1zM4 14v1h1v-1H4zm2 0v1h1v-1H6zm7 0v1h1v-1h-1zm2 0v1h1v-1h-1zM8 8.118a.5.5 0 01.757-.429l4 2.382a.5.5 0 010 .858l-4 2.382A.5.5 0 018 12.882V8.118z",
|
|
5927
|
-
clipRule: "evenodd"
|
|
5928
|
-
}
|
|
5929
|
-
)
|
|
5930
|
-
),
|
|
5796
|
+
/* @__PURE__ */ React69.createElement(Image, { className: "w-5 h-5", "aria-hidden": true }),
|
|
5931
5797
|
artifactCount > 0 && /* @__PURE__ */ React69.createElement(
|
|
5932
5798
|
"span",
|
|
5933
5799
|
{
|
|
@@ -5940,7 +5806,8 @@ var ArtifactsPanelToggle = React69.forwardRef(({ artifactCount = 0, onExpand, cl
|
|
|
5940
5806
|
ArtifactsPanelToggle.displayName = "ArtifactsPanelToggle";
|
|
5941
5807
|
|
|
5942
5808
|
// src/components/chat/HistoryPanel.tsx
|
|
5943
|
-
import React70, { useCallback as
|
|
5809
|
+
import React70, { useCallback as useCallback18, useEffect as useEffect13, useMemo as useMemo3, useRef as useRef12, useState as useState18 } from "react";
|
|
5810
|
+
import { ChevronDown as ChevronDown2, Pencil as Pencil2 } from "lucide-react";
|
|
5944
5811
|
function parseTimestamp(ts) {
|
|
5945
5812
|
if (ts == null) {
|
|
5946
5813
|
return null;
|
|
@@ -5976,64 +5843,16 @@ function groupConversations(conversations) {
|
|
|
5976
5843
|
{ key: "older", label: "Older", conversations: olderList }
|
|
5977
5844
|
].filter((g) => g.conversations.length > 0);
|
|
5978
5845
|
}
|
|
5979
|
-
function ChevronDownIcon({ className }) {
|
|
5980
|
-
return /* @__PURE__ */ React70.createElement(
|
|
5981
|
-
"svg",
|
|
5982
|
-
{
|
|
5983
|
-
xmlns: "http://www.w3.org/2000/svg",
|
|
5984
|
-
viewBox: "0 0 20 20",
|
|
5985
|
-
fill: "currentColor",
|
|
5986
|
-
className,
|
|
5987
|
-
"aria-hidden": "true"
|
|
5988
|
-
},
|
|
5989
|
-
/* @__PURE__ */ React70.createElement(
|
|
5990
|
-
"path",
|
|
5991
|
-
{
|
|
5992
|
-
fillRule: "evenodd",
|
|
5993
|
-
d: "M5.23 7.21a.75.75 0 011.06.02L10 11.06l3.71-3.83a.75.75 0 111.08 1.04l-4.25 4.39a.75.75 0 01-1.08 0L5.21 8.27a.75.75 0 01.02-1.06z",
|
|
5994
|
-
clipRule: "evenodd"
|
|
5995
|
-
}
|
|
5996
|
-
)
|
|
5997
|
-
);
|
|
5998
|
-
}
|
|
5999
|
-
function PencilIcon2({ className }) {
|
|
6000
|
-
return /* @__PURE__ */ React70.createElement(
|
|
6001
|
-
"svg",
|
|
6002
|
-
{
|
|
6003
|
-
xmlns: "http://www.w3.org/2000/svg",
|
|
6004
|
-
viewBox: "0 0 20 20",
|
|
6005
|
-
fill: "currentColor",
|
|
6006
|
-
className,
|
|
6007
|
-
"aria-hidden": "true"
|
|
6008
|
-
},
|
|
6009
|
-
/* @__PURE__ */ React70.createElement(
|
|
6010
|
-
"path",
|
|
6011
|
-
{
|
|
6012
|
-
d: "M13.586 3.586a2 2 0 112.828 2.828l-.793.793-2.828-2.828.793-.793zM11.379 5.793L3 14.172V17h2.828l8.38-8.379-2.83-2.828z"
|
|
6013
|
-
}
|
|
6014
|
-
)
|
|
6015
|
-
);
|
|
6016
|
-
}
|
|
6017
5846
|
function ProjectFilter({
|
|
6018
5847
|
projects,
|
|
6019
5848
|
value,
|
|
6020
5849
|
onChange,
|
|
6021
5850
|
className
|
|
6022
5851
|
}) {
|
|
6023
|
-
const [open, setOpen] =
|
|
6024
|
-
const ref =
|
|
6025
|
-
|
|
6026
|
-
|
|
6027
|
-
return;
|
|
6028
|
-
}
|
|
6029
|
-
const handler = (e) => {
|
|
6030
|
-
if (ref.current && !ref.current.contains(e.target)) {
|
|
6031
|
-
setOpen(false);
|
|
6032
|
-
}
|
|
6033
|
-
};
|
|
6034
|
-
document.addEventListener("mousedown", handler);
|
|
6035
|
-
return () => document.removeEventListener("mousedown", handler);
|
|
6036
|
-
}, [open]);
|
|
5852
|
+
const [open, setOpen] = useState18(false);
|
|
5853
|
+
const ref = useRef12(null);
|
|
5854
|
+
const closeFilter = useCallback18(() => setOpen(false), []);
|
|
5855
|
+
useClickOutside(ref, closeFilter, open);
|
|
6037
5856
|
const label = value ?? "All projects";
|
|
6038
5857
|
return /* @__PURE__ */ React70.createElement("div", { className: cx("relative min-w-0", className), ref }, /* @__PURE__ */ React70.createElement(
|
|
6039
5858
|
"button",
|
|
@@ -6052,7 +5871,7 @@ function ProjectFilter({
|
|
|
6052
5871
|
)
|
|
6053
5872
|
},
|
|
6054
5873
|
/* @__PURE__ */ React70.createElement("span", { className: "truncate" }, label),
|
|
6055
|
-
/* @__PURE__ */ React70.createElement(
|
|
5874
|
+
/* @__PURE__ */ React70.createElement(ChevronDown2, { className: "w-3 h-3 shrink-0", "aria-hidden": true })
|
|
6056
5875
|
), open && /* @__PURE__ */ React70.createElement(
|
|
6057
5876
|
"div",
|
|
6058
5877
|
{
|
|
@@ -6107,28 +5926,28 @@ function ConversationRow({
|
|
|
6107
5926
|
onSelect,
|
|
6108
5927
|
onRename
|
|
6109
5928
|
}) {
|
|
6110
|
-
const [isEditing, setIsEditing] =
|
|
6111
|
-
const [draft, setDraft] =
|
|
6112
|
-
const inputRef =
|
|
5929
|
+
const [isEditing, setIsEditing] = useState18(false);
|
|
5930
|
+
const [draft, setDraft] = useState18(conversation.title);
|
|
5931
|
+
const inputRef = useRef12(null);
|
|
6113
5932
|
useEffect13(() => {
|
|
6114
5933
|
if (isEditing && inputRef.current) {
|
|
6115
5934
|
inputRef.current.focus();
|
|
6116
5935
|
inputRef.current.select();
|
|
6117
5936
|
}
|
|
6118
5937
|
}, [isEditing]);
|
|
6119
|
-
const startEdit =
|
|
5938
|
+
const startEdit = useCallback18((e) => {
|
|
6120
5939
|
e.stopPropagation();
|
|
6121
5940
|
setDraft(conversation.title);
|
|
6122
5941
|
setIsEditing(true);
|
|
6123
5942
|
}, [conversation.title]);
|
|
6124
|
-
const commit =
|
|
5943
|
+
const commit = useCallback18(() => {
|
|
6125
5944
|
const trimmed = draft.trim();
|
|
6126
5945
|
if (trimmed && trimmed !== conversation.title) {
|
|
6127
5946
|
onRename?.(conversation.id, trimmed);
|
|
6128
5947
|
}
|
|
6129
5948
|
setIsEditing(false);
|
|
6130
5949
|
}, [draft, conversation.id, conversation.title, onRename]);
|
|
6131
|
-
const cancel =
|
|
5950
|
+
const cancel = useCallback18(() => {
|
|
6132
5951
|
setDraft(conversation.title);
|
|
6133
5952
|
setIsEditing(false);
|
|
6134
5953
|
}, [conversation.title]);
|
|
@@ -6203,7 +6022,7 @@ function ConversationRow({
|
|
|
6203
6022
|
"transition-opacity duration-150"
|
|
6204
6023
|
)
|
|
6205
6024
|
},
|
|
6206
|
-
/* @__PURE__ */ React70.createElement(
|
|
6025
|
+
/* @__PURE__ */ React70.createElement(Pencil2, { className: "w-3.5 h-3.5", "aria-hidden": true })
|
|
6207
6026
|
));
|
|
6208
6027
|
}
|
|
6209
6028
|
function HistoryPanel({
|
|
@@ -6212,7 +6031,7 @@ function HistoryPanel({
|
|
|
6212
6031
|
onNewChat,
|
|
6213
6032
|
onRenameConversation
|
|
6214
6033
|
}) {
|
|
6215
|
-
const [projectFilter, setProjectFilter] =
|
|
6034
|
+
const [projectFilter, setProjectFilter] = useState18(null);
|
|
6216
6035
|
const projects = useMemo3(() => {
|
|
6217
6036
|
const set = /* @__PURE__ */ new Set();
|
|
6218
6037
|
for (const c of conversations) {
|
|
@@ -6278,7 +6097,7 @@ function HistoryPanel({
|
|
|
6278
6097
|
}
|
|
6279
6098
|
|
|
6280
6099
|
// src/components/chat/TodosList.tsx
|
|
6281
|
-
import React71, { useCallback as
|
|
6100
|
+
import React71, { useCallback as useCallback19, useMemo as useMemo4, useState as useState19 } from "react";
|
|
6282
6101
|
import { Loader2 as Loader22, Square as Square2 } from "lucide-react";
|
|
6283
6102
|
var TASK_STATUSES = {
|
|
6284
6103
|
PENDING: "pending",
|
|
@@ -6357,8 +6176,8 @@ function hasInProgressTask(tasks) {
|
|
|
6357
6176
|
var TodosList = React71.forwardRef(
|
|
6358
6177
|
({ tasks, title = "Tasks", onStopAllTasks, className, ...rest }, ref) => {
|
|
6359
6178
|
const sortedTasks = useMemo4(() => sortTasks(tasks), [tasks]);
|
|
6360
|
-
const [isStopping, setIsStopping] =
|
|
6361
|
-
const handleStopClick =
|
|
6179
|
+
const [isStopping, setIsStopping] = useState19(false);
|
|
6180
|
+
const handleStopClick = useCallback19(async () => {
|
|
6362
6181
|
if (!onStopAllTasks || isStopping) {
|
|
6363
6182
|
return;
|
|
6364
6183
|
}
|
|
@@ -6483,7 +6302,7 @@ var ToolSidebar = React72.forwardRef(
|
|
|
6483
6302
|
ToolSidebar.displayName = "ToolSidebar";
|
|
6484
6303
|
|
|
6485
6304
|
// src/components/chat/ToolPanelContainer.tsx
|
|
6486
|
-
import React73, { useCallback as
|
|
6305
|
+
import React73, { useCallback as useCallback20, useEffect as useEffect14, useRef as useRef13, useState as useState20 } from "react";
|
|
6487
6306
|
var ToolPanelContainer = React73.forwardRef(
|
|
6488
6307
|
({
|
|
6489
6308
|
topContent,
|
|
@@ -6495,21 +6314,21 @@ var ToolPanelContainer = React73.forwardRef(
|
|
|
6495
6314
|
initialTopPercent = 60,
|
|
6496
6315
|
...rest
|
|
6497
6316
|
}, ref) => {
|
|
6498
|
-
const [topPercent, setTopPercent] =
|
|
6499
|
-
const [isResizingHeight, setIsResizingHeight] =
|
|
6500
|
-
const containerRef =
|
|
6501
|
-
const lastY =
|
|
6317
|
+
const [topPercent, setTopPercent] = useState20(initialTopPercent);
|
|
6318
|
+
const [isResizingHeight, setIsResizingHeight] = useState20(false);
|
|
6319
|
+
const containerRef = useRef13(null);
|
|
6320
|
+
const lastY = useRef13(null);
|
|
6502
6321
|
const hasBoth = topContent !== null && bottomContent !== null;
|
|
6503
|
-
const startHeightResize =
|
|
6322
|
+
const startHeightResize = useCallback20((e) => {
|
|
6504
6323
|
e.preventDefault();
|
|
6505
6324
|
setIsResizingHeight(true);
|
|
6506
6325
|
lastY.current = e.clientY;
|
|
6507
6326
|
}, []);
|
|
6508
|
-
const stopHeightResize =
|
|
6327
|
+
const stopHeightResize = useCallback20(() => {
|
|
6509
6328
|
setIsResizingHeight(false);
|
|
6510
6329
|
lastY.current = null;
|
|
6511
6330
|
}, []);
|
|
6512
|
-
const resizeHeight =
|
|
6331
|
+
const resizeHeight = useCallback20(
|
|
6513
6332
|
(e) => {
|
|
6514
6333
|
if (!isResizingHeight || lastY.current === null || !containerRef.current) {
|
|
6515
6334
|
return;
|
|
@@ -6550,14 +6369,7 @@ var ToolPanelContainer = React73.forwardRef(
|
|
|
6550
6369
|
return /* @__PURE__ */ React73.createElement(
|
|
6551
6370
|
"div",
|
|
6552
6371
|
{
|
|
6553
|
-
ref: (
|
|
6554
|
-
containerRef.current = node;
|
|
6555
|
-
if (typeof ref === "function") {
|
|
6556
|
-
ref(node);
|
|
6557
|
-
} else if (ref) {
|
|
6558
|
-
ref.current = node;
|
|
6559
|
-
}
|
|
6560
|
-
},
|
|
6372
|
+
ref: composeRefs(containerRef, ref),
|
|
6561
6373
|
className: cx(
|
|
6562
6374
|
"h-full bg-charcoal/50 flex flex-col relative shrink-0",
|
|
6563
6375
|
side === "left" ? "border-r border-ash/40" : "border-l border-ash/40",
|
|
@@ -6611,26 +6423,26 @@ var ToolPanelContainer = React73.forwardRef(
|
|
|
6611
6423
|
ToolPanelContainer.displayName = "ToolPanelContainer";
|
|
6612
6424
|
|
|
6613
6425
|
// src/components/chat/hooks/useResizable.ts
|
|
6614
|
-
import { useCallback as
|
|
6426
|
+
import { useCallback as useCallback21, useEffect as useEffect15, useRef as useRef14, useState as useState21 } from "react";
|
|
6615
6427
|
function useResizable({
|
|
6616
6428
|
initialWidthPercent,
|
|
6617
6429
|
minWidthPercent,
|
|
6618
6430
|
maxWidthPercent,
|
|
6619
6431
|
direction
|
|
6620
6432
|
}) {
|
|
6621
|
-
const [widthPercent, setWidthPercent] =
|
|
6622
|
-
const [isResizing, setIsResizing] =
|
|
6623
|
-
const lastX =
|
|
6624
|
-
const startResizing =
|
|
6433
|
+
const [widthPercent, setWidthPercent] = useState21(initialWidthPercent);
|
|
6434
|
+
const [isResizing, setIsResizing] = useState21(false);
|
|
6435
|
+
const lastX = useRef14(null);
|
|
6436
|
+
const startResizing = useCallback21((e) => {
|
|
6625
6437
|
e.preventDefault();
|
|
6626
6438
|
setIsResizing(true);
|
|
6627
6439
|
lastX.current = e.clientX;
|
|
6628
6440
|
}, []);
|
|
6629
|
-
const stopResizing =
|
|
6441
|
+
const stopResizing = useCallback21(() => {
|
|
6630
6442
|
setIsResizing(false);
|
|
6631
6443
|
lastX.current = null;
|
|
6632
6444
|
}, []);
|
|
6633
|
-
const resize =
|
|
6445
|
+
const resize = useCallback21(
|
|
6634
6446
|
(e) => {
|
|
6635
6447
|
if (!isResizing || lastX.current === null) {
|
|
6636
6448
|
return;
|
|
@@ -6707,15 +6519,15 @@ var ChatInterface = React74.forwardRef(
|
|
|
6707
6519
|
className,
|
|
6708
6520
|
...rest
|
|
6709
6521
|
}, ref) => {
|
|
6710
|
-
const prevArtifactNodesRef =
|
|
6711
|
-
const prevTasksRef =
|
|
6712
|
-
const [internalTools, setInternalTools] =
|
|
6522
|
+
const prevArtifactNodesRef = useRef15([]);
|
|
6523
|
+
const prevTasksRef = useRef15([]);
|
|
6524
|
+
const [internalTools, setInternalTools] = useState22({
|
|
6713
6525
|
"top-left": "history",
|
|
6714
6526
|
"bottom-left": null,
|
|
6715
6527
|
"top-right": null,
|
|
6716
6528
|
"bottom-right": null
|
|
6717
6529
|
});
|
|
6718
|
-
const dismissedToolsRef =
|
|
6530
|
+
const dismissedToolsRef = useRef15(/* @__PURE__ */ new Set());
|
|
6719
6531
|
const isPanelControlled = isArtifactsPanelOpen !== void 0;
|
|
6720
6532
|
const activeTools = useMemo5(() => {
|
|
6721
6533
|
if (isPanelControlled) {
|
|
@@ -6761,7 +6573,7 @@ var ChatInterface = React74.forwardRef(
|
|
|
6761
6573
|
const external = externalTools.map(({ content: _content, ...def }) => def);
|
|
6762
6574
|
return [...builtIn, ...external];
|
|
6763
6575
|
}, [allSettled, externalTools]);
|
|
6764
|
-
const toggleTool =
|
|
6576
|
+
const toggleTool = useCallback22((toolId) => {
|
|
6765
6577
|
const toolDef = allToolDefinitions.find((t) => t.id === toolId);
|
|
6766
6578
|
if (!toolDef) {
|
|
6767
6579
|
return;
|
|
@@ -6830,7 +6642,7 @@ var ChatInterface = React74.forwardRef(
|
|
|
6830
6642
|
prevArtifactNodesRef.current = nodes;
|
|
6831
6643
|
prevTasksRef.current = tasks;
|
|
6832
6644
|
}, [artifactNodes, tasks, isPanelControlled]);
|
|
6833
|
-
const handleBranchSwitch =
|
|
6645
|
+
const handleBranchSwitch = useCallback22(
|
|
6834
6646
|
(nodeId, direction) => {
|
|
6835
6647
|
if (!isTreeMode || !conversationTree || !onTreeChange) {
|
|
6836
6648
|
return;
|
|
@@ -6883,7 +6695,7 @@ var ChatInterface = React74.forwardRef(
|
|
|
6883
6695
|
onRetryMessage,
|
|
6884
6696
|
handleBranchSwitch
|
|
6885
6697
|
]);
|
|
6886
|
-
const handleSubmit =
|
|
6698
|
+
const handleSubmit = useCallback22(
|
|
6887
6699
|
(message, attachments) => {
|
|
6888
6700
|
onMessageSubmit?.(message, attachments);
|
|
6889
6701
|
},
|
|
@@ -7038,8 +6850,8 @@ var ChatInterface = React74.forwardRef(
|
|
|
7038
6850
|
ChatInterface.displayName = "ChatInterface";
|
|
7039
6851
|
|
|
7040
6852
|
// src/components/chat/MessageActions.tsx
|
|
7041
|
-
import React75, { useCallback as
|
|
7042
|
-
import { Check as
|
|
6853
|
+
import React75, { useCallback as useCallback23, useState as useState23 } from "react";
|
|
6854
|
+
import { Check as Check4, Copy as Copy2, Pencil as Pencil3, RotateCcw as RotateCcw2, Send as Send3, X as X7 } from "lucide-react";
|
|
7043
6855
|
var ActionButton2 = ({ onClick, label, children, className, disabled }) => /* @__PURE__ */ React75.createElement(
|
|
7044
6856
|
"button",
|
|
7045
6857
|
{
|
|
@@ -7068,12 +6880,12 @@ var MessageActions = React75.forwardRef(
|
|
|
7068
6880
|
className,
|
|
7069
6881
|
...rest
|
|
7070
6882
|
}, ref) => {
|
|
7071
|
-
const [localIsEditing, setLocalIsEditing] =
|
|
7072
|
-
const [localEditValue, setLocalEditValue] =
|
|
7073
|
-
const
|
|
6883
|
+
const [localIsEditing, setLocalIsEditing] = useState23(false);
|
|
6884
|
+
const [localEditValue, setLocalEditValue] = useState23(content);
|
|
6885
|
+
const { copied, copy } = useCopyToClipboard();
|
|
7074
6886
|
const isEditing = controlledIsEditing ?? localIsEditing;
|
|
7075
6887
|
const editValue = controlledEditValue ?? localEditValue;
|
|
7076
|
-
const setIsEditing =
|
|
6888
|
+
const setIsEditing = useCallback23(
|
|
7077
6889
|
(value) => {
|
|
7078
6890
|
if (onEditingChange) {
|
|
7079
6891
|
onEditingChange(value);
|
|
@@ -7083,41 +6895,28 @@ var MessageActions = React75.forwardRef(
|
|
|
7083
6895
|
},
|
|
7084
6896
|
[onEditingChange]
|
|
7085
6897
|
);
|
|
7086
|
-
const setEditValue =
|
|
6898
|
+
const setEditValue = useCallback23((value) => {
|
|
7087
6899
|
setLocalEditValue(value);
|
|
7088
6900
|
}, []);
|
|
7089
|
-
const handleCopy =
|
|
7090
|
-
|
|
7091
|
-
|
|
7092
|
-
|
|
7093
|
-
setTimeout(() => setCopied(false), 2e3);
|
|
7094
|
-
} catch {
|
|
7095
|
-
const textArea = document.createElement("textarea");
|
|
7096
|
-
textArea.value = content;
|
|
7097
|
-
document.body.appendChild(textArea);
|
|
7098
|
-
textArea.select();
|
|
7099
|
-
document.execCommand("copy");
|
|
7100
|
-
document.body.removeChild(textArea);
|
|
7101
|
-
setCopied(true);
|
|
7102
|
-
setTimeout(() => setCopied(false), 2e3);
|
|
7103
|
-
}
|
|
7104
|
-
}, [content]);
|
|
7105
|
-
const handleStartEdit = useCallback21(() => {
|
|
6901
|
+
const handleCopy = useCallback23(() => {
|
|
6902
|
+
void copy(content);
|
|
6903
|
+
}, [copy, content]);
|
|
6904
|
+
const handleStartEdit = useCallback23(() => {
|
|
7106
6905
|
setLocalEditValue(content);
|
|
7107
6906
|
setIsEditing(true);
|
|
7108
6907
|
}, [content, setIsEditing]);
|
|
7109
|
-
const handleCancelEdit =
|
|
6908
|
+
const handleCancelEdit = useCallback23(() => {
|
|
7110
6909
|
setIsEditing(false);
|
|
7111
6910
|
setLocalEditValue(content);
|
|
7112
6911
|
}, [content, setIsEditing]);
|
|
7113
|
-
const handleSubmitEdit =
|
|
6912
|
+
const handleSubmitEdit = useCallback23(() => {
|
|
7114
6913
|
const trimmed = editValue.trim();
|
|
7115
6914
|
if (trimmed && trimmed !== content) {
|
|
7116
6915
|
onEdit?.(trimmed);
|
|
7117
6916
|
}
|
|
7118
6917
|
setIsEditing(false);
|
|
7119
6918
|
}, [editValue, content, onEdit, setIsEditing]);
|
|
7120
|
-
const handleEditKeyDown =
|
|
6919
|
+
const handleEditKeyDown = useCallback23(
|
|
7121
6920
|
(e) => {
|
|
7122
6921
|
if (e.key === "Enter" && !e.shiftKey) {
|
|
7123
6922
|
e.preventDefault();
|
|
@@ -7160,7 +6959,7 @@ var MessageActions = React75.forwardRef(
|
|
|
7160
6959
|
label: "Cancel edit",
|
|
7161
6960
|
className: "text-silver/60 hover:text-error"
|
|
7162
6961
|
},
|
|
7163
|
-
/* @__PURE__ */ React75.createElement(
|
|
6962
|
+
/* @__PURE__ */ React75.createElement(X7, { className: "w-4 h-4" })
|
|
7164
6963
|
), /* @__PURE__ */ React75.createElement(
|
|
7165
6964
|
ActionButton2,
|
|
7166
6965
|
{
|
|
@@ -7169,7 +6968,7 @@ var MessageActions = React75.forwardRef(
|
|
|
7169
6968
|
className: "text-silver/60 hover:text-gold",
|
|
7170
6969
|
disabled: !editValue.trim() || editValue.trim() === content
|
|
7171
6970
|
},
|
|
7172
|
-
/* @__PURE__ */ React75.createElement(
|
|
6971
|
+
/* @__PURE__ */ React75.createElement(Send3, { className: "w-4 h-4" })
|
|
7173
6972
|
))
|
|
7174
6973
|
),
|
|
7175
6974
|
/* @__PURE__ */ React75.createElement("p", { className: "text-xs text-silver/50 mt-1" }, "Press Enter to submit, Esc to cancel. This will create a new branch.")
|
|
@@ -7186,9 +6985,9 @@ var MessageActions = React75.forwardRef(
|
|
|
7186
6985
|
),
|
|
7187
6986
|
...rest
|
|
7188
6987
|
},
|
|
7189
|
-
/* @__PURE__ */ React75.createElement(ActionButton2, { onClick: handleCopy, label: copied ? "Copied!" : "Copy message" }, copied ? /* @__PURE__ */ React75.createElement(
|
|
7190
|
-
isUser && onEdit && /* @__PURE__ */ React75.createElement(ActionButton2, { onClick: handleStartEdit, label: "Edit message" }, /* @__PURE__ */ React75.createElement(
|
|
7191
|
-
!isUser && onRetry && /* @__PURE__ */ React75.createElement(ActionButton2, { onClick: onRetry, label: "Regenerate response" }, /* @__PURE__ */ React75.createElement(
|
|
6988
|
+
/* @__PURE__ */ React75.createElement(ActionButton2, { onClick: handleCopy, label: copied ? "Copied!" : "Copy message" }, copied ? /* @__PURE__ */ React75.createElement(Check4, { className: "w-3.5 h-3.5 text-success" }) : /* @__PURE__ */ React75.createElement(Copy2, { className: "w-3.5 h-3.5" })),
|
|
6989
|
+
isUser && onEdit && /* @__PURE__ */ React75.createElement(ActionButton2, { onClick: handleStartEdit, label: "Edit message" }, /* @__PURE__ */ React75.createElement(Pencil3, { className: "w-3.5 h-3.5" })),
|
|
6990
|
+
!isUser && onRetry && /* @__PURE__ */ React75.createElement(ActionButton2, { onClick: onRetry, label: "Regenerate response" }, /* @__PURE__ */ React75.createElement(RotateCcw2, { className: "w-3.5 h-3.5" }))
|
|
7192
6991
|
);
|
|
7193
6992
|
}
|
|
7194
6993
|
);
|
|
@@ -7196,7 +6995,7 @@ MessageActions.displayName = "MessageActions";
|
|
|
7196
6995
|
|
|
7197
6996
|
// src/components/chat/BranchNavigator.tsx
|
|
7198
6997
|
import React76 from "react";
|
|
7199
|
-
import { ChevronLeft as
|
|
6998
|
+
import { ChevronLeft as ChevronLeft3, ChevronRight as ChevronRight4, GitBranch as GitBranch2 } from "lucide-react";
|
|
7200
6999
|
var BranchNavigator = React76.forwardRef(
|
|
7201
7000
|
({
|
|
7202
7001
|
current,
|
|
@@ -7228,7 +7027,7 @@ var BranchNavigator = React76.forwardRef(
|
|
|
7228
7027
|
"aria-label": "Branch navigation",
|
|
7229
7028
|
...rest
|
|
7230
7029
|
},
|
|
7231
|
-
showIcon && /* @__PURE__ */ React76.createElement(
|
|
7030
|
+
showIcon && /* @__PURE__ */ React76.createElement(GitBranch2, { className: cx(iconSize, "mr-0.5 text-silver/50"), "aria-hidden": "true" }),
|
|
7232
7031
|
/* @__PURE__ */ React76.createElement(
|
|
7233
7032
|
"button",
|
|
7234
7033
|
{
|
|
@@ -7242,7 +7041,7 @@ var BranchNavigator = React76.forwardRef(
|
|
|
7242
7041
|
),
|
|
7243
7042
|
"aria-label": "Previous branch"
|
|
7244
7043
|
},
|
|
7245
|
-
/* @__PURE__ */ React76.createElement(
|
|
7044
|
+
/* @__PURE__ */ React76.createElement(ChevronLeft3, { className: iconSize })
|
|
7246
7045
|
),
|
|
7247
7046
|
/* @__PURE__ */ React76.createElement("span", { className: cx(textSize, "tabular-nums min-w-6 text-center") }, current, "/", total),
|
|
7248
7047
|
/* @__PURE__ */ React76.createElement(
|
|
@@ -7258,7 +7057,7 @@ var BranchNavigator = React76.forwardRef(
|
|
|
7258
7057
|
),
|
|
7259
7058
|
"aria-label": "Next branch"
|
|
7260
7059
|
},
|
|
7261
|
-
/* @__PURE__ */ React76.createElement(
|
|
7060
|
+
/* @__PURE__ */ React76.createElement(ChevronRight4, { className: iconSize })
|
|
7262
7061
|
)
|
|
7263
7062
|
);
|
|
7264
7063
|
}
|
|
@@ -7476,14 +7275,11 @@ export {
|
|
|
7476
7275
|
addMessageToTree,
|
|
7477
7276
|
areAllTasksSettled,
|
|
7478
7277
|
createEmptyTree,
|
|
7479
|
-
createPreviewUrl,
|
|
7480
7278
|
generateId,
|
|
7481
7279
|
getActivePathMessages,
|
|
7482
7280
|
getSiblingInfo,
|
|
7483
7281
|
isBranchPoint,
|
|
7484
|
-
isImageFile,
|
|
7485
7282
|
messagesToTree,
|
|
7486
|
-
revokePreviewUrl,
|
|
7487
7283
|
switchBranch,
|
|
7488
7284
|
updateNodeContent,
|
|
7489
7285
|
useArtifactTreeNavigation,
|