@tangle-network/sandbox-ui 0.23.1 → 0.23.2
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.
|
@@ -17,7 +17,7 @@ import {
|
|
|
17
17
|
DropdownMenuSeparator,
|
|
18
18
|
DropdownMenuTrigger
|
|
19
19
|
} from "@tangle-network/ui/primitives";
|
|
20
|
-
import { Skeleton } from "@tangle-network/ui/primitives";
|
|
20
|
+
import { Skeleton, useTheme } from "@tangle-network/ui/primitives";
|
|
21
21
|
|
|
22
22
|
// src/dashboard/sidebar-context.tsx
|
|
23
23
|
import * as React from "react";
|
|
@@ -142,6 +142,41 @@ function LogOutIcon({ className }) {
|
|
|
142
142
|
/* @__PURE__ */ jsx2("line", { x1: "21", x2: "9", y1: "12", y2: "12" })
|
|
143
143
|
] });
|
|
144
144
|
}
|
|
145
|
+
function SunIcon({ className }) {
|
|
146
|
+
return /* @__PURE__ */ jsxs("svg", { xmlns: "http://www.w3.org/2000/svg", viewBox: "0 0 24 24", fill: "none", stroke: "currentColor", strokeWidth: "2", strokeLinecap: "round", strokeLinejoin: "round", className, children: [
|
|
147
|
+
/* @__PURE__ */ jsx2("title", { children: "Light mode icon" }),
|
|
148
|
+
/* @__PURE__ */ jsx2("circle", { cx: "12", cy: "12", r: "4" }),
|
|
149
|
+
/* @__PURE__ */ jsx2("path", { d: "M12 2v2M12 20v2M4.93 4.93l1.41 1.41M17.66 17.66l1.41 1.41M2 12h2M20 12h2M6.34 17.66l-1.41 1.41M19.07 4.93l-1.41 1.41" })
|
|
150
|
+
] });
|
|
151
|
+
}
|
|
152
|
+
function MoonIcon({ className }) {
|
|
153
|
+
return /* @__PURE__ */ jsxs("svg", { xmlns: "http://www.w3.org/2000/svg", viewBox: "0 0 24 24", fill: "none", stroke: "currentColor", strokeWidth: "2", strokeLinecap: "round", strokeLinejoin: "round", className, children: [
|
|
154
|
+
/* @__PURE__ */ jsx2("title", { children: "Dark mode icon" }),
|
|
155
|
+
/* @__PURE__ */ jsx2("path", { d: "M12 3a6 6 0 0 0 9 9 9 9 0 1 1-9-9Z" })
|
|
156
|
+
] });
|
|
157
|
+
}
|
|
158
|
+
function RailThemeToggle({ className }) {
|
|
159
|
+
const { theme, setTheme } = useTheme();
|
|
160
|
+
const [mounted, setMounted] = React2.useState(false);
|
|
161
|
+
React2.useEffect(() => setMounted(true), []);
|
|
162
|
+
const isDark = mounted && (theme === "dark" || theme === "system" && typeof window !== "undefined" && window.matchMedia("(prefers-color-scheme: dark)").matches);
|
|
163
|
+
return /* @__PURE__ */ jsx2(
|
|
164
|
+
"button",
|
|
165
|
+
{
|
|
166
|
+
type: "button",
|
|
167
|
+
onClick: () => setTheme(isDark ? "light" : "dark"),
|
|
168
|
+
"aria-label": "Toggle theme",
|
|
169
|
+
title: isDark ? "Switch to light mode" : "Switch to dark mode",
|
|
170
|
+
className: cn(
|
|
171
|
+
"flex h-9 w-9 shrink-0 items-center justify-center rounded-lg text-muted-foreground transition-colors",
|
|
172
|
+
"hover:bg-[var(--accent-surface-soft)] hover:text-[var(--accent-text)]",
|
|
173
|
+
"focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-primary",
|
|
174
|
+
className
|
|
175
|
+
),
|
|
176
|
+
children: isDark ? /* @__PURE__ */ jsx2(SunIcon, { className: "h-4 w-4" }) : /* @__PURE__ */ jsx2(MoonIcon, { className: "h-4 w-4" })
|
|
177
|
+
}
|
|
178
|
+
);
|
|
179
|
+
}
|
|
145
180
|
function Sidebar({ children, className, style }) {
|
|
146
181
|
const { panelOpen, hidden, hasPanels, railWidth } = useSidebar();
|
|
147
182
|
return /* @__PURE__ */ jsx2(
|
|
@@ -174,20 +209,20 @@ function SidebarRail({ children, className, wide = false }) {
|
|
|
174
209
|
);
|
|
175
210
|
}
|
|
176
211
|
function SidebarRailHeader({ children, className }) {
|
|
177
|
-
return /* @__PURE__ */ jsx2("div", { className: cn("flex h-14 items-center justify-center border-b border-border", className), children });
|
|
212
|
+
return /* @__PURE__ */ jsx2("div", { className: cn("flex h-14 shrink-0 items-center justify-center border-b border-border", className), children });
|
|
178
213
|
}
|
|
179
214
|
function SidebarRailNav({ children, className }) {
|
|
180
|
-
return /* @__PURE__ */ jsx2("nav", { className: cn("flex flex-col items-center gap-1 py-3 flex-1", className), children });
|
|
215
|
+
return /* @__PURE__ */ jsx2("nav", { className: cn("flex flex-col items-center gap-1 py-3 flex-1 min-h-0 overflow-y-auto", className), children });
|
|
181
216
|
}
|
|
182
217
|
function SidebarRailFooter({ children, className }) {
|
|
183
|
-
return /* @__PURE__ */ jsx2("div", { className: cn("flex flex-col items-center gap-1 pb-3", className), children });
|
|
218
|
+
return /* @__PURE__ */ jsx2("div", { className: cn("flex flex-col items-center gap-1 pb-3 shrink-0", className), children });
|
|
184
219
|
}
|
|
185
220
|
function RailSeparator({ className }) {
|
|
186
221
|
return /* @__PURE__ */ jsx2("div", { className: cn("my-2 h-px w-10 bg-[var(--md3-outline-variant)]", className) });
|
|
187
222
|
}
|
|
188
223
|
function RailButton({ icon: Icon, label, isActive, badge, onClick, className, showLabel, asChild, children }) {
|
|
189
224
|
const classes = cn(
|
|
190
|
-
"group relative flex items-center justify-center rounded-xl transition-all duration-200",
|
|
225
|
+
"group relative flex shrink-0 items-center justify-center rounded-xl transition-all duration-200",
|
|
191
226
|
showLabel ? "w-full justify-start px-3 h-11 gap-3" : "w-11 h-11 justify-center",
|
|
192
227
|
"hover:bg-[var(--accent-surface-soft)] hover:text-[var(--accent-text)]",
|
|
193
228
|
"active:scale-95",
|
|
@@ -289,13 +324,7 @@ function ProfileAvatar({
|
|
|
289
324
|
user?.avatarUrl && /* @__PURE__ */ jsx2(AvatarImage, { src: user.avatarUrl, alt: "" }),
|
|
290
325
|
/* @__PURE__ */ jsx2(AvatarFallback, { className: "text-[10px] bg-violet-500/20 text-violet-300", children: getInitials(user?.name, user?.email) })
|
|
291
326
|
] }),
|
|
292
|
-
showDetails && /* @__PURE__ */ jsx2("div", { className: "min-w-0 flex-1", children: isLoading ? /* @__PURE__ */
|
|
293
|
-
/* @__PURE__ */ jsx2(Skeleton, { className: "mb-1 h-3.5 w-20" }),
|
|
294
|
-
/* @__PURE__ */ jsx2(Skeleton, { className: "h-3 w-28" })
|
|
295
|
-
] }) : /* @__PURE__ */ jsxs(Fragment, { children: [
|
|
296
|
-
/* @__PURE__ */ jsx2("p", { className: "truncate text-sm font-medium text-foreground", children: user?.name ?? user?.email ?? "Not signed in" }),
|
|
297
|
-
user?.email && user?.name && /* @__PURE__ */ jsx2("p", { className: "truncate text-xs text-muted-foreground", children: user.email })
|
|
298
|
-
] }) })
|
|
327
|
+
showDetails && /* @__PURE__ */ jsx2("div", { className: "min-w-0 flex-1", children: isLoading ? /* @__PURE__ */ jsx2(Skeleton, { className: "h-3.5 w-24" }) : /* @__PURE__ */ jsx2("p", { className: "truncate text-sm font-medium text-foreground", children: user?.name ?? user?.email ?? "Not signed in" }) })
|
|
299
328
|
]
|
|
300
329
|
}
|
|
301
330
|
) }),
|
|
@@ -1562,6 +1591,7 @@ function SidebarLayoutInner({
|
|
|
1562
1591
|
onSettingsClick,
|
|
1563
1592
|
settingsHref,
|
|
1564
1593
|
profileMenuItems,
|
|
1594
|
+
showThemeToggle = false,
|
|
1565
1595
|
railFooter,
|
|
1566
1596
|
LinkComponent,
|
|
1567
1597
|
hideBelow,
|
|
@@ -1603,19 +1633,29 @@ function SidebarLayoutInner({
|
|
|
1603
1633
|
) }),
|
|
1604
1634
|
(railFooter !== void 0 || hasProfile) && /* @__PURE__ */ jsxs13(SidebarRailFooter, { className: cn("border-t border-border pt-2", railLabels && "items-stretch px-2"), children: [
|
|
1605
1635
|
railFooter,
|
|
1606
|
-
hasProfile &&
|
|
1607
|
-
|
|
1608
|
-
|
|
1609
|
-
|
|
1610
|
-
|
|
1611
|
-
|
|
1612
|
-
|
|
1613
|
-
|
|
1614
|
-
|
|
1615
|
-
|
|
1616
|
-
|
|
1617
|
-
|
|
1618
|
-
|
|
1636
|
+
hasProfile && (() => {
|
|
1637
|
+
const profile = /* @__PURE__ */ jsx14(
|
|
1638
|
+
ProfileAvatar,
|
|
1639
|
+
{
|
|
1640
|
+
user: user ?? void 0,
|
|
1641
|
+
isLoading,
|
|
1642
|
+
onLogout,
|
|
1643
|
+
onSettingsClick,
|
|
1644
|
+
settingsHref,
|
|
1645
|
+
showDetails: railLabels,
|
|
1646
|
+
LinkComponent: Link,
|
|
1647
|
+
children: profileMenuItems
|
|
1648
|
+
}
|
|
1649
|
+
);
|
|
1650
|
+
if (!showThemeToggle) return profile;
|
|
1651
|
+
return railLabels ? /* @__PURE__ */ jsxs13("div", { className: "flex w-full items-center gap-1", children: [
|
|
1652
|
+
/* @__PURE__ */ jsx14("div", { className: "min-w-0 flex-1", children: profile }),
|
|
1653
|
+
/* @__PURE__ */ jsx14(RailThemeToggle, {})
|
|
1654
|
+
] }) : /* @__PURE__ */ jsxs13("div", { className: "flex flex-col items-center gap-1", children: [
|
|
1655
|
+
/* @__PURE__ */ jsx14(RailThemeToggle, {}),
|
|
1656
|
+
profile
|
|
1657
|
+
] });
|
|
1658
|
+
})()
|
|
1619
1659
|
] })
|
|
1620
1660
|
] }),
|
|
1621
1661
|
panel != null && /* @__PURE__ */ jsx14(SidebarPanel, { children: panel })
|
|
@@ -2177,14 +2217,14 @@ function VariantList({
|
|
|
2177
2217
|
|
|
2178
2218
|
// src/dashboard/system-logs.tsx
|
|
2179
2219
|
import { Terminal as Terminal3 } from "lucide-react";
|
|
2180
|
-
import { useEffect as
|
|
2220
|
+
import { useEffect as useEffect3, useRef as useRef2, useState as useState5 } from "react";
|
|
2181
2221
|
import { jsx as jsx18, jsxs as jsxs17 } from "react/jsx-runtime";
|
|
2182
2222
|
function SystemLogsViewer({ apiUrl, token, className }) {
|
|
2183
|
-
const [logs, setLogs] =
|
|
2184
|
-
const [error, setError] =
|
|
2185
|
-
const [isFollowing, setIsFollowing] =
|
|
2223
|
+
const [logs, setLogs] = useState5([]);
|
|
2224
|
+
const [error, setError] = useState5(null);
|
|
2225
|
+
const [isFollowing, setIsFollowing] = useState5(true);
|
|
2186
2226
|
const scrollRef = useRef2(null);
|
|
2187
|
-
|
|
2227
|
+
useEffect3(() => {
|
|
2188
2228
|
let timeoutId;
|
|
2189
2229
|
let backoff = 2e3;
|
|
2190
2230
|
const controller = new AbortController();
|
|
@@ -2220,7 +2260,7 @@ function SystemLogsViewer({ apiUrl, token, className }) {
|
|
|
2220
2260
|
clearTimeout(timeoutId);
|
|
2221
2261
|
};
|
|
2222
2262
|
}, [apiUrl, token]);
|
|
2223
|
-
|
|
2263
|
+
useEffect3(() => {
|
|
2224
2264
|
if (isFollowing && scrollRef.current) {
|
|
2225
2265
|
scrollRef.current.scrollTop = scrollRef.current.scrollHeight;
|
|
2226
2266
|
}
|
package/dist/dashboard.d.ts
CHANGED
|
@@ -535,6 +535,8 @@ interface SidebarLayoutProps {
|
|
|
535
535
|
settingsHref?: string;
|
|
536
536
|
/** Extra items rendered before settings/logout in the profile menu. */
|
|
537
537
|
profileMenuItems?: React.ReactNode;
|
|
538
|
+
/** Render a light/dark theme switch in the profile menu (uses the shared `useTheme`). */
|
|
539
|
+
showThemeToggle?: boolean;
|
|
538
540
|
/** Extra content in the rail footer, above the profile avatar. */
|
|
539
541
|
railFooter?: React.ReactNode;
|
|
540
542
|
LinkComponent?: React.ComponentType<any>;
|
package/dist/dashboard.js
CHANGED
package/dist/index.js
CHANGED
package/package.json
CHANGED