@adea-ai/ui 0.10.8 → 0.10.9
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/.turbo/turbo-build.log +1 -0
- package/dist/components/account-drawer.d.ts +11 -0
- package/dist/components/account-drawer.js +20 -0
- package/dist/components/on-screen-controls.d.ts +7 -0
- package/dist/components/on-screen-controls.js +50 -0
- package/dist/components/prop-catalog.d.ts +49 -0
- package/dist/components/prop-catalog.js +342 -0
- package/dist/components/scene-settings.d.ts +33 -0
- package/dist/components/scene-settings.js +34 -0
- package/dist/components/theme-provider.d.ts +5 -0
- package/dist/components/theme-provider.js +8 -0
- package/dist/components/theme-toggle.d.ts +7 -0
- package/dist/components/theme-toggle.js +20 -0
- package/dist/components/ui/badge.d.ts +7 -0
- package/dist/components/ui/badge.js +33 -0
- package/dist/components/ui/button.d.ts +8 -0
- package/dist/components/ui/button.js +35 -0
- package/dist/components/ui/card.d.ts +4 -0
- package/dist/components/ui/card.js +9 -0
- package/dist/components/ui/dialog.d.ts +15 -0
- package/dist/components/ui/dialog.js +36 -0
- package/dist/components/ui/drawer.d.ts +16 -0
- package/dist/components/ui/drawer.js +75 -0
- package/dist/components/ui/dropdown-menu.d.ts +29 -0
- package/dist/components/ui/dropdown-menu.js +51 -0
- package/dist/components/ui/empty.d.ts +11 -0
- package/dist/components/ui/empty.js +33 -0
- package/dist/components/ui/field.d.ts +24 -0
- package/dist/components/ui/field.js +66 -0
- package/dist/components/ui/input.d.ts +3 -0
- package/dist/components/ui/input.js +7 -0
- package/dist/components/ui/label.d.ts +3 -0
- package/dist/components/ui/label.js +7 -0
- package/dist/components/ui/radio-group.d.ts +5 -0
- package/dist/components/ui/radio-group.js +12 -0
- package/dist/components/ui/separator.d.ts +3 -0
- package/dist/components/ui/separator.js +8 -0
- package/dist/components/ui/skeleton.d.ts +2 -0
- package/dist/components/ui/skeleton.js +6 -0
- package/dist/components/ui/spinner.d.ts +4 -0
- package/dist/components/ui/spinner.js +7 -0
- package/dist/components/ui/switch.d.ts +5 -0
- package/dist/components/ui/switch.js +8 -0
- package/dist/components/ui/tabs.d.ts +10 -0
- package/dist/components/ui/tabs.js +29 -0
- package/dist/components/ui/toggle-group.d.ts +11 -0
- package/dist/components/ui/toggle-group.js +24 -0
- package/dist/components/ui/toggle.d.ts +8 -0
- package/dist/components/ui/toggle.js +26 -0
- package/dist/components/ui/tooltip.d.ts +8 -0
- package/dist/components/ui/tooltip.js +18 -0
- package/dist/components/version-dialog.d.ts +25 -0
- package/dist/components/version-dialog.js +136 -0
- package/dist/components/workspace-brand.d.ts +5 -0
- package/dist/components/workspace-brand.js +4 -0
- package/dist/components/workspace-logo.d.ts +3 -0
- package/dist/components/workspace-logo.js +5 -0
- package/dist/index.d.ts +20 -0
- package/dist/index.js +20 -0
- package/dist/lib/utils.d.ts +2 -0
- package/dist/lib/utils.js +5 -0
- package/dist/lib/version-notes.d.ts +2 -0
- package/dist/lib/version-notes.js +31 -0
- package/package.json +1 -1
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
import { Tabs as TabsPrimitive } from "@base-ui/react/tabs";
|
|
2
|
+
import { type VariantProps } from "class-variance-authority";
|
|
3
|
+
declare function Tabs({ className, orientation, ...props }: TabsPrimitive.Root.Props): import("react").JSX.Element;
|
|
4
|
+
declare const tabsListVariants: (props?: ({
|
|
5
|
+
variant?: "default" | "line" | null | undefined;
|
|
6
|
+
} & import("class-variance-authority/types").ClassProp) | undefined) => string;
|
|
7
|
+
declare function TabsList({ className, variant, ...props }: TabsPrimitive.List.Props & VariantProps<typeof tabsListVariants>): import("react").JSX.Element;
|
|
8
|
+
declare function TabsTrigger({ className, ...props }: TabsPrimitive.Tab.Props): import("react").JSX.Element;
|
|
9
|
+
declare function TabsContent({ className, ...props }: TabsPrimitive.Panel.Props): import("react").JSX.Element;
|
|
10
|
+
export { Tabs, TabsList, TabsTrigger, TabsContent, tabsListVariants };
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
"use client";
|
|
2
|
+
import { jsx as _jsx } from "react/jsx-runtime";
|
|
3
|
+
import { Tabs as TabsPrimitive } from "@base-ui/react/tabs";
|
|
4
|
+
import { cva } from "class-variance-authority";
|
|
5
|
+
import { cn } from "#lib/utils";
|
|
6
|
+
function Tabs({ className, orientation = "horizontal", ...props }) {
|
|
7
|
+
return (_jsx(TabsPrimitive.Root, { "data-slot": "tabs", "data-orientation": orientation, className: cn("group/tabs flex gap-2 data-horizontal:flex-col", className), ...props }));
|
|
8
|
+
}
|
|
9
|
+
const tabsListVariants = cva("group/tabs-list inline-flex w-fit items-center justify-center rounded-lg p-[3px] text-muted-foreground group-data-horizontal/tabs:h-8 group-data-vertical/tabs:h-fit group-data-vertical/tabs:flex-col data-[variant=line]:rounded-none", {
|
|
10
|
+
variants: {
|
|
11
|
+
variant: {
|
|
12
|
+
default: "bg-muted",
|
|
13
|
+
line: "gap-1 bg-transparent",
|
|
14
|
+
},
|
|
15
|
+
},
|
|
16
|
+
defaultVariants: {
|
|
17
|
+
variant: "default",
|
|
18
|
+
},
|
|
19
|
+
});
|
|
20
|
+
function TabsList({ className, variant = "default", ...props }) {
|
|
21
|
+
return (_jsx(TabsPrimitive.List, { "data-slot": "tabs-list", "data-variant": variant, className: cn(tabsListVariants({ variant }), className), ...props }));
|
|
22
|
+
}
|
|
23
|
+
function TabsTrigger({ className, ...props }) {
|
|
24
|
+
return (_jsx(TabsPrimitive.Tab, { "data-slot": "tabs-trigger", className: cn("relative inline-flex h-[calc(100%-1px)] flex-1 items-center justify-center gap-1.5 rounded-md border border-transparent px-1.5 py-0.5 text-sm font-medium whitespace-nowrap text-foreground/60 transition-all group-data-vertical/tabs:w-full group-data-vertical/tabs:justify-start hover:text-foreground focus-visible:border-ring focus-visible:ring-[3px] focus-visible:ring-ring/50 focus-visible:outline-1 focus-visible:outline-ring disabled:pointer-events-none disabled:opacity-50 has-data-[icon=inline-end]:pr-1 has-data-[icon=inline-start]:pl-1 aria-disabled:pointer-events-none aria-disabled:opacity-50 dark:text-muted-foreground dark:hover:text-foreground group-data-[variant=default]/tabs-list:data-active:shadow-sm group-data-[variant=line]/tabs-list:data-active:shadow-none [&_svg]:pointer-events-none [&_svg]:shrink-0 [&_svg:not([class*='size-'])]:size-4", "group-data-[variant=line]/tabs-list:bg-transparent group-data-[variant=line]/tabs-list:data-active:bg-transparent dark:group-data-[variant=line]/tabs-list:data-active:border-transparent dark:group-data-[variant=line]/tabs-list:data-active:bg-transparent", "data-active:bg-background data-active:text-foreground dark:data-active:border-input dark:data-active:bg-input/30 dark:data-active:text-foreground", "after:absolute after:bg-foreground after:opacity-0 after:transition-opacity group-data-horizontal/tabs:after:inset-x-0 group-data-horizontal/tabs:after:bottom-[-5px] group-data-horizontal/tabs:after:h-0.5 group-data-vertical/tabs:after:inset-y-0 group-data-vertical/tabs:after:-right-1 group-data-vertical/tabs:after:w-0.5 group-data-[variant=line]/tabs-list:data-active:after:opacity-100", className), ...props }));
|
|
25
|
+
}
|
|
26
|
+
function TabsContent({ className, ...props }) {
|
|
27
|
+
return (_jsx(TabsPrimitive.Panel, { "data-slot": "tabs-content", className: cn("flex-1 text-sm outline-none", className), ...props }));
|
|
28
|
+
}
|
|
29
|
+
export { Tabs, TabsList, TabsTrigger, TabsContent, tabsListVariants };
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
import * as React from "react";
|
|
2
|
+
import { Toggle as TogglePrimitive } from "@base-ui/react/toggle";
|
|
3
|
+
import { ToggleGroup as ToggleGroupPrimitive } from "@base-ui/react/toggle-group";
|
|
4
|
+
import { type VariantProps } from "class-variance-authority";
|
|
5
|
+
import { toggleVariants } from "#components/ui/toggle";
|
|
6
|
+
declare function ToggleGroup({ className, variant, size, spacing, orientation, children, ...props }: ToggleGroupPrimitive.Props & VariantProps<typeof toggleVariants> & {
|
|
7
|
+
spacing?: number;
|
|
8
|
+
orientation?: "horizontal" | "vertical";
|
|
9
|
+
}): React.JSX.Element;
|
|
10
|
+
declare function ToggleGroupItem({ className, children, variant, size, ...props }: TogglePrimitive.Props & VariantProps<typeof toggleVariants>): React.JSX.Element;
|
|
11
|
+
export { ToggleGroup, ToggleGroupItem };
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
"use client";
|
|
2
|
+
import { jsx as _jsx } from "react/jsx-runtime";
|
|
3
|
+
import * as React from "react";
|
|
4
|
+
import { Toggle as TogglePrimitive } from "@base-ui/react/toggle";
|
|
5
|
+
import { ToggleGroup as ToggleGroupPrimitive } from "@base-ui/react/toggle-group";
|
|
6
|
+
import { cn } from "#lib/utils";
|
|
7
|
+
import { toggleVariants } from "#components/ui/toggle";
|
|
8
|
+
const ToggleGroupContext = React.createContext({
|
|
9
|
+
size: "default",
|
|
10
|
+
variant: "default",
|
|
11
|
+
spacing: 2,
|
|
12
|
+
orientation: "horizontal",
|
|
13
|
+
});
|
|
14
|
+
function ToggleGroup({ className, variant, size, spacing = 2, orientation = "horizontal", children, ...props }) {
|
|
15
|
+
return (_jsx(ToggleGroupPrimitive, { "data-slot": "toggle-group", "data-variant": variant, "data-size": size, "data-spacing": spacing, "data-orientation": orientation, style: { "--gap": spacing }, className: cn("group/toggle-group flex w-fit flex-row items-center gap-[--spacing(var(--gap))] rounded-lg data-[size=sm]:rounded-[min(var(--radius-md),10px)] data-vertical:flex-col data-vertical:items-stretch", className), ...props, children: _jsx(ToggleGroupContext.Provider, { value: { variant, size, spacing, orientation }, children: children }) }));
|
|
16
|
+
}
|
|
17
|
+
function ToggleGroupItem({ className, children, variant = "default", size = "default", ...props }) {
|
|
18
|
+
const context = React.useContext(ToggleGroupContext);
|
|
19
|
+
return (_jsx(TogglePrimitive, { "data-slot": "toggle-group-item", "data-variant": context.variant || variant, "data-size": context.size || size, "data-spacing": context.spacing, className: cn("shrink-0 group-data-[spacing=0]/toggle-group:rounded-none group-data-[spacing=0]/toggle-group:px-2 focus:z-10 focus-visible:z-10 group-data-[spacing=0]/toggle-group:has-data-[icon=inline-end]:pr-1.5 group-data-[spacing=0]/toggle-group:has-data-[icon=inline-start]:pl-1.5 group-data-horizontal/toggle-group:data-[spacing=0]:first:rounded-l-lg group-data-vertical/toggle-group:data-[spacing=0]:first:rounded-t-lg group-data-horizontal/toggle-group:data-[spacing=0]:last:rounded-r-lg group-data-vertical/toggle-group:data-[spacing=0]:last:rounded-b-lg group-data-horizontal/toggle-group:data-[spacing=0]:data-[variant=outline]:border-l-0 group-data-vertical/toggle-group:data-[spacing=0]:data-[variant=outline]:border-t-0 group-data-horizontal/toggle-group:data-[spacing=0]:data-[variant=outline]:first:border-l group-data-vertical/toggle-group:data-[spacing=0]:data-[variant=outline]:first:border-t", toggleVariants({
|
|
20
|
+
variant: context.variant || variant,
|
|
21
|
+
size: context.size || size,
|
|
22
|
+
}), className), ...props, children: children }));
|
|
23
|
+
}
|
|
24
|
+
export { ToggleGroup, ToggleGroupItem };
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
import { Toggle as TogglePrimitive } from "@base-ui/react/toggle";
|
|
2
|
+
import { type VariantProps } from "class-variance-authority";
|
|
3
|
+
declare const toggleVariants: (props?: ({
|
|
4
|
+
variant?: "default" | "outline" | null | undefined;
|
|
5
|
+
size?: "default" | "sm" | "lg" | null | undefined;
|
|
6
|
+
} & import("class-variance-authority/types").ClassProp) | undefined) => string;
|
|
7
|
+
declare function Toggle({ className, variant, size, ...props }: TogglePrimitive.Props & VariantProps<typeof toggleVariants>): import("react").JSX.Element;
|
|
8
|
+
export { Toggle, toggleVariants };
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
"use client";
|
|
2
|
+
import { jsx as _jsx } from "react/jsx-runtime";
|
|
3
|
+
import { Toggle as TogglePrimitive } from "@base-ui/react/toggle";
|
|
4
|
+
import { cva } from "class-variance-authority";
|
|
5
|
+
import { cn } from "#lib/utils";
|
|
6
|
+
const toggleVariants = cva("group/toggle inline-flex items-center justify-center gap-1 rounded-lg text-sm font-medium whitespace-nowrap transition-all outline-none hover:bg-muted hover:text-foreground focus-visible:border-ring focus-visible:ring-[3px] focus-visible:ring-ring/50 disabled:pointer-events-none disabled:opacity-50 aria-invalid:border-destructive aria-invalid:ring-destructive/20 aria-pressed:bg-muted data-[state=on]:bg-muted dark:aria-invalid:ring-destructive/40 [&_svg]:pointer-events-none [&_svg]:shrink-0 [&_svg:not([class*='size-'])]:size-4", {
|
|
7
|
+
variants: {
|
|
8
|
+
variant: {
|
|
9
|
+
default: "bg-transparent",
|
|
10
|
+
outline: "border border-input bg-transparent hover:bg-muted",
|
|
11
|
+
},
|
|
12
|
+
size: {
|
|
13
|
+
default: "h-8 min-w-8 px-2.5 has-data-[icon=inline-end]:pr-2 has-data-[icon=inline-start]:pl-2",
|
|
14
|
+
sm: "h-7 min-w-7 rounded-[min(var(--radius-md),12px)] px-2.5 text-[0.8rem] has-data-[icon=inline-end]:pr-1.5 has-data-[icon=inline-start]:pl-1.5 [&_svg:not([class*='size-'])]:size-3.5",
|
|
15
|
+
lg: "h-9 min-w-9 px-2.5 has-data-[icon=inline-end]:pr-2 has-data-[icon=inline-start]:pl-2",
|
|
16
|
+
},
|
|
17
|
+
},
|
|
18
|
+
defaultVariants: {
|
|
19
|
+
variant: "default",
|
|
20
|
+
size: "default",
|
|
21
|
+
},
|
|
22
|
+
});
|
|
23
|
+
function Toggle({ className, variant = "default", size = "default", ...props }) {
|
|
24
|
+
return (_jsx(TogglePrimitive, { "data-slot": "toggle", className: cn(toggleVariants({ variant, size, className })), ...props }));
|
|
25
|
+
}
|
|
26
|
+
export { Toggle, toggleVariants };
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
import * as React from "react";
|
|
2
|
+
import { Tooltip as TooltipPrimitive } from "@base-ui/react/tooltip";
|
|
3
|
+
declare const TOOLTIP_DELAY = 200;
|
|
4
|
+
declare function TooltipProvider({ delay, ...props }: TooltipPrimitive.Provider.Props): React.JSX.Element;
|
|
5
|
+
declare function Tooltip({ ...props }: TooltipPrimitive.Root.Props): React.JSX.Element;
|
|
6
|
+
declare function TooltipTrigger({ ...props }: TooltipPrimitive.Trigger.Props): React.JSX.Element;
|
|
7
|
+
declare function TooltipContent({ className, side, sideOffset, align, alignOffset, children, ...props }: TooltipPrimitive.Popup.Props & Pick<TooltipPrimitive.Positioner.Props, "align" | "alignOffset" | "side" | "sideOffset">): React.JSX.Element;
|
|
8
|
+
export { Tooltip, TooltipTrigger, TooltipContent, TooltipProvider, TOOLTIP_DELAY };
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
"use client";
|
|
2
|
+
import { jsx as _jsx } from "react/jsx-runtime";
|
|
3
|
+
import { Tooltip as TooltipPrimitive } from "@base-ui/react/tooltip";
|
|
4
|
+
import { cn } from "#lib/utils";
|
|
5
|
+
const TOOLTIP_DELAY = 200;
|
|
6
|
+
function TooltipProvider({ delay = TOOLTIP_DELAY, ...props }) {
|
|
7
|
+
return _jsx(TooltipPrimitive.Provider, { "data-slot": "tooltip-provider", delay: delay, ...props });
|
|
8
|
+
}
|
|
9
|
+
function Tooltip({ ...props }) {
|
|
10
|
+
return _jsx(TooltipPrimitive.Root, { "data-slot": "tooltip", ...props });
|
|
11
|
+
}
|
|
12
|
+
function TooltipTrigger({ ...props }) {
|
|
13
|
+
return _jsx(TooltipPrimitive.Trigger, { "data-slot": "tooltip-trigger", ...props });
|
|
14
|
+
}
|
|
15
|
+
function TooltipContent({ className, side = "top", sideOffset = 4, align, alignOffset, children, ...props }) {
|
|
16
|
+
return (_jsx(TooltipPrimitive.Portal, { children: _jsx(TooltipPrimitive.Positioner, { className: "isolate z-[160] outline-none", align: align, alignOffset: alignOffset, side: side, sideOffset: sideOffset, children: _jsx(TooltipPrimitive.Popup, { "data-slot": "tooltip-content", className: cn("max-w-72 rounded-md bg-popover px-2.5 py-1.5 text-sm leading-5 text-popover-foreground shadow-md ring-1 ring-foreground/10", className), ...props, children: children }) }) }));
|
|
17
|
+
}
|
|
18
|
+
export { Tooltip, TooltipTrigger, TooltipContent, TooltipProvider, TOOLTIP_DELAY };
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
export type SharedDesktopUpdate = Readonly<{
|
|
2
|
+
available_version: string | null;
|
|
3
|
+
changelog: string;
|
|
4
|
+
current_version: string;
|
|
5
|
+
downloaded_bytes: number;
|
|
6
|
+
error: string | null;
|
|
7
|
+
github_url: string;
|
|
8
|
+
phase: "idle" | "checking" | "current" | "available" | "downloading" | "installing" | "installed" | "failed";
|
|
9
|
+
release_date: string | null;
|
|
10
|
+
release_notes: string | null;
|
|
11
|
+
restart_required: boolean;
|
|
12
|
+
total_bytes: number | null;
|
|
13
|
+
}>;
|
|
14
|
+
export type VersionDialogAdapter = Readonly<{
|
|
15
|
+
check(): Promise<SharedDesktopUpdate>;
|
|
16
|
+
getStatus(): Promise<SharedDesktopUpdate>;
|
|
17
|
+
install(expectedVersion: string): Promise<SharedDesktopUpdate>;
|
|
18
|
+
isDesktopRuntime(): boolean;
|
|
19
|
+
}>;
|
|
20
|
+
export declare function VersionDialog({ adapter, fallbackVersion, onOpenChange, open: controlledOpen, }: Readonly<{
|
|
21
|
+
adapter: VersionDialogAdapter;
|
|
22
|
+
fallbackVersion?: string;
|
|
23
|
+
onOpenChange?: (open: boolean) => void;
|
|
24
|
+
open?: boolean;
|
|
25
|
+
}>): import("react").JSX.Element;
|
|
@@ -0,0 +1,136 @@
|
|
|
1
|
+
"use client";
|
|
2
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
3
|
+
import { useCallback, useEffect, useMemo, useState } from "react";
|
|
4
|
+
import { Check, Download, ExternalLink, FileText, LoaderCircle, RefreshCw, Sparkles, } from "lucide-react";
|
|
5
|
+
import { formatReleaseDate, plainTextFromMarkdown } from "#lib/version-notes";
|
|
6
|
+
import { Button } from "#components/ui/button";
|
|
7
|
+
import { Dialog, DialogClose, DialogContent, DialogDescription, DialogFooter, DialogHeader, DialogTitle, DialogTrigger, } from "#components/ui/dialog";
|
|
8
|
+
function errorMessage(caught, fallback) {
|
|
9
|
+
if (caught instanceof Error && caught.message)
|
|
10
|
+
return caught.message;
|
|
11
|
+
if (typeof caught === "string" && caught)
|
|
12
|
+
return caught;
|
|
13
|
+
return fallback;
|
|
14
|
+
}
|
|
15
|
+
function phaseLabel(update, fallbackVersion) {
|
|
16
|
+
if (!update)
|
|
17
|
+
return `Agent HQ v${fallbackVersion}`;
|
|
18
|
+
if (update.phase === "checking")
|
|
19
|
+
return "Checking for updates…";
|
|
20
|
+
if (update.phase === "available" && update.available_version) {
|
|
21
|
+
return `Update v${update.available_version} available`;
|
|
22
|
+
}
|
|
23
|
+
if (update.phase === "downloading" || update.phase === "installing") {
|
|
24
|
+
return "Installing update…";
|
|
25
|
+
}
|
|
26
|
+
if (update.phase === "failed")
|
|
27
|
+
return `Version ${update.current_version} · Retry`;
|
|
28
|
+
return `Agent HQ v${update.current_version || fallbackVersion}`;
|
|
29
|
+
}
|
|
30
|
+
function isUpdateBusy(update) {
|
|
31
|
+
return (update?.phase === "checking" ||
|
|
32
|
+
update?.phase === "downloading" ||
|
|
33
|
+
update?.phase === "installing");
|
|
34
|
+
}
|
|
35
|
+
export function VersionDialog({ adapter, fallbackVersion = "0.1.0", onOpenChange, open: controlledOpen, }) {
|
|
36
|
+
const [uncontrolledOpen, setUncontrolledOpen] = useState(false);
|
|
37
|
+
const open = controlledOpen ?? uncontrolledOpen;
|
|
38
|
+
const setOpen = useCallback((nextOpen) => {
|
|
39
|
+
if (controlledOpen === undefined)
|
|
40
|
+
setUncontrolledOpen(nextOpen);
|
|
41
|
+
onOpenChange?.(nextOpen);
|
|
42
|
+
}, [controlledOpen, onOpenChange]);
|
|
43
|
+
const [desktopRuntime, setDesktopRuntime] = useState(false);
|
|
44
|
+
const [update, setUpdate] = useState(null);
|
|
45
|
+
const [busy, setBusy] = useState(false);
|
|
46
|
+
const [error, setError] = useState("");
|
|
47
|
+
useEffect(() => setDesktopRuntime(adapter.isDesktopRuntime()), [adapter]);
|
|
48
|
+
const loadCurrentStatus = useCallback(async () => {
|
|
49
|
+
if (!desktopRuntime)
|
|
50
|
+
return;
|
|
51
|
+
try {
|
|
52
|
+
setUpdate(await adapter.getStatus());
|
|
53
|
+
}
|
|
54
|
+
catch (caught) {
|
|
55
|
+
setError(errorMessage(caught, "Version status is unavailable"));
|
|
56
|
+
}
|
|
57
|
+
}, [adapter, desktopRuntime]);
|
|
58
|
+
useEffect(() => {
|
|
59
|
+
if (desktopRuntime)
|
|
60
|
+
void loadCurrentStatus();
|
|
61
|
+
}, [desktopRuntime, loadCurrentStatus]);
|
|
62
|
+
const checkForUpdates = useCallback(async () => {
|
|
63
|
+
if (!desktopRuntime) {
|
|
64
|
+
setError("Update checks are available from the desktop app.");
|
|
65
|
+
return;
|
|
66
|
+
}
|
|
67
|
+
setBusy(true);
|
|
68
|
+
setError("");
|
|
69
|
+
try {
|
|
70
|
+
setUpdate(await adapter.check());
|
|
71
|
+
}
|
|
72
|
+
catch (caught) {
|
|
73
|
+
setError(errorMessage(caught, "Could not check for updates"));
|
|
74
|
+
await loadCurrentStatus();
|
|
75
|
+
}
|
|
76
|
+
finally {
|
|
77
|
+
setBusy(false);
|
|
78
|
+
}
|
|
79
|
+
}, [adapter, desktopRuntime, loadCurrentStatus]);
|
|
80
|
+
useEffect(() => {
|
|
81
|
+
if (!open || !desktopRuntime)
|
|
82
|
+
return;
|
|
83
|
+
let active = true;
|
|
84
|
+
setError("");
|
|
85
|
+
setBusy(true);
|
|
86
|
+
void (async () => {
|
|
87
|
+
try {
|
|
88
|
+
const current = await adapter.getStatus();
|
|
89
|
+
if (!active)
|
|
90
|
+
return;
|
|
91
|
+
setUpdate(current);
|
|
92
|
+
const checked = await adapter.check();
|
|
93
|
+
if (active)
|
|
94
|
+
setUpdate(checked);
|
|
95
|
+
}
|
|
96
|
+
catch (caught) {
|
|
97
|
+
if (active)
|
|
98
|
+
setError(errorMessage(caught, "Could not check for updates"));
|
|
99
|
+
}
|
|
100
|
+
finally {
|
|
101
|
+
if (active)
|
|
102
|
+
setBusy(false);
|
|
103
|
+
}
|
|
104
|
+
})();
|
|
105
|
+
return () => {
|
|
106
|
+
active = false;
|
|
107
|
+
};
|
|
108
|
+
}, [adapter, desktopRuntime, open]);
|
|
109
|
+
const install = async () => {
|
|
110
|
+
const version = update?.available_version;
|
|
111
|
+
if (!version)
|
|
112
|
+
return;
|
|
113
|
+
setBusy(true);
|
|
114
|
+
setError("");
|
|
115
|
+
try {
|
|
116
|
+
setUpdate(await adapter.install(version));
|
|
117
|
+
}
|
|
118
|
+
catch (caught) {
|
|
119
|
+
setError(errorMessage(caught, "Update installation failed"));
|
|
120
|
+
await loadCurrentStatus();
|
|
121
|
+
}
|
|
122
|
+
finally {
|
|
123
|
+
setBusy(false);
|
|
124
|
+
}
|
|
125
|
+
};
|
|
126
|
+
const currentChangelog = useMemo(() => plainTextFromMarkdown(update?.changelog || "Changelog is loading…"), [update?.changelog]);
|
|
127
|
+
const releaseNotes = update?.release_notes ? plainTextFromMarkdown(update.release_notes) : "";
|
|
128
|
+
const busyFromSnapshot = isUpdateBusy(update);
|
|
129
|
+
return (_jsxs(Dialog, { open: open, onOpenChange: setOpen, children: [controlledOpen === undefined ? (_jsxs(DialogTrigger, { render: _jsx(Button, { type: "button", variant: "ghost", size: "sm", "aria-label": "Open version and updates dialog", "aria-haspopup": "dialog", onClick: () => setOpen(true) }), children: [update?.phase === "available" ? (_jsx(Sparkles, { "aria-hidden": "true" })) : (_jsx(FileText, { "aria-hidden": "true" })), phaseLabel(update, fallbackVersion)] })) : null, _jsxs(DialogContent, { className: "max-w-3xl", children: [_jsx(DialogHeader, { children: _jsxs("div", { className: "flex items-center gap-3", children: [_jsx("span", { className: "flex size-10 items-center justify-center rounded-xl bg-primary text-primary-foreground", children: _jsx(Sparkles, { className: "size-5", "aria-hidden": "true" }) }), _jsxs("div", { children: [_jsx(DialogTitle, { children: "Version & updates" }), _jsx(DialogDescription, { children: "Keep Agent HQ current and review what changed in each release." })] })] }) }), _jsxs("div", { className: "min-h-0 space-y-5 overflow-y-auto p-6", children: [_jsx("section", { className: "rounded-xl border bg-background/45 p-4", "aria-label": "Version status", children: _jsxs("div", { className: "flex flex-wrap items-start justify-between gap-4", children: [_jsxs("div", { className: "space-y-1", children: [_jsx("p", { className: "text-xs font-semibold uppercase tracking-[0.14em] text-muted-foreground", children: "Installed version" }), _jsxs("p", { className: "text-xl font-semibold tracking-tight", children: ["v", update?.current_version || fallbackVersion] }), _jsx("p", { className: "text-sm text-muted-foreground", children: update?.phase === "current"
|
|
130
|
+
? "You are running the latest desktop release."
|
|
131
|
+
: update?.phase === "available" && update.available_version
|
|
132
|
+
? `A newer desktop release, v${update.available_version}, is ready.`
|
|
133
|
+
: desktopRuntime
|
|
134
|
+
? "Check the release channel for the latest signed build."
|
|
135
|
+
: "Open this dialog inside the desktop app to check for updates." })] }), _jsxs(Button, { type: "button", variant: "outline", size: "sm", disabled: !desktopRuntime || busy || busyFromSnapshot, onClick: () => void checkForUpdates(), children: [busy || busyFromSnapshot ? (_jsx(LoaderCircle, { className: "animate-spin", "aria-hidden": "true" })) : (_jsx(RefreshCw, { "aria-hidden": "true" })), "Check latest version"] })] }) }), update?.phase === "available" && update.available_version ? (_jsx("section", { className: "rounded-xl border border-primary/35 bg-primary/8 p-4", "aria-label": "Available update", children: _jsxs("div", { className: "flex flex-wrap items-start justify-between gap-4", children: [_jsxs("div", { className: "space-y-1", children: [_jsxs("p", { className: "flex items-center gap-2 text-sm font-semibold", children: [_jsx(Sparkles, { className: "size-4 text-primary", "aria-hidden": "true" }), "Version ", update.available_version, " is ready"] }), _jsx("p", { className: "text-sm text-muted-foreground", children: "The signed installer will be verified before Agent HQ restarts." }), formatReleaseDate(update.release_date) ? (_jsxs("p", { className: "text-xs text-muted-foreground", children: ["Released ", formatReleaseDate(update.release_date)] })) : null] }), _jsxs(Button, { type: "button", size: "sm", disabled: busy || busyFromSnapshot, onClick: () => void install(), children: [busy || busyFromSnapshot ? (_jsx(LoaderCircle, { className: "animate-spin", "aria-hidden": "true" })) : (_jsx(Download, { "aria-hidden": "true" })), "Install and restart"] })] }) })) : null, update?.phase === "current" ? (_jsxs("p", { className: "flex items-center gap-2 text-sm text-emerald-700 dark:text-emerald-300", role: "status", children: [_jsx(Check, { className: "size-4", "aria-hidden": "true" }), "Agent HQ is up to date."] })) : null, error ? (_jsx("p", { className: "rounded-lg border border-destructive/35 bg-destructive/8 px-3 py-2 text-sm text-destructive", role: "alert", children: error })) : null, releaseNotes ? (_jsxs("section", { className: "space-y-2", "aria-labelledby": "agent-hq-release-notes", children: [_jsxs("div", { children: [_jsx("h2", { id: "agent-hq-release-notes", className: "text-sm font-semibold", children: "What changed in this release" }), _jsx("p", { className: "text-xs text-muted-foreground", children: "Release notes are shown as readable text." })] }), _jsx("div", { className: "max-h-52 overflow-y-auto whitespace-pre-wrap rounded-xl border bg-background/45 p-4 font-mono text-xs leading-5 text-muted-foreground", children: releaseNotes })] })) : null, _jsxs("section", { className: "space-y-2", "aria-labelledby": "agent-hq-changelog", children: [_jsxs("div", { children: [_jsx("h2", { id: "agent-hq-changelog", className: "text-sm font-semibold", children: "Installed changelog" }), _jsx("p", { className: "text-xs text-muted-foreground", children: "A plain-text history of the installed channel." })] }), _jsx("div", { className: "max-h-72 overflow-y-auto whitespace-pre-wrap rounded-xl border bg-background/45 p-4 font-mono text-xs leading-5 text-muted-foreground", children: currentChangelog })] })] }), _jsxs(DialogFooter, { children: [update?.github_url ? (_jsxs(Button, { type: "button", variant: "ghost", size: "sm", onClick: () => window.open(update.github_url, "_blank", "noopener,noreferrer"), children: [_jsx(ExternalLink, { "aria-hidden": "true" }), "View releases"] })) : null, _jsx(DialogClose, { render: _jsx(Button, { type: "button", variant: "outline", size: "sm" }), children: "Close" })] })] })] }));
|
|
136
|
+
}
|
|
@@ -0,0 +1,4 @@
|
|
|
1
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
2
|
+
export function WorkspaceBrand({ title, eyebrow = "AGENT OPERATIONS" }) {
|
|
3
|
+
return (_jsxs("div", { className: "workspace-brand", children: [_jsx("div", { className: "workspace-brand__mark", "aria-hidden": "true", children: _jsx("span", { children: "HQ" }) }), _jsxs("div", { children: [_jsx("p", { className: "workspace-eyebrow", children: eyebrow }), _jsx("h1", { children: title })] })] }));
|
|
4
|
+
}
|
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
2
|
+
/** The canonical Agent HQ mark used by web, desktop, and dialogs. */
|
|
3
|
+
export function WorkspaceLogo(props) {
|
|
4
|
+
return (_jsxs("svg", { viewBox: "0 0 64 64", role: "img", "aria-label": "Agent HQ", ...props, children: [_jsx("rect", { width: "64", height: "64", rx: "16", fill: "#111827" }), _jsx("path", { d: "M10 16h7v13h9V16h7v32h-7V36h-9v12h-7z", fill: "#f8fafc" }), _jsx("path", { d: "M45 16c-7.18 0-13 6-13 16s5.82 16 13 16c7.18 0 13-6 13-16s-5.82-16-13-16Zm0 7c3.42 0 6 3.46 6 9s-2.58 9-6 9-6-3.46-6-9 2.58-9 6-9Z", fill: "#f8fafc", fillRule: "evenodd" }), _jsx("path", { d: "m45 35 11 11-4 4-11-11z", fill: "#f8fafc" })] }));
|
|
5
|
+
}
|
package/dist/index.d.ts
ADDED
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
export { Button, buttonVariants } from "./components/ui/button";
|
|
2
|
+
export { Switch } from "./components/ui/switch";
|
|
3
|
+
export { Toggle } from "./components/ui/toggle";
|
|
4
|
+
export { ToggleGroup, ToggleGroupItem } from "./components/ui/toggle-group";
|
|
5
|
+
export { RadioGroup, RadioGroupItem } from "./components/ui/radio-group";
|
|
6
|
+
export { ThemeToggle } from "./components/theme-toggle";
|
|
7
|
+
export { ThemeProvider } from "./components/theme-provider";
|
|
8
|
+
export { Drawer, DrawerClose, DrawerContent, DrawerDescription, DrawerFooter, DrawerHeader, DrawerOverlay, DrawerPortal, DrawerSwipeHandle, DrawerTitle, DrawerTrigger, } from "./components/ui/drawer";
|
|
9
|
+
export { AccountDrawer, type AccountDrawerProps } from "./components/account-drawer";
|
|
10
|
+
export { WorkspaceBrand, type WorkspaceBrandProps } from "./components/workspace-brand";
|
|
11
|
+
export { WorkspaceLogo } from "./components/workspace-logo";
|
|
12
|
+
export { OnScreenControls } from "./components/on-screen-controls";
|
|
13
|
+
export { SceneSettings, type SceneSettingsProps } from "./components/scene-settings";
|
|
14
|
+
export { VersionDialog, type SharedDesktopUpdate, type VersionDialogAdapter, } from "./components/version-dialog";
|
|
15
|
+
export { Tooltip, TooltipContent, TooltipProvider, TooltipTrigger } from "./components/ui/tooltip";
|
|
16
|
+
export { Card, CardContent } from "./components/ui/card";
|
|
17
|
+
export { Spinner } from "./components/ui/spinner";
|
|
18
|
+
export { Dialog, DialogClose, DialogContent, DialogDescription, DialogFooter, DialogHeader, DialogOverlay, DialogPortal, DialogTitle, DialogTrigger, } from "./components/ui/dialog";
|
|
19
|
+
export { ModelThumbnail, PropCatalog, defaultPropCatalogCategories, getSharedLoader, type PropCatalogCategory, type PropCatalogItem, type PropCatalogProps, } from "./components/prop-catalog";
|
|
20
|
+
export { cn } from "./lib/utils";
|
package/dist/index.js
ADDED
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
export { Button, buttonVariants } from "./components/ui/button";
|
|
2
|
+
export { Switch } from "./components/ui/switch";
|
|
3
|
+
export { Toggle } from "./components/ui/toggle";
|
|
4
|
+
export { ToggleGroup, ToggleGroupItem } from "./components/ui/toggle-group";
|
|
5
|
+
export { RadioGroup, RadioGroupItem } from "./components/ui/radio-group";
|
|
6
|
+
export { ThemeToggle } from "./components/theme-toggle";
|
|
7
|
+
export { ThemeProvider } from "./components/theme-provider";
|
|
8
|
+
export { Drawer, DrawerClose, DrawerContent, DrawerDescription, DrawerFooter, DrawerHeader, DrawerOverlay, DrawerPortal, DrawerSwipeHandle, DrawerTitle, DrawerTrigger, } from "./components/ui/drawer";
|
|
9
|
+
export { AccountDrawer } from "./components/account-drawer";
|
|
10
|
+
export { WorkspaceBrand } from "./components/workspace-brand";
|
|
11
|
+
export { WorkspaceLogo } from "./components/workspace-logo";
|
|
12
|
+
export { OnScreenControls } from "./components/on-screen-controls";
|
|
13
|
+
export { SceneSettings } from "./components/scene-settings";
|
|
14
|
+
export { VersionDialog, } from "./components/version-dialog";
|
|
15
|
+
export { Tooltip, TooltipContent, TooltipProvider, TooltipTrigger } from "./components/ui/tooltip";
|
|
16
|
+
export { Card, CardContent } from "./components/ui/card";
|
|
17
|
+
export { Spinner } from "./components/ui/spinner";
|
|
18
|
+
export { Dialog, DialogClose, DialogContent, DialogDescription, DialogFooter, DialogHeader, DialogOverlay, DialogPortal, DialogTitle, DialogTrigger, } from "./components/ui/dialog";
|
|
19
|
+
export { ModelThumbnail, PropCatalog, defaultPropCatalogCategories, getSharedLoader, } from "./components/prop-catalog";
|
|
20
|
+
export { cn } from "./lib/utils";
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
export function plainTextFromMarkdown(markdown) {
|
|
2
|
+
return markdown
|
|
3
|
+
.replace(/\r\n/g, "\n")
|
|
4
|
+
.replace(/!\[([^\]]*)\]\([^)]*\)/g, "$1")
|
|
5
|
+
.replace(/\[([^\]]+)\]\([^)]*\)/g, "$1")
|
|
6
|
+
.replace(/^[ \t]*#{1,6}[ \t]*/gm, "")
|
|
7
|
+
.replace(/^[ \t]*>[ \t]?/gm, "")
|
|
8
|
+
.replace(/^[ \t]*---+[ \t]*$/gm, "")
|
|
9
|
+
.replace(/^[ \t]*[-*+][ \t]+/gm, "• ")
|
|
10
|
+
.replace(/^[ \t]*\d+\.[ \t]+/gm, "")
|
|
11
|
+
.replace(/```[^\n]*\n?/g, "")
|
|
12
|
+
.replace(/`([^`]+)`/g, "$1")
|
|
13
|
+
.replace(/\*\*([^*]+)\*\*/g, "$1")
|
|
14
|
+
.replace(/__([^_]+)__/g, "$1")
|
|
15
|
+
.replace(/\*([^*]+)\*/g, "$1")
|
|
16
|
+
.replace(/_([^_]+)_/g, "$1")
|
|
17
|
+
.replace(/\n{3,}/g, "\n\n")
|
|
18
|
+
.trim();
|
|
19
|
+
}
|
|
20
|
+
export function formatReleaseDate(value) {
|
|
21
|
+
if (!value)
|
|
22
|
+
return null;
|
|
23
|
+
const date = new Date(value);
|
|
24
|
+
if (Number.isNaN(date.getTime()))
|
|
25
|
+
return value;
|
|
26
|
+
return new Intl.DateTimeFormat(undefined, {
|
|
27
|
+
day: "numeric",
|
|
28
|
+
month: "short",
|
|
29
|
+
year: "numeric",
|
|
30
|
+
}).format(date);
|
|
31
|
+
}
|