@cosmicstack/mercury-agent 1.1.12 → 1.2.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +9 -6
- package/dist/index.js +29767 -18219
- package/dist/index.js.map +1 -1
- package/dist/web/ui/assets/Chat-CajL8sV3.js +27 -0
- package/dist/web/ui/assets/{Dashboard-1rlAqQ-Y.js → Dashboard-ClnaDoDG.js} +1 -2
- package/dist/web/ui/assets/{Goals-CgSUAXLH.js → Goals-Rm3s3OGd.js} +1 -2
- package/dist/web/ui/assets/{Graph-DnlOWkay.js → Graph-hYGmN5vp.js} +1 -2
- package/dist/web/ui/assets/{Kanban-DRlNiNRF.js → Kanban-BK_Oi6am.js} +1 -2
- package/dist/web/ui/assets/{Login-BP5524pC.js → Login-Bl8tq7KA.js} +1 -2
- package/dist/web/ui/assets/MarkdownRenderer-DKGKZih7.js +21 -0
- package/dist/web/ui/assets/{Memory-BOQEY0H8.js → Memory-kKRHTUyC.js} +1 -2
- package/dist/web/ui/assets/{Permissions-jbFH-toa.js → Permissions-CDRBOdMO.js} +1 -2
- package/dist/web/ui/assets/{PersonDetail-Ca8B9io8.js → PersonDetail-DLbZBUS0.js} +1 -2
- package/dist/web/ui/assets/{Persons-epdmUeBM.js → Persons-C-GjzdmT.js} +1 -2
- package/dist/web/ui/assets/{Providers-Bm8sZNZo.js → Providers-L32issLd.js} +1 -2
- package/dist/web/ui/assets/{Schedules-BZKhm9R7.js → Schedules-BvGLrPPD.js} +1 -2
- package/dist/web/ui/assets/{Settings-Hii-5oku.js → Settings-BP9_1JW3.js} +1 -2
- package/dist/web/ui/assets/{Skills-BHJp2CgD.js → Skills-CvXlgjZK.js} +1 -2
- package/dist/web/ui/assets/{Tasks-D36pqkro.js → Tasks-XcAVd2Ff.js} +1 -2
- package/dist/web/ui/assets/{Usage-CmjaYrsT.js → Usage--2hxK31f.js} +1 -2
- package/dist/web/ui/assets/{Workspace-BYLf-wTJ.js → Workspace-BPChIyBc.js} +11 -12
- package/dist/web/ui/assets/{activity-MOTqH8zM.js → activity-CDTOZzUZ.js} +1 -2
- package/dist/web/ui/assets/{alert-dialog-MbYSbZx5.js → alert-dialog-B3JUwsIN.js} +1 -2
- package/dist/web/ui/assets/{arrow-left-CtqQsBC6.js → arrow-left-CkDXNwR2.js} +1 -2
- package/dist/web/ui/assets/{avatar-BIYaY7pR.js → avatar-NU204zr9.js} +1 -2
- package/dist/web/ui/assets/{badge-CUJiWF1y.js → badge-DpVeNL8j.js} +1 -2
- package/dist/web/ui/assets/{button-CNasMlFE.js → button-V3Fu7_kO.js} +1 -2
- package/dist/web/ui/assets/{card-BdsEOP7t.js → card-CjAvp22k.js} +1 -2
- package/dist/web/ui/assets/{chevron-down-CB9J_vvZ.js → chevron-down-C66c9kfo.js} +1 -2
- package/dist/web/ui/assets/{circle-check-DvGSe1uZ.js → circle-check-Cch4Kwja.js} +1 -2
- package/dist/web/ui/assets/{circle-x-CyaGJ_BM.js → circle-x-DK0DQPGB.js} +1 -2
- package/dist/web/ui/assets/collapsible-BU_K9n8f.js +0 -1
- package/dist/web/ui/assets/{dialog-Bd1rELXb.js → dialog-FHqlAspv.js} +1 -2
- package/dist/web/ui/assets/{download-C8RvlFqO.js → download-D73EX-Ki.js} +1 -2
- package/dist/web/ui/assets/{eye-BJ0NucMz.js → eye-CxEb5_L8.js} +1 -2
- package/dist/web/ui/assets/{file-text-BWWBuD_N.js → file-text-CDTjVG9h.js} +1 -2
- package/dist/web/ui/assets/{folder-open-BwjemFy7.js → folder-open-CF5wm-xS.js} +1 -2
- package/dist/web/ui/assets/{git-branch-D9JVASpC.js → git-branch-CYWJZoQx.js} +1 -2
- package/dist/web/ui/assets/{index-C3YiF4qv.js → index-B1xAjISP.js} +4 -5
- package/dist/web/ui/assets/{index-CaqLZNof.js → index-CufYpqmV.js} +1 -2
- package/dist/web/ui/assets/{input-CH3dmo9r.js → input-CF6e2HL4.js} +1 -2
- package/dist/web/ui/assets/{loader-circle-DbYKk0_Q.js → loader-circle-CJko6bz6.js} +1 -2
- package/dist/web/ui/assets/{pencil-gNDEMhav.js → pencil-DGvW-dl_.js} +1 -2
- package/dist/web/ui/assets/{plus-7rbHkByr.js → plus-DhHrgqcD.js} +1 -2
- package/dist/web/ui/assets/{power-BS7gCDWs.js → power-BFKfrVvI.js} +1 -2
- package/dist/web/ui/assets/{progress-ZzhsBV2v.js → progress-CsRtYJ3t.js} +1 -2
- package/dist/web/ui/assets/{search-BZsbhO0B.js → search-BwE8vRR_.js} +1 -2
- package/dist/web/ui/assets/{select-vRSgBrHz.js → select-Xy3UJnp-.js} +1 -2
- package/dist/web/ui/assets/{send-BkyTIUtJ.js → send-DHy23R-c.js} +1 -2
- package/dist/web/ui/assets/{sparkles-DcP24GEL.js → sparkles-wNQvP7So.js} +1 -2
- package/dist/web/ui/assets/{switch-LRN9wWy2.js → switch-CGgMESDf.js} +1 -2
- package/dist/web/ui/assets/{terminal-CWG62zdD.js → terminal-BvZc6N0C.js} +1 -2
- package/dist/web/ui/assets/{textarea-CXh3tmJ1.js → textarea-BTxEQ_C2.js} +1 -2
- package/dist/web/ui/assets/vendor-dnd-DRBSMxXo.js +0 -1
- package/dist/web/ui/assets/vendor-markdown-DwTbvico.js +0 -1
- package/dist/web/ui/assets/vendor-motion-Dwx3-JO5.js +0 -1
- package/dist/web/ui/assets/vendor-radix-3UdfCgs_.js +0 -1
- package/dist/web/ui/assets/vendor-react-C7pctHW3.js +0 -1
- package/dist/web/ui/assets/vendor-syntax-xZUI6Op9.js +0 -1
- package/dist/web/ui/assets/{zap-BEfqVtvZ.js → zap-CK8xUBKc.js} +1 -2
- package/dist/web/ui/index.html +1 -1
- package/dist/web/ui/workbox-0bb07689.js +1 -0
- package/package.json +10 -1
- package/dist/web/ui/assets/Chat-DXSn2dY8.js +0 -28
- package/dist/web/ui/assets/Chat-DXSn2dY8.js.map +0 -1
- package/dist/web/ui/assets/Dashboard-1rlAqQ-Y.js.map +0 -1
- package/dist/web/ui/assets/Goals-CgSUAXLH.js.map +0 -1
- package/dist/web/ui/assets/Graph-DnlOWkay.js.map +0 -1
- package/dist/web/ui/assets/Kanban-DRlNiNRF.js.map +0 -1
- package/dist/web/ui/assets/Login-BP5524pC.js.map +0 -1
- package/dist/web/ui/assets/MarkdownRenderer-B9KGVD0X.js +0 -22
- package/dist/web/ui/assets/MarkdownRenderer-B9KGVD0X.js.map +0 -1
- package/dist/web/ui/assets/Memory-BOQEY0H8.js.map +0 -1
- package/dist/web/ui/assets/Permissions-jbFH-toa.js.map +0 -1
- package/dist/web/ui/assets/PersonDetail-Ca8B9io8.js.map +0 -1
- package/dist/web/ui/assets/Persons-epdmUeBM.js.map +0 -1
- package/dist/web/ui/assets/Providers-Bm8sZNZo.js.map +0 -1
- package/dist/web/ui/assets/Schedules-BZKhm9R7.js.map +0 -1
- package/dist/web/ui/assets/Settings-Hii-5oku.js.map +0 -1
- package/dist/web/ui/assets/Skills-BHJp2CgD.js.map +0 -1
- package/dist/web/ui/assets/Tasks-D36pqkro.js.map +0 -1
- package/dist/web/ui/assets/Usage-CmjaYrsT.js.map +0 -1
- package/dist/web/ui/assets/Workspace-BYLf-wTJ.js.map +0 -1
- package/dist/web/ui/assets/activity-MOTqH8zM.js.map +0 -1
- package/dist/web/ui/assets/alert-dialog-MbYSbZx5.js.map +0 -1
- package/dist/web/ui/assets/arrow-left-CtqQsBC6.js.map +0 -1
- package/dist/web/ui/assets/avatar-BIYaY7pR.js.map +0 -1
- package/dist/web/ui/assets/badge-CUJiWF1y.js.map +0 -1
- package/dist/web/ui/assets/button-CNasMlFE.js.map +0 -1
- package/dist/web/ui/assets/card-BdsEOP7t.js.map +0 -1
- package/dist/web/ui/assets/chevron-down-CB9J_vvZ.js.map +0 -1
- package/dist/web/ui/assets/circle-check-DvGSe1uZ.js.map +0 -1
- package/dist/web/ui/assets/circle-x-CyaGJ_BM.js.map +0 -1
- package/dist/web/ui/assets/collapsible-BU_K9n8f.js.map +0 -1
- package/dist/web/ui/assets/dialog-Bd1rELXb.js.map +0 -1
- package/dist/web/ui/assets/download-C8RvlFqO.js.map +0 -1
- package/dist/web/ui/assets/eye-BJ0NucMz.js.map +0 -1
- package/dist/web/ui/assets/file-text-BWWBuD_N.js.map +0 -1
- package/dist/web/ui/assets/folder-open-BwjemFy7.js.map +0 -1
- package/dist/web/ui/assets/git-branch-D9JVASpC.js.map +0 -1
- package/dist/web/ui/assets/index-C3YiF4qv.js.map +0 -1
- package/dist/web/ui/assets/index-CaqLZNof.js.map +0 -1
- package/dist/web/ui/assets/input-CH3dmo9r.js.map +0 -1
- package/dist/web/ui/assets/loader-circle-DbYKk0_Q.js.map +0 -1
- package/dist/web/ui/assets/pencil-gNDEMhav.js.map +0 -1
- package/dist/web/ui/assets/plus-7rbHkByr.js.map +0 -1
- package/dist/web/ui/assets/power-BS7gCDWs.js.map +0 -1
- package/dist/web/ui/assets/progress-ZzhsBV2v.js.map +0 -1
- package/dist/web/ui/assets/search-BZsbhO0B.js.map +0 -1
- package/dist/web/ui/assets/select-vRSgBrHz.js.map +0 -1
- package/dist/web/ui/assets/send-BkyTIUtJ.js.map +0 -1
- package/dist/web/ui/assets/sparkles-DcP24GEL.js.map +0 -1
- package/dist/web/ui/assets/switch-LRN9wWy2.js.map +0 -1
- package/dist/web/ui/assets/terminal-CWG62zdD.js.map +0 -1
- package/dist/web/ui/assets/textarea-CXh3tmJ1.js.map +0 -1
- package/dist/web/ui/assets/vendor-dnd-DRBSMxXo.js.map +0 -1
- package/dist/web/ui/assets/vendor-markdown-DwTbvico.js.map +0 -1
- package/dist/web/ui/assets/vendor-motion-Dwx3-JO5.js.map +0 -1
- package/dist/web/ui/assets/vendor-radix-3UdfCgs_.js.map +0 -1
- package/dist/web/ui/assets/vendor-react-C7pctHW3.js.map +0 -1
- package/dist/web/ui/assets/vendor-syntax-xZUI6Op9.js.map +0 -1
- package/dist/web/ui/assets/zap-BEfqVtvZ.js.map +0 -1
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"Goals-CgSUAXLH.js","sources":["../../node_modules/lucide-react/dist/esm/icons/folder-kanban.js","../../node_modules/lucide-react/dist/esm/icons/rocket.js","../../src/components/ui/tabs.tsx","../../src/pages/brain/Goals.tsx"],"sourcesContent":["/**\n * @license lucide-react v0.511.0 - ISC\n *\n * This source code is licensed under the ISC license.\n * See the LICENSE file in the root directory of this source tree.\n */\n\nimport createLucideIcon from '../createLucideIcon.js';\n\nconst __iconNode = [\n [\n \"path\",\n {\n d: \"M4 20h16a2 2 0 0 0 2-2V8a2 2 0 0 0-2-2h-7.93a2 2 0 0 1-1.66-.9l-.82-1.2A2 2 0 0 0 7.93 3H4a2 2 0 0 0-2 2v13c0 1.1.9 2 2 2Z\",\n key: \"1fr9dc\"\n }\n ],\n [\"path\", { d: \"M8 10v4\", key: \"tgpxqk\" }],\n [\"path\", { d: \"M12 10v2\", key: \"hh53o1\" }],\n [\"path\", { d: \"M16 10v6\", key: \"1d6xys\" }]\n];\nconst FolderKanban = createLucideIcon(\"folder-kanban\", __iconNode);\n\nexport { __iconNode, FolderKanban as default };\n//# sourceMappingURL=folder-kanban.js.map\n","/**\n * @license lucide-react v0.511.0 - ISC\n *\n * This source code is licensed under the ISC license.\n * See the LICENSE file in the root directory of this source tree.\n */\n\nimport createLucideIcon from '../createLucideIcon.js';\n\nconst __iconNode = [\n [\n \"path\",\n {\n d: \"M4.5 16.5c-1.5 1.26-2 5-2 5s3.74-.5 5-2c.71-.84.7-2.13-.09-2.91a2.18 2.18 0 0 0-2.91-.09z\",\n key: \"m3kijz\"\n }\n ],\n [\n \"path\",\n {\n d: \"m12 15-3-3a22 22 0 0 1 2-3.95A12.88 12.88 0 0 1 22 2c0 2.72-.78 7.5-6 11a22.35 22.35 0 0 1-4 2z\",\n key: \"1fmvmk\"\n }\n ],\n [\"path\", { d: \"M9 12H4s.55-3.03 2-4c1.62-1.08 5 0 5 0\", key: \"1f8sc4\" }],\n [\"path\", { d: \"M12 15v5s3.03-.55 4-2c1.08-1.62 0-5 0-5\", key: \"qeys4\" }]\n];\nconst Rocket = createLucideIcon(\"rocket\", __iconNode);\n\nexport { __iconNode, Rocket as default };\n//# sourceMappingURL=rocket.js.map\n","import * as React from \"react\";\nimport * as TabsPrimitive from \"@radix-ui/react-tabs\";\nimport { cn } from \"@/lib/utils\";\n\nconst Tabs = TabsPrimitive.Root;\n\nconst TabsList = React.forwardRef<\n React.ElementRef<typeof TabsPrimitive.List>,\n React.ComponentPropsWithoutRef<typeof TabsPrimitive.List>\n>(({ className, ...props }, ref) => (\n <TabsPrimitive.List\n ref={ref}\n className={cn(\n \"inline-flex h-9 items-center justify-center gap-1 border-b border-border bg-transparent p-0 text-muted-foreground\",\n className\n )}\n {...props}\n />\n));\nTabsList.displayName = TabsPrimitive.List.displayName;\n\nconst TabsTrigger = React.forwardRef<\n React.ElementRef<typeof TabsPrimitive.Trigger>,\n React.ComponentPropsWithoutRef<typeof TabsPrimitive.Trigger>\n>(({ className, ...props }, ref) => (\n <TabsPrimitive.Trigger\n ref={ref}\n className={cn(\n \"inline-flex items-center justify-center whitespace-nowrap px-3 py-1.5 text-sm font-medium ring-offset-background transition-all focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring focus-visible:ring-offset-2 disabled:pointer-events-none disabled:opacity-50 border-b-2 border-transparent data-[state=active]:border-primary data-[state=active]:text-foreground data-[state=active]:shadow-none\",\n className\n )}\n {...props}\n />\n));\nTabsTrigger.displayName = TabsPrimitive.Trigger.displayName;\n\nconst TabsContent = React.forwardRef<\n React.ElementRef<typeof TabsPrimitive.Content>,\n React.ComponentPropsWithoutRef<typeof TabsPrimitive.Content>\n>(({ className, ...props }, ref) => (\n <TabsPrimitive.Content\n ref={ref}\n className={cn(\n \"mt-2 ring-offset-background focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring focus-visible:ring-offset-2\",\n className\n )}\n {...props}\n />\n));\nTabsContent.displayName = TabsPrimitive.Content.displayName;\n\nexport { Tabs, TabsList, TabsTrigger, TabsContent };\n","import { useEffect, useState, useCallback } from \"react\";\nimport { motion, AnimatePresence } from \"framer-motion\";\nimport {\n Target,\n FolderKanban,\n Plus,\n Trash2,\n Loader2,\n CheckCircle2,\n XCircle,\n Rocket,\n} from \"lucide-react\";\nimport { Card, CardContent } from \"@/components/ui/card\";\nimport { Button } from \"@/components/ui/button\";\nimport { Input } from \"@/components/ui/input\";\nimport { Badge } from \"@/components/ui/badge\";\nimport { Textarea } from \"@/components/ui/textarea\";\nimport { Tabs, TabsList, TabsTrigger, TabsContent } from \"@/components/ui/tabs\";\nimport {\n Dialog,\n DialogContent,\n DialogHeader,\n DialogTitle,\n DialogFooter,\n DialogDescription,\n} from \"@/components/ui/dialog\";\nimport {\n AlertDialog,\n AlertDialogAction,\n AlertDialogCancel,\n AlertDialogContent,\n AlertDialogDescription,\n AlertDialogFooter,\n AlertDialogHeader,\n AlertDialogTitle,\n AlertDialogTrigger,\n} from \"@/components/ui/alert-dialog\";\nimport { cn, formatDate } from \"@/lib/utils\";\nimport api, { type Memory, type MemoryCreate } from \"@/lib/api\";\n\n/* ── Animations ─────────────────────────────────────────────── */\n\nconst fadeUp = {\n hidden: { opacity: 0, y: 12 },\n visible: (i: number) => ({\n opacity: 1,\n y: 0,\n transition: { delay: i * 0.05, duration: 0.3, ease: \"easeOut\" as const },\n }),\n exit: { opacity: 0, y: -8, transition: { duration: 0.2 } },\n};\n\nconst stagger = {\n visible: { transition: { staggerChildren: 0.05 } },\n};\n\n/* ── Toast ──────────────────────────────────────────────────── */\n\ninterface Toast {\n id: number;\n type: \"success\" | \"error\";\n message: string;\n}\n\nfunction ToastBar({ toasts }: { toasts: Toast[] }) {\n return (\n <div className=\"fixed bottom-6 right-6 z-50 flex flex-col gap-2\">\n <AnimatePresence>\n {toasts.map((t) => (\n <motion.div\n key={t.id}\n initial={{ opacity: 0, x: 40 }}\n animate={{ opacity: 1, x: 0 }}\n exit={{ opacity: 0, x: 40 }}\n className={cn(\n \"flex items-center gap-2 rounded-lg border px-4 py-3 text-sm shadow-lg backdrop-blur-sm\",\n t.type === \"success\"\n ? \"border-emerald-500/30 bg-emerald-500/10 text-emerald-400\"\n : \"border-destructive/30 bg-destructive/10 text-destructive\"\n )}\n >\n {t.type === \"success\" ? (\n <CheckCircle2 className=\"h-4 w-4\" />\n ) : (\n <XCircle className=\"h-4 w-4\" />\n )}\n {t.message}\n </motion.div>\n ))}\n </AnimatePresence>\n </div>\n );\n}\n\n/* ── Skeleton ───────────────────────────────────────────────── */\n\nfunction Skeleton({ className }: { className?: string }) {\n return (\n <div className={cn(\"animate-pulse rounded-lg bg-muted\", className)} />\n );\n}\n\nfunction ItemCardSkeleton() {\n return (\n <Card>\n <CardContent className=\"p-5 space-y-3\">\n <Skeleton className=\"h-5 w-3/4\" />\n <Skeleton className=\"h-3 w-full\" />\n <div className=\"flex items-center gap-3\">\n <Skeleton className=\"h-3 w-16\" />\n <Skeleton className=\"h-3 w-20\" />\n </div>\n </CardContent>\n </Card>\n );\n}\n\n/* ── Priority Indicator ─────────────────────────────────────── */\n\nfunction PriorityIndicator({ importance }: { importance: number }) {\n const label =\n importance >= 8\n ? \"Critical\"\n : importance >= 6\n ? \"High\"\n : importance >= 4\n ? \"Medium\"\n : \"Low\";\n const color =\n importance >= 8\n ? \"text-red-400 bg-red-500/15\"\n : importance >= 6\n ? \"text-amber-400 bg-amber-500/15\"\n : importance >= 4\n ? \"text-[#00d4ff] bg-[#00d4ff]/15\"\n : \"text-muted-foreground bg-muted\";\n\n return (\n <span\n className={cn(\n \"inline-flex items-center rounded-md px-2 py-0.5 text-xs font-medium\",\n color\n )}\n >\n {label}\n </span>\n );\n}\n\n/* ── Item Card ──────────────────────────────────────────────── */\n\nfunction ItemCard({\n item,\n onDelete,\n index,\n kind,\n}: {\n item: Memory;\n onDelete: (id: string) => void;\n index: number;\n kind: \"goal\" | \"project\";\n}) {\n return (\n <motion.div\n custom={index}\n variants={fadeUp}\n initial=\"hidden\"\n animate=\"visible\"\n exit=\"exit\"\n layout\n >\n <Card className=\"group transition-colors hover:border-[#00d4ff]/20\">\n <CardContent className=\"p-5\">\n <div className=\"flex items-start justify-between gap-3\">\n <div className=\"flex-1 min-w-0 space-y-2\">\n {/* Title row */}\n <div className=\"flex items-center gap-2.5\">\n {kind === \"goal\" ? (\n <Target className=\"h-4 w-4 text-amber-400 shrink-0\" />\n ) : (\n <FolderKanban className=\"h-4 w-4 text-cyan-400 shrink-0\" />\n )}\n <h3 className=\"text-sm font-semibold text-foreground leading-tight\">\n {item.summary}\n </h3>\n </div>\n\n {/* Detail */}\n {item.detail && (\n <p className=\"text-sm text-muted-foreground leading-relaxed line-clamp-3\">\n {item.detail}\n </p>\n )}\n\n {/* Meta */}\n <div className=\"flex flex-wrap items-center gap-3 pt-0.5\">\n {item.importance != null && (\n <PriorityIndicator importance={item.importance} />\n )}\n <span className=\"text-xs text-muted-foreground/50\">\n {formatDate(item.createdAt)}\n </span>\n </div>\n </div>\n\n {/* Delete */}\n <AlertDialog>\n <AlertDialogTrigger asChild>\n <Button\n size=\"sm\"\n variant=\"ghost\"\n className=\"opacity-0 group-hover:opacity-100 transition-opacity text-muted-foreground hover:text-destructive shrink-0\"\n >\n <Trash2 className=\"h-3.5 w-3.5\" />\n </Button>\n </AlertDialogTrigger>\n <AlertDialogContent>\n <AlertDialogHeader>\n <AlertDialogTitle>\n Delete {kind === \"goal\" ? \"Goal\" : \"Project\"}\n </AlertDialogTitle>\n <AlertDialogDescription>\n Are you sure you want to delete this{\" \"}\n {kind === \"goal\" ? \"goal\" : \"project\"}? This action cannot\n be undone.\n </AlertDialogDescription>\n </AlertDialogHeader>\n <AlertDialogFooter>\n <AlertDialogCancel>Cancel</AlertDialogCancel>\n <AlertDialogAction\n onClick={() => onDelete(item.id)}\n className=\"bg-destructive text-destructive-foreground hover:bg-destructive/90\"\n >\n Delete\n </AlertDialogAction>\n </AlertDialogFooter>\n </AlertDialogContent>\n </AlertDialog>\n </div>\n </CardContent>\n </Card>\n </motion.div>\n );\n}\n\n/* ── Add Dialog ─────────────────────────────────────────────── */\n\nfunction AddItemDialog({\n open,\n onOpenChange,\n onSubmit,\n submitting,\n kind,\n}: {\n open: boolean;\n onOpenChange: (open: boolean) => void;\n onSubmit: (data: MemoryCreate) => void;\n submitting: boolean;\n kind: \"goal\" | \"project\";\n}) {\n const [summary, setSummary] = useState(\"\");\n const [detail, setDetail] = useState(\"\");\n const [importance, setImportance] = useState(\"5\");\n\n const handleSubmit = (e: React.FormEvent) => {\n e.preventDefault();\n if (!summary.trim()) return;\n onSubmit({\n type: kind,\n summary: summary.trim(),\n detail: detail.trim() || undefined,\n importance: parseInt(importance),\n });\n };\n\n const reset = () => {\n setSummary(\"\");\n setDetail(\"\");\n setImportance(\"5\");\n };\n\n return (\n <Dialog\n open={open}\n onOpenChange={(v) => {\n if (!v) reset();\n onOpenChange(v);\n }}\n >\n <DialogContent className=\"sm:max-w-md\">\n <DialogHeader>\n <DialogTitle>\n Add {kind === \"goal\" ? \"Goal\" : \"Project\"}\n </DialogTitle>\n <DialogDescription>\n Create a new {kind === \"goal\" ? \"goal\" : \"project\"} in the Second\n Brain.\n </DialogDescription>\n </DialogHeader>\n <form onSubmit={handleSubmit} className=\"space-y-4\">\n <div className=\"space-y-1.5\">\n <label className=\"text-sm font-medium text-foreground\">\n Summary <span className=\"text-destructive\">*</span>\n </label>\n <Input\n placeholder={\n kind === \"goal\"\n ? \"What do you want to achieve?\"\n : \"What are you working on?\"\n }\n value={summary}\n onChange={(e) => setSummary(e.target.value)}\n required\n />\n </div>\n\n <div className=\"space-y-1.5\">\n <label className=\"text-sm font-medium text-foreground\">\n Detail\n </label>\n <Textarea\n placeholder=\"Additional context...\"\n value={detail}\n onChange={(e) => setDetail(e.target.value)}\n rows={3}\n />\n </div>\n\n <div className=\"space-y-1.5\">\n <label className=\"text-sm font-medium text-foreground\">\n Importance (1–10)\n </label>\n <Input\n type=\"number\"\n min=\"1\"\n max=\"10\"\n step=\"1\"\n value={importance}\n onChange={(e) => setImportance(e.target.value)}\n />\n </div>\n\n <DialogFooter>\n <Button type=\"submit\" disabled={submitting || !summary.trim()}>\n {submitting ? (\n <>\n <Loader2 className=\"h-4 w-4 animate-spin\" />\n Saving...\n </>\n ) : (\n `Add ${kind === \"goal\" ? \"Goal\" : \"Project\"}`\n )}\n </Button>\n </DialogFooter>\n </form>\n </DialogContent>\n </Dialog>\n );\n}\n\n/* ── Tab Content ────────────────────────────────────────────── */\n\nfunction TabSection({\n items,\n loading,\n error,\n kind,\n onDelete,\n onRetry,\n onAdd,\n}: {\n items: Memory[];\n loading: boolean;\n error: string | null;\n kind: \"goal\" | \"project\";\n onDelete: (id: string) => void;\n onRetry: () => void;\n onAdd: () => void;\n}) {\n if (error) {\n return (\n <Card className=\"border-destructive/30\">\n <CardContent className=\"flex items-center gap-3 p-4 text-sm text-destructive\">\n <XCircle className=\"h-4 w-4 shrink-0\" />\n {error}\n <Button size=\"sm\" variant=\"outline\" className=\"ml-auto\" onClick={onRetry}>\n Retry\n </Button>\n </CardContent>\n </Card>\n );\n }\n\n if (loading) {\n return (\n <div className=\"space-y-3\">\n {Array.from({ length: 3 }).map((_, i) => (\n <ItemCardSkeleton key={i} />\n ))}\n </div>\n );\n }\n\n if (items.length === 0) {\n return (\n <Card>\n <CardContent className=\"flex flex-col items-center justify-center py-16 text-center\">\n <div className=\"flex h-14 w-14 items-center justify-center rounded-full bg-muted mb-4\">\n {kind === \"goal\" ? (\n <Target className=\"h-7 w-7 text-muted-foreground\" />\n ) : (\n <Rocket className=\"h-7 w-7 text-muted-foreground\" />\n )}\n </div>\n <h3 className=\"text-base font-medium text-foreground mb-1\">\n No {kind === \"goal\" ? \"goals\" : \"projects\"} yet\n </h3>\n <p className=\"text-sm text-muted-foreground max-w-sm\">\n {kind === \"goal\"\n ? \"Add goals to help Mercury understand what you're working towards.\"\n : \"Track active projects so Mercury can provide better context.\"}\n </p>\n <Button className=\"mt-4\" onClick={onAdd}>\n <Plus className=\"h-4 w-4\" />\n Add {kind === \"goal\" ? \"Goal\" : \"Project\"}\n </Button>\n </CardContent>\n </Card>\n );\n }\n\n return (\n <motion.div\n className=\"space-y-3\"\n variants={stagger}\n initial=\"hidden\"\n animate=\"visible\"\n >\n <AnimatePresence mode=\"popLayout\">\n {items.map((item, i) => (\n <ItemCard\n key={item.id}\n item={item}\n onDelete={onDelete}\n index={i}\n kind={kind}\n />\n ))}\n </AnimatePresence>\n </motion.div>\n );\n}\n\n/* ── Main Page ──────────────────────────────────────────────── */\n\nexport function GoalsPage() {\n const [goals, setGoals] = useState<Memory[]>([]);\n const [projects, setProjects] = useState<Memory[]>([]);\n const [goalsLoading, setGoalsLoading] = useState(true);\n const [projectsLoading, setProjectsLoading] = useState(true);\n const [goalsError, setGoalsError] = useState<string | null>(null);\n const [projectsError, setProjectsError] = useState<string | null>(null);\n const [dialogOpen, setDialogOpen] = useState(false);\n const [dialogKind, setDialogKind] = useState<\"goal\" | \"project\">(\"goal\");\n const [submitting, setSubmitting] = useState(false);\n const [activeTab, setActiveTab] = useState(\"goals\");\n const [toasts, setToasts] = useState<Toast[]>([]);\n\n const toast = useCallback((type: \"success\" | \"error\", message: string) => {\n const id = Date.now();\n setToasts((prev) => [...prev, { id, type, message }]);\n setTimeout(() => {\n setToasts((prev) => prev.filter((t) => t.id !== id));\n }, 3500);\n }, []);\n\n const fetchGoals = useCallback(async () => {\n try {\n setGoalsLoading(true);\n setGoalsError(null);\n const res = await api.brain.memory.list({ type: \"goal\" });\n setGoals(res.memories);\n } catch (err: unknown) {\n setGoalsError(\n err instanceof Error ? err.message : \"Failed to load goals\"\n );\n } finally {\n setGoalsLoading(false);\n }\n }, []);\n\n const fetchProjects = useCallback(async () => {\n try {\n setProjectsLoading(true);\n setProjectsError(null);\n const res = await api.brain.memory.list({ type: \"project\" });\n setProjects(res.memories);\n } catch (err: unknown) {\n setProjectsError(\n err instanceof Error ? err.message : \"Failed to load projects\"\n );\n } finally {\n setProjectsLoading(false);\n }\n }, []);\n\n useEffect(() => {\n fetchGoals();\n fetchProjects();\n }, [fetchGoals, fetchProjects]);\n\n const openDialog = (kind: \"goal\" | \"project\") => {\n setDialogKind(kind);\n setDialogOpen(true);\n };\n\n const handleCreate = async (data: MemoryCreate) => {\n setSubmitting(true);\n try {\n await api.brain.memory.create(data);\n toast(\"success\", `${data.type === \"goal\" ? \"Goal\" : \"Project\"} created`);\n setDialogOpen(false);\n if (data.type === \"goal\") fetchGoals();\n else fetchProjects();\n } catch (err: unknown) {\n toast(\"error\", err instanceof Error ? err.message : \"Failed to create\");\n } finally {\n setSubmitting(false);\n }\n };\n\n const handleDeleteGoal = async (id: string) => {\n try {\n await api.brain.memory.delete(id);\n setGoals((prev) => prev.filter((g) => g.id !== id));\n toast(\"success\", \"Goal deleted\");\n } catch (err: unknown) {\n toast(\"error\", err instanceof Error ? err.message : \"Failed to delete\");\n }\n };\n\n const handleDeleteProject = async (id: string) => {\n try {\n await api.brain.memory.delete(id);\n setProjects((prev) => prev.filter((p) => p.id !== id));\n toast(\"success\", \"Project deleted\");\n } catch (err: unknown) {\n toast(\"error\", err instanceof Error ? err.message : \"Failed to delete\");\n }\n };\n\n return (\n <div className=\"space-y-6 p-6\">\n {/* Header */}\n <motion.div\n initial={{ opacity: 0, y: -8 }}\n animate={{ opacity: 1, y: 0 }}\n transition={{ duration: 0.3 }}\n className=\"flex items-start justify-between gap-4\"\n >\n <div className=\"flex items-center gap-3\">\n <div className=\"flex h-10 w-10 items-center justify-center rounded-lg bg-[#00d4ff]/10\">\n <Target className=\"h-5 w-5 text-[#00d4ff]\" />\n </div>\n <div>\n <div className=\"flex items-center gap-2.5\">\n <h1 className=\"text-2xl font-semibold text-foreground\">\n Goals & Projects\n </h1>\n <Badge variant=\"secondary\" className=\"tabular-nums\">\n {goals.length + projects.length}\n </Badge>\n </div>\n <p className=\"text-sm text-muted-foreground\">\n Track objectives and active initiatives\n </p>\n </div>\n </div>\n <Button\n onClick={() =>\n openDialog(activeTab === \"goals\" ? \"goal\" : \"project\")\n }\n >\n <Plus className=\"h-4 w-4\" />\n Add {activeTab === \"goals\" ? \"Goal\" : \"Project\"}\n </Button>\n </motion.div>\n\n {/* Tabs */}\n <motion.div\n initial={{ opacity: 0, y: 8 }}\n animate={{ opacity: 1, y: 0 }}\n transition={{ delay: 0.1, duration: 0.3 }}\n >\n <Tabs\n value={activeTab}\n onValueChange={setActiveTab}\n className=\"space-y-4\"\n >\n <TabsList className=\"w-full sm:w-auto\">\n <TabsTrigger value=\"goals\" className=\"gap-1.5\">\n <Target className=\"h-3.5 w-3.5\" />\n Goals\n {!goalsLoading && (\n <span className=\"ml-1 text-xs text-muted-foreground/60 tabular-nums\">\n ({goals.length})\n </span>\n )}\n </TabsTrigger>\n <TabsTrigger value=\"projects\" className=\"gap-1.5\">\n <FolderKanban className=\"h-3.5 w-3.5\" />\n Projects\n {!projectsLoading && (\n <span className=\"ml-1 text-xs text-muted-foreground/60 tabular-nums\">\n ({projects.length})\n </span>\n )}\n </TabsTrigger>\n </TabsList>\n\n <TabsContent value=\"goals\">\n <TabSection\n items={goals}\n loading={goalsLoading}\n error={goalsError}\n kind=\"goal\"\n onDelete={handleDeleteGoal}\n onRetry={fetchGoals}\n onAdd={() => openDialog(\"goal\")}\n />\n </TabsContent>\n\n <TabsContent value=\"projects\">\n <TabSection\n items={projects}\n loading={projectsLoading}\n error={projectsError}\n kind=\"project\"\n onDelete={handleDeleteProject}\n onRetry={fetchProjects}\n onAdd={() => openDialog(\"project\")}\n />\n </TabsContent>\n </Tabs>\n </motion.div>\n\n {/* Add dialog */}\n <AddItemDialog\n open={dialogOpen}\n onOpenChange={setDialogOpen}\n onSubmit={handleCreate}\n submitting={submitting}\n kind={dialogKind}\n />\n\n <ToastBar toasts={toasts} />\n </div>\n );\n}\n"],"names":["__iconNode","FolderKanban","createLucideIcon","Rocket","Tabs","TabsPrimitive.Root","TabsList","React.forwardRef","className","props","ref","jsx","TabsPrimitive.List","cn","TabsTrigger","TabsPrimitive.Trigger","TabsContent","TabsPrimitive.Content","fadeUp","i","stagger","ToastBar","toasts","AnimatePresence","t","jsxs","motion","CheckCircle2","XCircle","Skeleton","ItemCardSkeleton","Card","CardContent","PriorityIndicator","importance","label","color","ItemCard","item","onDelete","index","kind","Target","formatDate","AlertDialog","AlertDialogTrigger","Button","Trash2","AlertDialogContent","AlertDialogHeader","AlertDialogTitle","AlertDialogDescription","AlertDialogFooter","AlertDialogCancel","AlertDialogAction","AddItemDialog","open","onOpenChange","onSubmit","submitting","summary","setSummary","useState","detail","setDetail","setImportance","handleSubmit","e","reset","Dialog","v","DialogContent","DialogHeader","DialogTitle","DialogDescription","Input","Textarea","DialogFooter","Fragment","Loader2","TabSection","items","loading","error","onRetry","onAdd","_","Plus","GoalsPage","goals","setGoals","projects","setProjects","goalsLoading","setGoalsLoading","projectsLoading","setProjectsLoading","goalsError","setGoalsError","projectsError","setProjectsError","dialogOpen","setDialogOpen","dialogKind","setDialogKind","setSubmitting","activeTab","setActiveTab","setToasts","toast","useCallback","type","message","id","prev","fetchGoals","res","api","err","fetchProjects","useEffect","openDialog","handleCreate","data","handleDeleteGoal","g","handleDeleteProject","p","Badge"],"mappings":"m4BAAA;AAAA;AAAA;AAAA;AAAA;AAAA,GASA,MAAMA,GAAa,CACjB,CACE,OACA,CACE,EAAG,6HACH,IAAK,QACX,CACA,EACE,CAAC,OAAQ,CAAE,EAAG,UAAW,IAAK,QAAQ,CAAE,EACxC,CAAC,OAAQ,CAAE,EAAG,WAAY,IAAK,QAAQ,CAAE,EACzC,CAAC,OAAQ,CAAE,EAAG,WAAY,IAAK,QAAQ,CAAE,CAC3C,EACMC,EAAeC,EAAiB,gBAAiBF,EAAU,ECrBjE;AAAA;AAAA;AAAA;AAAA;AAAA,GASA,MAAMA,GAAa,CACjB,CACE,OACA,CACE,EAAG,4FACH,IAAK,QACX,CACA,EACE,CACE,OACA,CACE,EAAG,kGACH,IAAK,QACX,CACA,EACE,CAAC,OAAQ,CAAE,EAAG,yCAA0C,IAAK,QAAQ,CAAE,EACvE,CAAC,OAAQ,CAAE,EAAG,0CAA2C,IAAK,OAAO,CAAE,CACzE,EACMG,GAASD,EAAiB,SAAUF,EAAU,ECvB9CI,GAAOC,GAEPC,EAAWC,EAAAA,WAGf,CAAC,CAAE,UAAAC,EAAW,GAAGC,CAAA,EAASC,IAC1BC,EAAAA,IAACC,EAAA,CACC,IAAAF,EACA,UAAWG,EACT,oHACAL,CAAA,EAED,GAAGC,CAAA,CACN,CACD,EACDH,EAAS,YAAcM,EAAmB,YAE1C,MAAME,EAAcP,EAAAA,WAGlB,CAAC,CAAE,UAAAC,EAAW,GAAGC,CAAA,EAASC,IAC1BC,EAAAA,IAACI,EAAA,CACC,IAAAL,EACA,UAAWG,EACT,4ZACAL,CAAA,EAED,GAAGC,CAAA,CACN,CACD,EACDK,EAAY,YAAcC,EAAsB,YAEhD,MAAMC,EAAcT,EAAAA,WAGlB,CAAC,CAAE,UAAAC,EAAW,GAAGC,CAAA,EAASC,IAC1BC,EAAAA,IAACM,EAAA,CACC,IAAAP,EACA,UAAWG,EACT,kIACAL,CAAA,EAED,GAAGC,CAAA,CACN,CACD,EACDO,EAAY,YAAcC,EAAsB,YCPhD,MAAMC,GAAS,CACb,OAAQ,CAAE,QAAS,EAAG,EAAG,EAAA,EACzB,QAAUC,IAAe,CACvB,QAAS,EACT,EAAG,EACH,WAAY,CAAE,MAAOA,EAAI,IAAM,SAAU,GAAK,KAAM,SAAA,CAAmB,GAEzE,KAAM,CAAE,QAAS,EAAG,EAAG,GAAI,WAAY,CAAE,SAAU,EAAA,CAAI,CACzD,EAEMC,GAAU,CACd,QAAS,CAAE,WAAY,CAAE,gBAAiB,IAAK,CACjD,EAUA,SAASC,GAAS,CAAE,OAAAC,GAA+B,CACjD,OACEX,EAAAA,IAAC,OAAI,UAAU,kDACb,eAACY,EAAA,CACE,SAAAD,EAAO,IAAKE,GACXC,EAAAA,KAACC,EAAO,IAAP,CAEC,QAAS,CAAE,QAAS,EAAG,EAAG,EAAA,EAC1B,QAAS,CAAE,QAAS,EAAG,EAAG,CAAA,EAC1B,KAAM,CAAE,QAAS,EAAG,EAAG,EAAA,EACvB,UAAWb,EACT,yFACAW,EAAE,OAAS,UACP,2DACA,0DAAA,EAGL,SAAA,CAAAA,EAAE,OAAS,UACVb,EAAAA,IAACgB,GAAA,CAAa,UAAU,UAAU,EAElChB,EAAAA,IAACiB,EAAA,CAAQ,UAAU,SAAA,CAAU,EAE9BJ,EAAE,OAAA,CAAA,EAhBEA,EAAE,EAAA,CAkBV,EACH,CAAA,CACF,CAEJ,CAIA,SAASK,EAAS,CAAE,UAAArB,GAAqC,CACvD,aACG,MAAA,CAAI,UAAWK,EAAG,oCAAqCL,CAAS,EAAG,CAExE,CAEA,SAASsB,IAAmB,CAC1B,OACEnB,EAAAA,IAACoB,EAAA,CACC,SAAAN,EAAAA,KAACO,EAAA,CAAY,UAAU,gBACrB,SAAA,CAAArB,EAAAA,IAACkB,EAAA,CAAS,UAAU,WAAA,CAAY,EAChClB,EAAAA,IAACkB,EAAA,CAAS,UAAU,YAAA,CAAa,EACjCJ,EAAAA,KAAC,MAAA,CAAI,UAAU,0BACb,SAAA,CAAAd,EAAAA,IAACkB,EAAA,CAAS,UAAU,UAAA,CAAW,EAC/BlB,EAAAA,IAACkB,EAAA,CAAS,UAAU,UAAA,CAAW,CAAA,CAAA,CACjC,CAAA,CAAA,CACF,CAAA,CACF,CAEJ,CAIA,SAASI,GAAkB,CAAE,WAAAC,GAAsC,CACjE,MAAMC,EACJD,GAAc,EACV,WACAA,GAAc,EACZ,OACAA,GAAc,EACZ,SACA,MACJE,EACJF,GAAc,EACV,6BACAA,GAAc,EACZ,iCACAA,GAAc,EACZ,iCACA,iCAEV,OACEvB,EAAAA,IAAC,OAAA,CACC,UAAWE,EACT,sEACAuB,CAAA,EAGD,SAAAD,CAAA,CAAA,CAGP,CAIA,SAASE,GAAS,CAChB,KAAAC,EACA,SAAAC,EACA,MAAAC,EACA,KAAAC,CACF,EAKG,CACD,OACE9B,EAAAA,IAACe,EAAO,IAAP,CACC,OAAQc,EACR,SAAUtB,GACV,QAAQ,SACR,QAAQ,UACR,KAAK,OACL,OAAM,GAEN,SAAAP,EAAAA,IAACoB,EAAA,CAAK,UAAU,oDACd,SAAApB,EAAAA,IAACqB,EAAA,CAAY,UAAU,MACrB,SAAAP,EAAAA,KAAC,MAAA,CAAI,UAAU,yCACb,SAAA,CAAAA,EAAAA,KAAC,MAAA,CAAI,UAAU,2BAEb,SAAA,CAAAA,EAAAA,KAAC,MAAA,CAAI,UAAU,4BACZ,SAAA,CAAAgB,IAAS,aACPC,EAAA,CAAO,UAAU,kCAAkC,EAEpD/B,EAAAA,IAACV,EAAA,CAAa,UAAU,gCAAA,CAAiC,EAE3DU,EAAAA,IAAC,KAAA,CAAG,UAAU,sDACX,WAAK,OAAA,CACR,CAAA,EACF,EAGC2B,EAAK,QACJ3B,EAAAA,IAAC,KAAE,UAAU,6DACV,WAAK,OACR,EAIFc,EAAAA,KAAC,MAAA,CAAI,UAAU,2CACZ,SAAA,CAAAa,EAAK,YAAc,MAClB3B,EAAAA,IAACsB,GAAA,CAAkB,WAAYK,EAAK,WAAY,QAEjD,OAAA,CAAK,UAAU,mCACb,SAAAK,GAAWL,EAAK,SAAS,CAAA,CAC5B,CAAA,CAAA,CACF,CAAA,EACF,SAGCM,GAAA,CACC,SAAA,CAAAjC,EAAAA,IAACkC,GAAA,CAAmB,QAAO,GACzB,SAAAlC,EAAAA,IAACmC,EAAA,CACC,KAAK,KACL,QAAQ,QACR,UAAU,6GAEV,SAAAnC,EAAAA,IAACoC,GAAA,CAAO,UAAU,aAAA,CAAc,CAAA,CAAA,EAEpC,SACCC,GAAA,CACC,SAAA,CAAAvB,OAACwB,GAAA,CACC,SAAA,CAAAxB,OAACyB,GAAA,CAAiB,SAAA,CAAA,UACRT,IAAS,OAAS,OAAS,SAAA,EACrC,SACCU,GAAA,CAAuB,SAAA,CAAA,uCACe,IACpCV,IAAS,OAAS,OAAS,UAAU,iCAAA,CAAA,CAExC,CAAA,EACF,SACCW,GAAA,CACC,SAAA,CAAAzC,EAAAA,IAAC0C,IAAkB,SAAA,QAAA,CAAM,EACzB1C,EAAAA,IAAC2C,GAAA,CACC,QAAS,IAAMf,EAASD,EAAK,EAAE,EAC/B,UAAU,qEACX,SAAA,QAAA,CAAA,CAED,CAAA,CACF,CAAA,CAAA,CACF,CAAA,CAAA,CACF,CAAA,CAAA,CACF,EACF,CAAA,CACF,CAAA,CAAA,CAGN,CAIA,SAASiB,GAAc,CACrB,KAAAC,EACA,aAAAC,EACA,SAAAC,EACA,WAAAC,EACA,KAAAlB,CACF,EAMG,CACD,KAAM,CAACmB,EAASC,CAAU,EAAIC,EAAAA,SAAS,EAAE,EACnC,CAACC,EAAQC,CAAS,EAAIF,EAAAA,SAAS,EAAE,EACjC,CAAC5B,EAAY+B,CAAa,EAAIH,EAAAA,SAAS,GAAG,EAE1CI,EAAgBC,GAAuB,CAC3CA,EAAE,eAAA,EACGP,EAAQ,QACbF,EAAS,CACP,KAAMjB,EACN,QAASmB,EAAQ,KAAA,EACjB,OAAQG,EAAO,KAAA,GAAU,OACzB,WAAY,SAAS7B,CAAU,CAAA,CAChC,CACH,EAEMkC,EAAQ,IAAM,CAClBP,EAAW,EAAE,EACbG,EAAU,EAAE,EACZC,EAAc,GAAG,CACnB,EAEA,OACEtD,EAAAA,IAAC0D,GAAA,CACC,KAAAb,EACA,aAAec,GAAM,CACdA,GAAGF,EAAA,EACRX,EAAaa,CAAC,CAChB,EAEA,SAAA7C,EAAAA,KAAC8C,GAAA,CAAc,UAAU,cACvB,SAAA,CAAA9C,OAAC+C,GAAA,CACC,SAAA,CAAA/C,OAACgD,GAAA,CAAY,SAAA,CAAA,OACNhC,IAAS,OAAS,OAAS,SAAA,EAClC,SACCiC,GAAA,CAAkB,SAAA,CAAA,gBACHjC,IAAS,OAAS,OAAS,UAAU,uBAAA,CAAA,CAErD,CAAA,EACF,EACAhB,EAAAA,KAAC,OAAA,CAAK,SAAUyC,EAAc,UAAU,YACtC,SAAA,CAAAzC,EAAAA,KAAC,MAAA,CAAI,UAAU,cACb,SAAA,CAAAA,EAAAA,KAAC,QAAA,CAAM,UAAU,sCAAsC,SAAA,CAAA,WAC7Cd,EAAAA,IAAC,OAAA,CAAK,UAAU,mBAAmB,SAAA,GAAA,CAAC,CAAA,EAC9C,EACAA,EAAAA,IAACgE,EAAA,CACC,YACElC,IAAS,OACL,+BACA,2BAEN,MAAOmB,EACP,SAAWO,GAAMN,EAAWM,EAAE,OAAO,KAAK,EAC1C,SAAQ,EAAA,CAAA,CACV,EACF,EAEA1C,EAAAA,KAAC,MAAA,CAAI,UAAU,cACb,SAAA,CAAAd,EAAAA,IAAC,QAAA,CAAM,UAAU,sCAAsC,SAAA,SAEvD,EACAA,EAAAA,IAACiE,GAAA,CACC,YAAY,wBACZ,MAAOb,EACP,SAAWI,GAAMH,EAAUG,EAAE,OAAO,KAAK,EACzC,KAAM,CAAA,CAAA,CACR,EACF,EAEA1C,EAAAA,KAAC,MAAA,CAAI,UAAU,cACb,SAAA,CAAAd,EAAAA,IAAC,QAAA,CAAM,UAAU,sCAAsC,SAAA,oBAEvD,EACAA,EAAAA,IAACgE,EAAA,CACC,KAAK,SACL,IAAI,IACJ,IAAI,KACJ,KAAK,IACL,MAAOzC,EACP,SAAWiC,GAAMF,EAAcE,EAAE,OAAO,KAAK,CAAA,CAAA,CAC/C,EACF,EAEAxD,MAACkE,GAAA,CACC,SAAAlE,EAAAA,IAACmC,EAAA,CAAO,KAAK,SAAS,SAAUa,GAAc,CAACC,EAAQ,KAAA,EACpD,WACCnC,OAAAqD,EAAAA,SAAA,CACE,SAAA,CAAAnE,EAAAA,IAACoE,GAAA,CAAQ,UAAU,sBAAA,CAAuB,EAAE,WAAA,EAE9C,EAEA,OAAOtC,IAAS,OAAS,OAAS,SAAS,GAE/C,CAAA,CACF,CAAA,CAAA,CACF,CAAA,CAAA,CACF,CAAA,CAAA,CAGN,CAIA,SAASuC,EAAW,CAClB,MAAAC,EACA,QAAAC,EACA,MAAAC,EACA,KAAA1C,EACA,SAAAF,EACA,QAAA6C,EACA,MAAAC,CACF,EAQG,CACD,OAAIF,QAECpD,EAAA,CAAK,UAAU,wBACd,SAAAN,EAAAA,KAACO,EAAA,CAAY,UAAU,uDACrB,SAAA,CAAArB,EAAAA,IAACiB,EAAA,CAAQ,UAAU,kBAAA,CAAmB,EACrCuD,EACDxE,EAAAA,IAACmC,EAAA,CAAO,KAAK,KAAK,QAAQ,UAAU,UAAU,UAAU,QAASsC,EAAS,SAAA,OAAA,CAE1E,CAAA,CAAA,CACF,CAAA,CACF,EAIAF,QAEC,MAAA,CAAI,UAAU,YACZ,SAAA,MAAM,KAAK,CAAE,OAAQ,CAAA,CAAG,EAAE,IAAI,CAACI,EAAGnE,UAChCW,GAAA,CAAA,EAAsBX,CAAG,CAC3B,EACH,EAIA8D,EAAM,SAAW,EAEjBtE,EAAAA,IAACoB,EAAA,CACC,SAAAN,EAAAA,KAACO,EAAA,CAAY,UAAU,8DACrB,SAAA,CAAArB,MAAC,MAAA,CAAI,UAAU,wEACZ,SAAA8B,IAAS,OACR9B,MAAC+B,EAAA,CAAO,UAAU,+BAAA,CAAgC,EAElD/B,EAAAA,IAACR,GAAA,CAAO,UAAU,gCAAgC,EAEtD,EACAsB,EAAAA,KAAC,KAAA,CAAG,UAAU,6CAA6C,SAAA,CAAA,MACrDgB,IAAS,OAAS,QAAU,WAAW,MAAA,EAC7C,QACC,IAAA,CAAE,UAAU,yCACV,SAAAA,IAAS,OACN,oEACA,+DACN,EACAhB,EAAAA,KAACqB,EAAA,CAAO,UAAU,OAAO,QAASuC,EAChC,SAAA,CAAA1E,EAAAA,IAAC4E,EAAA,CAAK,UAAU,SAAA,CAAU,EAAE,OACvB9C,IAAS,OAAS,OAAS,SAAA,CAAA,CAClC,CAAA,CAAA,CACF,CAAA,CACF,EAKF9B,EAAAA,IAACe,EAAO,IAAP,CACC,UAAU,YACV,SAAUN,GACV,QAAQ,SACR,QAAQ,UAER,SAAAT,EAAAA,IAACY,GAAgB,KAAK,YACnB,WAAM,IAAI,CAACe,EAAMnB,IAChBR,EAAAA,IAAC0B,GAAA,CAEC,KAAAC,EACA,SAAAC,EACA,MAAOpB,EACP,KAAAsB,CAAA,EAJKH,EAAK,EAAA,CAMb,CAAA,CACH,CAAA,CAAA,CAGN,CAIO,SAASkD,IAAY,CAC1B,KAAM,CAACC,EAAOC,CAAQ,EAAI5B,EAAAA,SAAmB,CAAA,CAAE,EACzC,CAAC6B,EAAUC,CAAW,EAAI9B,EAAAA,SAAmB,CAAA,CAAE,EAC/C,CAAC+B,EAAcC,CAAe,EAAIhC,EAAAA,SAAS,EAAI,EAC/C,CAACiC,EAAiBC,CAAkB,EAAIlC,EAAAA,SAAS,EAAI,EACrD,CAACmC,EAAYC,CAAa,EAAIpC,EAAAA,SAAwB,IAAI,EAC1D,CAACqC,EAAeC,CAAgB,EAAItC,EAAAA,SAAwB,IAAI,EAChE,CAACuC,EAAYC,CAAa,EAAIxC,EAAAA,SAAS,EAAK,EAC5C,CAACyC,EAAYC,CAAa,EAAI1C,EAAAA,SAA6B,MAAM,EACjE,CAACH,EAAY8C,CAAa,EAAI3C,EAAAA,SAAS,EAAK,EAC5C,CAAC4C,EAAWC,CAAY,EAAI7C,EAAAA,SAAS,OAAO,EAC5C,CAACxC,EAAQsF,CAAS,EAAI9C,EAAAA,SAAkB,CAAA,CAAE,EAE1C+C,EAAQC,EAAAA,YAAY,CAACC,EAA2BC,IAAoB,CACxE,MAAMC,EAAK,KAAK,IAAA,EAChBL,EAAWM,GAAS,CAAC,GAAGA,EAAM,CAAE,GAAAD,EAAI,KAAAF,EAAM,QAAAC,CAAA,CAAS,CAAC,EACpD,WAAW,IAAM,CACfJ,EAAWM,GAASA,EAAK,OAAQ1F,IAAMA,GAAE,KAAOyF,CAAE,CAAC,CACrD,EAAG,IAAI,CACT,EAAG,CAAA,CAAE,EAECE,EAAaL,EAAAA,YAAY,SAAY,CACzC,GAAI,CACFhB,EAAgB,EAAI,EACpBI,EAAc,IAAI,EAClB,MAAMkB,EAAM,MAAMC,EAAI,MAAM,OAAO,KAAK,CAAE,KAAM,OAAQ,EACxD3B,EAAS0B,EAAI,QAAQ,CACvB,OAASE,EAAc,CACrBpB,EACEoB,aAAe,MAAQA,EAAI,QAAU,sBAAA,CAEzC,QAAA,CACExB,EAAgB,EAAK,CACvB,CACF,EAAG,CAAA,CAAE,EAECyB,EAAgBT,EAAAA,YAAY,SAAY,CAC5C,GAAI,CACFd,EAAmB,EAAI,EACvBI,EAAiB,IAAI,EACrB,MAAMgB,EAAM,MAAMC,EAAI,MAAM,OAAO,KAAK,CAAE,KAAM,UAAW,EAC3DzB,EAAYwB,EAAI,QAAQ,CAC1B,OAASE,EAAc,CACrBlB,EACEkB,aAAe,MAAQA,EAAI,QAAU,yBAAA,CAEzC,QAAA,CACEtB,EAAmB,EAAK,CAC1B,CACF,EAAG,CAAA,CAAE,EAELwB,EAAAA,UAAU,IAAM,CACdL,EAAA,EACAI,EAAA,CACF,EAAG,CAACJ,EAAYI,CAAa,CAAC,EAE9B,MAAME,EAAchF,GAA6B,CAC/C+D,EAAc/D,CAAI,EAClB6D,EAAc,EAAI,CACpB,EAEMoB,EAAe,MAAOC,GAAuB,CACjDlB,EAAc,EAAI,EAClB,GAAI,CACF,MAAMY,EAAI,MAAM,OAAO,OAAOM,CAAI,EAClCd,EAAM,UAAW,GAAGc,EAAK,OAAS,OAAS,OAAS,SAAS,UAAU,EACvErB,EAAc,EAAK,EACfqB,EAAK,OAAS,OAAQR,EAAA,EACrBI,EAAA,CACP,OAASD,EAAc,CACrBT,EAAM,QAASS,aAAe,MAAQA,EAAI,QAAU,kBAAkB,CACxE,QAAA,CACEb,EAAc,EAAK,CACrB,CACF,EAEMmB,GAAmB,MAAOX,GAAe,CAC7C,GAAI,CACF,MAAMI,EAAI,MAAM,OAAO,OAAOJ,CAAE,EAChCvB,EAAUwB,GAASA,EAAK,OAAQW,GAAMA,EAAE,KAAOZ,CAAE,CAAC,EAClDJ,EAAM,UAAW,cAAc,CACjC,OAASS,EAAc,CACrBT,EAAM,QAASS,aAAe,MAAQA,EAAI,QAAU,kBAAkB,CACxE,CACF,EAEMQ,GAAsB,MAAOb,GAAe,CAChD,GAAI,CACF,MAAMI,EAAI,MAAM,OAAO,OAAOJ,CAAE,EAChCrB,EAAasB,GAASA,EAAK,OAAQa,GAAMA,EAAE,KAAOd,CAAE,CAAC,EACrDJ,EAAM,UAAW,iBAAiB,CACpC,OAASS,EAAc,CACrBT,EAAM,QAASS,aAAe,MAAQA,EAAI,QAAU,kBAAkB,CACxE,CACF,EAEA,OACE7F,EAAAA,KAAC,MAAA,CAAI,UAAU,gBAEb,SAAA,CAAAA,EAAAA,KAACC,EAAO,IAAP,CACC,QAAS,CAAE,QAAS,EAAG,EAAG,EAAA,EAC1B,QAAS,CAAE,QAAS,EAAG,EAAG,CAAA,EAC1B,WAAY,CAAE,SAAU,EAAA,EACxB,UAAU,yCAEV,SAAA,CAAAD,EAAAA,KAAC,MAAA,CAAI,UAAU,0BACb,SAAA,CAAAd,EAAAA,IAAC,OAAI,UAAU,wEACb,eAAC+B,EAAA,CAAO,UAAU,yBAAyB,CAAA,CAC7C,SACC,MAAA,CACC,SAAA,CAAAjB,EAAAA,KAAC,MAAA,CAAI,UAAU,4BACb,SAAA,CAAAd,EAAAA,IAAC,KAAA,CAAG,UAAU,yCAAyC,SAAA,mBAEvD,EACAA,EAAAA,IAACqH,IAAM,QAAQ,YAAY,UAAU,eAClC,SAAAvC,EAAM,OAASE,EAAS,MAAA,CAC3B,CAAA,EACF,EACAhF,EAAAA,IAAC,IAAA,CAAE,UAAU,gCAAgC,SAAA,yCAAA,CAE7C,CAAA,CAAA,CACF,CAAA,EACF,EACAc,EAAAA,KAACqB,EAAA,CACC,QAAS,IACP2E,EAAWf,IAAc,QAAU,OAAS,SAAS,EAGvD,SAAA,CAAA/F,EAAAA,IAAC4E,EAAA,CAAK,UAAU,SAAA,CAAU,EAAE,OACvBmB,IAAc,QAAU,OAAS,SAAA,CAAA,CAAA,CACxC,CAAA,CAAA,EAIF/F,EAAAA,IAACe,EAAO,IAAP,CACC,QAAS,CAAE,QAAS,EAAG,EAAG,CAAA,EAC1B,QAAS,CAAE,QAAS,EAAG,EAAG,CAAA,EAC1B,WAAY,CAAE,MAAO,GAAK,SAAU,EAAA,EAEpC,SAAAD,EAAAA,KAACrB,GAAA,CACC,MAAOsG,EACP,cAAeC,EACf,UAAU,YAEV,SAAA,CAAAlF,EAAAA,KAACnB,EAAA,CAAS,UAAU,mBAClB,SAAA,CAAAmB,EAAAA,KAACX,EAAA,CAAY,MAAM,QAAQ,UAAU,UACnC,SAAA,CAAAH,EAAAA,IAAC+B,EAAA,CAAO,UAAU,aAAA,CAAc,EAAE,QAEjC,CAACmD,GACApE,EAAAA,KAAC,OAAA,CAAK,UAAU,qDAAqD,SAAA,CAAA,IACjEgE,EAAM,OAAO,GAAA,CAAA,CACjB,CAAA,EAEJ,EACAhE,EAAAA,KAACX,EAAA,CAAY,MAAM,WAAW,UAAU,UACtC,SAAA,CAAAH,EAAAA,IAACV,EAAA,CAAa,UAAU,aAAA,CAAc,EAAE,WAEvC,CAAC8F,GACAtE,EAAAA,KAAC,OAAA,CAAK,UAAU,qDAAqD,SAAA,CAAA,IACjEkE,EAAS,OAAO,GAAA,CAAA,CACpB,CAAA,CAAA,CAEJ,CAAA,EACF,EAEAhF,EAAAA,IAACK,EAAA,CAAY,MAAM,QACjB,SAAAL,EAAAA,IAACqE,EAAA,CACC,MAAOS,EACP,QAASI,EACT,MAAOI,EACP,KAAK,OACL,SAAU2B,GACV,QAAST,EACT,MAAO,IAAMM,EAAW,MAAM,CAAA,CAAA,EAElC,EAEA9G,EAAAA,IAACK,EAAA,CAAY,MAAM,WACjB,SAAAL,EAAAA,IAACqE,EAAA,CACC,MAAOW,EACP,QAASI,EACT,MAAOI,EACP,KAAK,UACL,SAAU2B,GACV,QAASP,EACT,MAAO,IAAME,EAAW,SAAS,CAAA,CAAA,CACnC,CACF,CAAA,CAAA,CAAA,CACF,CAAA,EAIF9G,EAAAA,IAAC4C,GAAA,CACC,KAAM8C,EACN,aAAcC,EACd,SAAUoB,EACV,WAAA/D,EACA,KAAM4C,CAAA,CAAA,EAGR5F,MAACU,IAAS,OAAAC,CAAA,CAAgB,CAAA,EAC5B,CAEJ","x_google_ignoreList":[0,1]}
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"Graph-DnlOWkay.js","sources":["../../node_modules/lucide-react/dist/esm/icons/network.js","../../src/pages/brain/Graph.tsx"],"sourcesContent":["/**\n * @license lucide-react v0.511.0 - ISC\n *\n * This source code is licensed under the ISC license.\n * See the LICENSE file in the root directory of this source tree.\n */\n\nimport createLucideIcon from '../createLucideIcon.js';\n\nconst __iconNode = [\n [\"rect\", { x: \"16\", y: \"16\", width: \"6\", height: \"6\", rx: \"1\", key: \"4q2zg0\" }],\n [\"rect\", { x: \"2\", y: \"16\", width: \"6\", height: \"6\", rx: \"1\", key: \"8cvhb9\" }],\n [\"rect\", { x: \"9\", y: \"2\", width: \"6\", height: \"6\", rx: \"1\", key: \"1egb70\" }],\n [\"path\", { d: \"M5 16v-3a1 1 0 0 1 1-1h12a1 1 0 0 1 1 1v3\", key: \"1jsf9p\" }],\n [\"path\", { d: \"M12 12V8\", key: \"2874zd\" }]\n];\nconst Network = createLucideIcon(\"network\", __iconNode);\n\nexport { __iconNode, Network as default };\n//# sourceMappingURL=network.js.map\n","import { useEffect, useRef, useState, useCallback } from \"react\";\nimport { Network, Search, Loader2 } from \"lucide-react\";\nimport api, { type GraphNode, type GraphEdge, type Memory } from \"@/lib/api\";\nimport {\n Dialog,\n DialogContent,\n DialogHeader,\n DialogTitle,\n} from \"@/components/ui/dialog\";\n\n// ── Node type color map ──\nconst TYPE_COLORS: Record<string, string> = {\n fact: \"#3b82f6\",\n preference: \"#a78bfa\",\n experience: \"#22c55e\",\n goal: \"#f59e0b\",\n project: \"#00d4ff\",\n person: \"#ec4899\",\n skill: \"#6366f1\",\n belief: \"#f97316\",\n observation: \"#14b8a6\",\n default: \"#6b7280\",\n};\n\nfunction getTypeColor(type: string): string {\n return TYPE_COLORS[type] || TYPE_COLORS.default;\n}\n\n// ── Internal layout types ──\ninterface NodePos {\n x: number;\n y: number;\n}\n\ninterface NodeVelocity {\n seed: number;\n freq: number;\n amp: number;\n}\n\ninterface TooltipInfo {\n x: number;\n y: number;\n node: GraphNode;\n connections: number;\n}\n\nfunction isDarkMode(): boolean {\n return (\n document.documentElement.classList.contains(\"dark\") ||\n document.documentElement.getAttribute(\"data-theme\") !== \"light\"\n );\n}\n\nexport function GraphPage() {\n const canvasRef = useRef<HTMLCanvasElement>(null);\n const containerRef = useRef<HTMLDivElement>(null);\n\n const [loading, setLoading] = useState(true);\n const [nodes, setNodes] = useState<GraphNode[]>([]);\n const [edges, setEdges] = useState<GraphEdge[]>([]);\n const [searchQuery, setSearchQuery] = useState(\"\");\n const [tooltip, setTooltip] = useState<TooltipInfo | null>(null);\n\n // Detail dialog state — opens on single-click of a node.\n const [detailOpen, setDetailOpen] = useState(false);\n const [detailNode, setDetailNode] = useState<GraphNode | null>(null);\n const [detailMemory, setDetailMemory] = useState<Memory | null>(null);\n const [detailLoading, setDetailLoading] = useState(false);\n const [detailError, setDetailError] = useState<string | null>(null);\n\n // Mutable refs for canvas state (avoid re-renders during animation)\n const stateRef = useRef({\n nodes: [] as GraphNode[],\n edges: [] as GraphEdge[],\n positions: new Map<string, NodePos>(),\n anchors: new Map<string, NodePos>(),\n velocities: new Map<string, NodeVelocity>(),\n pan: { x: 0, y: 0 },\n zoom: 1,\n dragging: false,\n dragNode: null as GraphNode | null,\n hoveredNode: null as GraphNode | null,\n selectedNode: null as GraphNode | null,\n lastMouse: { x: 0, y: 0 },\n // Press tracking — used to distinguish a click from a drag.\n pressNode: null as GraphNode | null,\n pressX: 0,\n pressY: 0,\n pressT: 0,\n moved: false,\n searchQuery: \"\",\n animFrame: 0,\n dpr: 1,\n });\n\n // Keep searchQuery in sync with ref\n useEffect(() => {\n stateRef.current.searchQuery = searchQuery;\n }, [searchQuery]);\n\n // ── Connection count helper ──\n const connectionCount = useCallback((nodeId: string, edgeList: GraphEdge[]) => {\n let count = 0;\n for (const e of edgeList) {\n if (e.source === nodeId || e.target === nodeId) count++;\n }\n return count;\n }, []);\n\n // ── Init positions in a circle ──\n const initPositions = useCallback(\n (nodeList: GraphNode[], canvasW: number, canvasH: number) => {\n const s = stateRef.current;\n const cx = canvasW / 2;\n const cy = canvasH / 2;\n s.positions.clear();\n s.anchors.clear();\n s.velocities.clear();\n\n nodeList.forEach((node, i) => {\n const angle = (i / nodeList.length) * Math.PI * 2;\n const r = 150 + Math.random() * 100;\n const x = cx + r * Math.cos(angle);\n const y = cy + r * Math.sin(angle);\n s.positions.set(node.id, { x, y });\n s.anchors.set(node.id, { x, y });\n s.velocities.set(node.id, {\n seed: Math.random(),\n freq: 0.00009 + Math.random() * 0.00007,\n amp: 0.25 + Math.random() * 0.25,\n });\n });\n },\n []\n );\n\n // ── Force-directed layout (80 iterations) ──\n const runLayout = useCallback(\n (nodeList: GraphNode[], edgeList: GraphEdge[], w: number, h: number) => {\n const s = stateRef.current;\n const iters = 80;\n\n for (let iter = 0; iter < iters; iter++) {\n const area = w * h;\n const k = Math.sqrt(area / Math.max(1, nodeList.length));\n const repForce = k * k;\n const attForce = 0.01;\n const forces = new Map<string, { fx: number; fy: number }>();\n nodeList.forEach((n) => forces.set(n.id, { fx: 0, fy: 0 }));\n\n // Repulsion (Coulomb)\n for (let i = 0; i < nodeList.length; i++) {\n for (let j = i + 1; j < nodeList.length; j++) {\n const pi = s.positions.get(nodeList[i].id);\n const pj = s.positions.get(nodeList[j].id);\n if (!pi || !pj) continue;\n const dx = pi.x - pj.x;\n const dy = pi.y - pj.y;\n const dist = Math.max(Math.sqrt(dx * dx + dy * dy), 1);\n const f = repForce / (dist * dist);\n const fx = (dx / dist) * f;\n const fy = (dy / dist) * f;\n forces.get(nodeList[i].id)!.fx += fx;\n forces.get(nodeList[i].id)!.fy += fy;\n forces.get(nodeList[j].id)!.fx -= fx;\n forces.get(nodeList[j].id)!.fy -= fy;\n }\n }\n\n // Attraction (Hooke) along edges\n edgeList.forEach((e) => {\n const ps = s.positions.get(e.source);\n const pt = s.positions.get(e.target);\n if (!ps || !pt) return;\n const dx = pt.x - ps.x;\n const dy = pt.y - ps.y;\n const fs = forces.get(e.source);\n const ft = forces.get(e.target);\n if (fs) {\n fs.fx += dx * attForce;\n fs.fy += dy * attForce;\n }\n if (ft) {\n ft.fx -= dx * attForce;\n ft.fy -= dy * attForce;\n }\n });\n\n // Center gravity\n const cx = w / 2;\n const cy = h / 2;\n const gravity = 0.001;\n nodeList.forEach((n) => {\n const p = s.positions.get(n.id);\n const f = forces.get(n.id);\n if (!p || !f) return;\n f.fx += (cx - p.x) * gravity;\n f.fy += (cy - p.y) * gravity;\n });\n\n // Apply with damping\n const damp = 0.1;\n nodeList.forEach((n) => {\n const f = forces.get(n.id);\n const p = s.positions.get(n.id);\n if (!f || !p) return;\n p.x += f.fx * damp;\n p.y += f.fy * damp;\n });\n }\n\n // Sync anchors\n nodeList.forEach((n) => {\n const p = s.positions.get(n.id);\n const a = s.anchors.get(n.id);\n if (p && a) {\n a.x = p.x;\n a.y = p.y;\n }\n });\n },\n []\n );\n\n // ── Resize canvas with DPR ──\n const resizeCanvas = useCallback(() => {\n const canvas = canvasRef.current;\n const container = containerRef.current;\n if (!canvas || !container) return;\n\n const dpr = window.devicePixelRatio || 1;\n stateRef.current.dpr = dpr;\n const w = container.clientWidth;\n const h = container.clientHeight;\n canvas.width = w * dpr;\n canvas.height = h * dpr;\n canvas.style.width = `${w}px`;\n canvas.style.height = `${h}px`;\n }, []);\n\n // ── Screen → graph coordinate transform ──\n const screenToGraph = useCallback(\n (sx: number, sy: number): { x: number; y: number } => {\n const s = stateRef.current;\n const dpr = s.dpr;\n return {\n x: (sx * dpr - s.pan.x) / s.zoom,\n y: (sy * dpr - s.pan.y) / s.zoom,\n };\n },\n []\n );\n\n // ── Hit test ──\n const findNodeAt = useCallback(\n (gx: number, gy: number): GraphNode | null => {\n const s = stateRef.current;\n for (let i = s.nodes.length - 1; i >= 0; i--) {\n const n = s.nodes[i];\n const p = s.positions.get(n.id);\n if (!p) continue;\n const r = (n.size || 8) * 1.5;\n const dx = gx - p.x;\n const dy = gy - p.y;\n if (dx * dx + dy * dy < r * r) return n;\n }\n return null;\n },\n []\n );\n\n // ── Draw ──\n const draw = useCallback((ts: number) => {\n const canvas = canvasRef.current;\n if (!canvas) return;\n const ctx = canvas.getContext(\"2d\");\n if (!ctx) return;\n\n const s = stateRef.current;\n const dpr = s.dpr;\n const w = canvas.width;\n const h = canvas.height;\n const dark = isDarkMode();\n\n ctx.clearRect(0, 0, w, h);\n\n // Background\n ctx.fillStyle = dark ? \"#0a0e14\" : \"#ffffff\";\n ctx.fillRect(0, 0, w, h);\n\n ctx.save();\n ctx.translate(s.pan.x, s.pan.y);\n ctx.scale(s.zoom, s.zoom);\n\n // Focus neighborhood\n const focus = s.hoveredNode || s.selectedNode;\n const neighbors = new Set<string>();\n const activeEdgeIdx = new Set<number>();\n if (focus) {\n s.edges.forEach((e, i) => {\n if (e.source === focus.id) {\n neighbors.add(e.target);\n activeEdgeIdx.add(i);\n }\n if (e.target === focus.id) {\n neighbors.add(e.source);\n activeEdgeIdx.add(i);\n }\n });\n neighbors.add(focus.id);\n }\n\n // ── Edges ──\n s.edges.forEach((e, i) => {\n const ps = s.positions.get(e.source);\n const pt = s.positions.get(e.target);\n if (!ps || !pt) return;\n\n const active = activeEdgeIdx.has(i);\n if (active) {\n ctx.strokeStyle = dark\n ? \"rgba(0,212,255,0.7)\"\n : \"rgba(0,136,170,0.6)\";\n ctx.lineWidth = (2 * dpr) / s.zoom;\n } else if (focus) {\n ctx.strokeStyle = dark\n ? \"rgba(0,212,255,0.06)\"\n : \"rgba(0,136,170,0.05)\";\n ctx.lineWidth = (0.6 * dpr) / s.zoom;\n } else {\n const pulse = (Math.sin(ts * 0.00022 + i * 1.3) + 1) * 0.5;\n const alpha = (dark ? 0.16 : 0.13) + pulse * 0.06;\n ctx.strokeStyle = dark\n ? `rgba(0,212,255,${alpha.toFixed(3)})`\n : `rgba(0,136,170,${alpha.toFixed(3)})`;\n ctx.lineWidth = ((0.7 + pulse * 0.3) * dpr) / s.zoom;\n }\n\n ctx.beginPath();\n ctx.moveTo(ps.x, ps.y);\n ctx.lineTo(pt.x, pt.y);\n ctx.stroke();\n });\n\n // ── Nodes ──\n const searchQ = s.searchQuery.toLowerCase();\n\n s.nodes.forEach((n) => {\n const p = s.positions.get(n.id);\n if (!p) return;\n\n const isHovered = s.hoveredNode?.id === n.id;\n const isSelected = s.selectedNode?.id === n.id;\n const isNeighbor = neighbors.has(n.id);\n\n const v = s.velocities.get(n.id);\n const breathe =\n 1 + Math.sin(ts * 0.00035 + (v?.seed ?? 0) * 11.7) * 0.01;\n const baseR = (n.size || 8) * dpr;\n const r = baseR * (isHovered || isSelected ? 1.4 : breathe);\n\n // Alpha based on search / focus\n let alpha = 1;\n if (searchQ) {\n const hay = (n.fullLabel || n.label).toLowerCase();\n alpha = hay.includes(searchQ) ? 1 : 0.12;\n } else if (focus) {\n alpha = isHovered || isSelected || isNeighbor ? 1 : 0.18;\n }\n ctx.globalAlpha = alpha;\n\n // Glow\n if (isHovered || isSelected) {\n ctx.beginPath();\n ctx.arc(p.x, p.y, r + (5 * dpr) / s.zoom, 0, Math.PI * 2);\n ctx.fillStyle = dark\n ? \"rgba(0,212,255,0.14)\"\n : \"rgba(0,136,170,0.12)\";\n ctx.fill();\n }\n\n // Node circle\n ctx.beginPath();\n ctx.arc(p.x, p.y, r, 0, Math.PI * 2);\n ctx.fillStyle = getTypeColor(n.type);\n ctx.fill();\n\n // Stroke\n if (isHovered || isSelected) {\n ctx.strokeStyle = dark ? \"#f0f0f0\" : \"#1a1a1a\";\n ctx.lineWidth = (2 * dpr) / s.zoom;\n ctx.stroke();\n } else if (isNeighbor && focus) {\n ctx.strokeStyle = dark\n ? \"rgba(0,212,255,0.65)\"\n : \"rgba(0,136,170,0.55)\";\n ctx.lineWidth = (1.8 * dpr) / s.zoom;\n ctx.stroke();\n }\n\n // Label — only for hovered / selected node. Keep it short (truncated `label`)\n // since the full text is shown in the tooltip / detail dialog instead.\n // This keeps the canvas clean and readable.\n if (isHovered || isSelected) {\n const fontSize = Math.max(10 * dpr, (11 * dpr) / s.zoom);\n ctx.font = `${fontSize}px -apple-system, BlinkMacSystemFont, \"Segoe UI\", sans-serif`;\n ctx.textAlign = \"center\";\n ctx.textBaseline = \"top\";\n\n // Background pill for legibility\n const text = n.label;\n const metrics = ctx.measureText(text);\n const padX = 6 * dpr;\n const padY = 3 * dpr;\n const bx = p.x - metrics.width / 2 - padX;\n const by = p.y + r + 4 * dpr;\n const bw = metrics.width + padX * 2;\n const bh = fontSize + padY * 2;\n ctx.fillStyle = dark ? \"rgba(10,14,20,0.92)\" : \"rgba(255,255,255,0.95)\";\n ctx.beginPath();\n ctx.roundRect?.(bx, by, bw, bh, 4 * dpr);\n ctx.fill();\n\n ctx.fillStyle = dark\n ? `rgba(240,240,240,${alpha})`\n : `rgba(20,20,20,${alpha})`;\n ctx.fillText(text, p.x, by + padY);\n }\n\n ctx.globalAlpha = 1;\n });\n\n ctx.restore();\n }, []);\n\n // ── Motion update (breathing drift) ──\n const updateMotion = useCallback((ts: number) => {\n const s = stateRef.current;\n s.nodes.forEach((n) => {\n if (s.dragNode?.id === n.id) return;\n const p = s.positions.get(n.id);\n const a = s.anchors.get(n.id);\n const v = s.velocities.get(n.id);\n if (!p || !a || !v) return;\n p.x = a.x + Math.sin(ts * v.freq + v.seed * 11.1) * v.amp;\n p.y = a.y + Math.cos(ts * v.freq * 0.87 + v.seed * 17.3) * v.amp;\n });\n }, []);\n\n // ── Open detail dialog for a node (fetches full memory record) ──\n const openNodeDetail = useCallback(async (node: GraphNode) => {\n setDetailNode(node);\n setDetailMemory(null);\n setDetailError(null);\n setDetailOpen(true);\n setDetailLoading(true);\n stateRef.current.selectedNode = node;\n try {\n const mem = await api.brain.memory.get(node.id);\n setDetailMemory(mem);\n } catch (err) {\n // Not every node has a backing memory record (graph may include\n // person / goal aggregates) — fall back gracefully to node-only info.\n setDetailError(\n err instanceof Error ? err.message : \"Failed to load details\"\n );\n } finally {\n setDetailLoading(false);\n }\n }, []);\n\n // ── Mouse handlers ──\n const onMouseDown = useCallback(\n (e: MouseEvent) => {\n const canvas = canvasRef.current;\n if (!canvas) return;\n const rect = canvas.getBoundingClientRect();\n const sx = e.clientX - rect.left;\n const sy = e.clientY - rect.top;\n const gp = screenToGraph(sx, sy);\n const node = findNodeAt(gp.x, gp.y);\n const s = stateRef.current;\n\n s.pressNode = node;\n s.pressX = e.clientX;\n s.pressY = e.clientY;\n s.pressT = performance.now();\n s.moved = false;\n\n if (node) {\n s.dragNode = node;\n } else {\n s.dragging = true;\n }\n s.lastMouse = { x: e.clientX, y: e.clientY };\n },\n [screenToGraph, findNodeAt]\n );\n\n const onMouseMove = useCallback(\n (e: MouseEvent) => {\n const canvas = canvasRef.current;\n if (!canvas) return;\n const rect = canvas.getBoundingClientRect();\n const sx = e.clientX - rect.left;\n const sy = e.clientY - rect.top;\n const s = stateRef.current;\n\n // Track whether the mouse has moved meaningfully since press.\n // 4px threshold lets micro-jitter still count as a click.\n if (s.pressT && !s.moved) {\n const ddx = e.clientX - s.pressX;\n const ddy = e.clientY - s.pressY;\n if (ddx * ddx + ddy * ddy > 16) s.moved = true;\n }\n\n if (s.dragNode) {\n const gp = screenToGraph(sx, sy);\n const p = s.positions.get(s.dragNode.id);\n const a = s.anchors.get(s.dragNode.id);\n if (p) {\n p.x = gp.x;\n p.y = gp.y;\n }\n if (a) {\n a.x = gp.x;\n a.y = gp.y;\n }\n } else if (s.dragging) {\n const dpr = s.dpr;\n s.pan.x += (e.clientX - s.lastMouse.x) * dpr;\n s.pan.y += (e.clientY - s.lastMouse.y) * dpr;\n } else {\n const gp = screenToGraph(sx, sy);\n const node = findNodeAt(gp.x, gp.y);\n if (node !== s.hoveredNode) {\n s.hoveredNode = node;\n if (node) {\n setTooltip({\n x: e.clientX - rect.left + 14,\n y: e.clientY - rect.top + 14,\n node,\n connections: connectionCount(node.id, s.edges),\n });\n } else {\n setTooltip(null);\n }\n } else if (node && tooltip) {\n setTooltip((prev) =>\n prev\n ? {\n ...prev,\n x: e.clientX - rect.left + 14,\n y: e.clientY - rect.top + 14,\n }\n : null\n );\n }\n }\n s.lastMouse = { x: e.clientX, y: e.clientY };\n },\n [screenToGraph, findNodeAt, connectionCount, tooltip]\n );\n\n const onMouseUp = useCallback(() => {\n const s = stateRef.current;\n const wasClick =\n !s.moved &&\n s.pressNode !== null &&\n performance.now() - s.pressT < 500;\n const clickedNode = s.pressNode;\n\n s.dragNode = null;\n s.dragging = false;\n s.pressNode = null;\n s.pressT = 0;\n s.moved = false;\n\n if (wasClick && clickedNode) {\n openNodeDetail(clickedNode);\n }\n }, [openNodeDetail]);\n\n const onWheel = useCallback(\n (e: WheelEvent) => {\n e.preventDefault();\n const s = stateRef.current;\n const delta = e.deltaY > 0 ? 0.92 : 1.08;\n const newZoom = Math.min(3.0, Math.max(0.3, s.zoom * delta));\n const scaleFactor = newZoom / s.zoom;\n\n const canvas = canvasRef.current;\n if (!canvas) return;\n const rect = canvas.getBoundingClientRect();\n const mx = (e.clientX - rect.left) * s.dpr;\n const my = (e.clientY - rect.top) * s.dpr;\n\n s.pan.x = mx - (mx - s.pan.x) * scaleFactor;\n s.pan.y = my - (my - s.pan.y) * scaleFactor;\n s.zoom = newZoom;\n },\n []\n );\n\n // ── Main effect: fetch, layout, animate ──\n useEffect(() => {\n let cancelled = false;\n\n async function init() {\n setLoading(true);\n try {\n const data = await api.brain.graph();\n if (cancelled) return;\n const n = data.nodes || [];\n const e = data.edges || [];\n setNodes(n);\n setEdges(e);\n\n const s = stateRef.current;\n s.nodes = n;\n s.edges = e;\n\n resizeCanvas();\n const canvas = canvasRef.current;\n const cw = canvas ? canvas.width : 800;\n const ch = canvas ? canvas.height : 600;\n\n initPositions(n, cw, ch);\n runLayout(n, e, cw, ch);\n } catch (err) {\n console.error(\"Failed to load graph data:\", err);\n }\n if (!cancelled) setLoading(false);\n }\n\n init();\n return () => {\n cancelled = true;\n };\n }, [initPositions, runLayout, resizeCanvas]);\n\n // ── Animation loop + event listeners ──\n useEffect(() => {\n const canvas = canvasRef.current;\n if (!canvas || loading) return;\n\n resizeCanvas();\n\n // Animation loop\n let running = true;\n const loop = (ts: number) => {\n if (!running) return;\n updateMotion(ts);\n draw(ts);\n stateRef.current.animFrame = requestAnimationFrame(loop);\n };\n stateRef.current.animFrame = requestAnimationFrame(loop);\n\n // Event listeners\n canvas.addEventListener(\"mousedown\", onMouseDown);\n canvas.addEventListener(\"mousemove\", onMouseMove);\n canvas.addEventListener(\"mouseup\", onMouseUp);\n canvas.addEventListener(\"mouseleave\", onMouseUp);\n canvas.addEventListener(\"wheel\", onWheel, { passive: false });\n\n const handleResize = () => {\n resizeCanvas();\n };\n window.addEventListener(\"resize\", handleResize);\n\n return () => {\n running = false;\n cancelAnimationFrame(stateRef.current.animFrame);\n canvas.removeEventListener(\"mousedown\", onMouseDown);\n canvas.removeEventListener(\"mousemove\", onMouseMove);\n canvas.removeEventListener(\"mouseup\", onMouseUp);\n canvas.removeEventListener(\"mouseleave\", onMouseUp);\n canvas.removeEventListener(\"wheel\", onWheel);\n window.removeEventListener(\"resize\", handleResize);\n };\n }, [\n loading,\n resizeCanvas,\n updateMotion,\n draw,\n onMouseDown,\n onMouseMove,\n onMouseUp,\n onWheel,\n ]);\n\n // ── Legend entries ──\n const legendEntries = nodes.length\n ? [...new Set(nodes.map((n) => n.type))].sort()\n : [];\n\n return (\n <div className=\"flex h-full flex-col\">\n {/* Header */}\n <div className=\"flex items-center justify-between border-b border-border/50 bg-background/80 px-6 py-4 backdrop-blur-sm\">\n <div className=\"flex items-center gap-3\">\n <div className=\"flex h-9 w-9 items-center justify-center rounded-lg bg-[#00d4ff]/10\">\n <Network className=\"h-5 w-5 text-[#00d4ff]\" />\n </div>\n <div>\n <h1 className=\"text-xl font-semibold tracking-tight text-foreground\">\n Knowledge Graph\n </h1>\n <p className=\"text-xs text-muted-foreground\">\n Visualize connections in Mercury's memory\n </p>\n </div>\n </div>\n </div>\n\n {/* Canvas area */}\n <div\n ref={containerRef}\n className=\"relative flex-1\"\n style={{ minHeight: 500 }}\n >\n {loading && (\n <div className=\"absolute inset-0 z-20 flex items-center justify-center bg-background/60 backdrop-blur-sm\">\n <div className=\"flex flex-col items-center gap-3\">\n <Loader2 className=\"h-8 w-8 animate-spin text-[#00d4ff]\" />\n <span className=\"text-sm text-muted-foreground\">\n Loading knowledge graph...\n </span>\n </div>\n </div>\n )}\n\n {!loading && nodes.length === 0 && (\n <div className=\"absolute inset-0 z-20 flex items-center justify-center\">\n <div className=\"flex flex-col items-center gap-3 text-center\">\n <Network className=\"h-12 w-12 text-muted-foreground/40\" />\n <p className=\"text-sm text-muted-foreground\">\n No knowledge graph data available yet\n </p>\n </div>\n </div>\n )}\n\n <canvas\n ref={canvasRef}\n className={`absolute inset-0 h-full w-full ${tooltip ? \"cursor-pointer\" : \"cursor-grab\"}`}\n />\n\n {/* Search overlay */}\n <div className=\"absolute right-4 top-4 z-10\">\n <div className=\"flex items-center gap-2 rounded-lg border border-border/60 bg-background/90 px-3 py-1.5 shadow-lg backdrop-blur-sm\">\n <Search className=\"h-4 w-4 text-muted-foreground\" />\n <input\n type=\"text\"\n placeholder=\"Search nodes...\"\n value={searchQuery}\n onChange={(e) => setSearchQuery(e.target.value)}\n className=\"w-48 border-none bg-transparent text-sm text-foreground outline-none placeholder:text-muted-foreground/60\"\n />\n </div>\n </div>\n\n {/* Legend overlay */}\n {legendEntries.length > 0 && (\n <div className=\"absolute bottom-4 left-4 z-10 rounded-lg border border-border/60 bg-background/90 px-3 py-2.5 shadow-lg backdrop-blur-sm\">\n <p className=\"mb-1.5 text-[10px] font-medium uppercase tracking-wider text-muted-foreground\">\n Node Types\n </p>\n <div className=\"flex flex-col gap-1\">\n {legendEntries.map((type) => (\n <div key={type} className=\"flex items-center gap-2\">\n <span\n className=\"inline-block h-2.5 w-2.5 rounded-full\"\n style={{ backgroundColor: getTypeColor(type) }}\n />\n <span className=\"text-[11px] capitalize text-foreground/80\">\n {type}\n </span>\n </div>\n ))}\n </div>\n </div>\n )}\n\n {/* Tooltip */}\n {tooltip && (\n <div\n className=\"pointer-events-none absolute z-30 rounded-lg border border-border/60 bg-popover/95 px-3 py-2 shadow-xl backdrop-blur-sm\"\n style={{\n left: tooltip.x,\n top: tooltip.y,\n maxWidth: 320,\n // Flip horizontally near the right edge of the container so the\n // tooltip never gets clipped or pushes off-screen.\n transform:\n containerRef.current &&\n tooltip.x + 340 > containerRef.current.clientWidth\n ? \"translateX(calc(-100% - 28px))\"\n : undefined,\n }}\n >\n <p className=\"break-words text-sm font-medium leading-snug text-foreground\">\n {tooltip.node.fullLabel || tooltip.node.label}\n </p>\n <div className=\"mt-1 flex items-center gap-2\">\n <span\n className=\"inline-block h-2 w-2 rounded-full\"\n style={{ backgroundColor: getTypeColor(tooltip.node.type) }}\n />\n <span className=\"text-xs capitalize text-muted-foreground\">\n {tooltip.node.type}\n </span>\n <span className=\"text-xs text-muted-foreground/60\">·</span>\n <span className=\"text-xs text-muted-foreground\">\n {tooltip.connections} connection\n {tooltip.connections !== 1 ? \"s\" : \"\"}\n </span>\n </div>\n <p className=\"mt-1.5 text-[10px] uppercase tracking-wider text-muted-foreground/70\">\n Click for details\n </p>\n </div>\n )}\n </div>\n\n {/* Node detail dialog */}\n <NodeDetailDialog\n open={detailOpen}\n onOpenChange={(v) => {\n setDetailOpen(v);\n if (!v) {\n stateRef.current.selectedNode = null;\n }\n }}\n node={detailNode}\n memory={detailMemory}\n loading={detailLoading}\n error={detailError}\n connections={\n detailNode ? connectionCount(detailNode.id, edges) : 0\n }\n />\n </div>\n );\n}\n\n// ── Detail dialog ──\ninterface NodeDetailDialogProps {\n open: boolean;\n onOpenChange: (open: boolean) => void;\n node: GraphNode | null;\n memory: Memory | null;\n loading: boolean;\n error: string | null;\n connections: number;\n}\n\nfunction formatTs(ts: string | number | undefined): string {\n if (!ts) return \"—\";\n const d = typeof ts === \"number\" ? new Date(ts) : new Date(ts);\n if (Number.isNaN(d.getTime())) return String(ts);\n return d.toLocaleString();\n}\n\nfunction NodeDetailDialog({\n open,\n onOpenChange,\n node,\n memory,\n loading,\n error,\n connections,\n}: NodeDetailDialogProps) {\n if (!node) return null;\n const color = getTypeColor(node.type);\n const fullLabel = node.fullLabel || node.label;\n const summary = memory?.summary || fullLabel;\n const detail = memory?.detail;\n\n return (\n <Dialog open={open} onOpenChange={onOpenChange}>\n <DialogContent className=\"max-w-2xl\">\n <DialogHeader>\n <div className=\"flex items-center gap-2\">\n <span\n className=\"inline-block h-3 w-3 rounded-full\"\n style={{ backgroundColor: color }}\n />\n <span className=\"text-xs font-medium uppercase tracking-wider text-muted-foreground\">\n {node.type}\n </span>\n </div>\n <DialogTitle className=\"mt-1 break-words text-lg leading-snug\">\n {summary}\n </DialogTitle>\n </DialogHeader>\n\n {loading && (\n <div className=\"flex items-center gap-2 py-4 text-sm text-muted-foreground\">\n <Loader2 className=\"h-4 w-4 animate-spin\" />\n Loading details…\n </div>\n )}\n\n {!loading && memory && (\n <div className=\"space-y-4\">\n {detail && (\n <div>\n <p className=\"mb-1 text-[10px] font-medium uppercase tracking-wider text-muted-foreground\">\n Detail\n </p>\n <p className=\"whitespace-pre-wrap break-words text-sm leading-relaxed text-foreground/90\">\n {detail}\n </p>\n </div>\n )}\n\n <div className=\"grid grid-cols-2 gap-3 text-xs sm:grid-cols-3\">\n {memory.scope && (\n <DetailField label=\"Scope\" value={memory.scope} />\n )}\n {typeof memory.importance === \"number\" && (\n <DetailField\n label=\"Importance\"\n value={memory.importance.toFixed(2)}\n />\n )}\n {typeof memory.confidence === \"number\" && (\n <DetailField\n label=\"Confidence\"\n value={memory.confidence.toFixed(2)}\n />\n )}\n {typeof memory.evidenceCount === \"number\" && (\n <DetailField\n label=\"Evidence\"\n value={String(memory.evidenceCount)}\n />\n )}\n <DetailField label=\"Connections\" value={String(connections)} />\n {memory.evidenceKind && (\n <DetailField label=\"Source\" value={memory.evidenceKind} />\n )}\n <DetailField label=\"Created\" value={formatTs(memory.createdAt)} />\n {memory.updatedAt && (\n <DetailField label=\"Updated\" value={formatTs(memory.updatedAt)} />\n )}\n {memory.lastSeenAt && (\n <DetailField\n label=\"Last seen\"\n value={formatTs(memory.lastSeenAt)}\n />\n )}\n </div>\n\n <div className=\"border-t border-border/40 pt-2\">\n <p className=\"font-mono text-[10px] text-muted-foreground/70\">\n {memory.id}\n </p>\n </div>\n </div>\n )}\n\n {!loading && !memory && (\n <div className=\"space-y-3\">\n <p className=\"whitespace-pre-wrap break-words text-sm leading-relaxed text-foreground/90\">\n {fullLabel}\n </p>\n <div className=\"grid grid-cols-2 gap-3 text-xs\">\n <DetailField label=\"Type\" value={node.type} />\n <DetailField label=\"Connections\" value={String(connections)} />\n {typeof node.importance === \"number\" && (\n <DetailField\n label=\"Importance\"\n value={node.importance.toFixed(2)}\n />\n )}\n {typeof node.confidence === \"number\" && (\n <DetailField\n label=\"Confidence\"\n value={node.confidence.toFixed(2)}\n />\n )}\n </div>\n {error && (\n <p className=\"text-xs text-muted-foreground/70\">\n Could not load full record: {error}\n </p>\n )}\n <p className=\"font-mono text-[10px] text-muted-foreground/70\">\n {node.id}\n </p>\n </div>\n )}\n </DialogContent>\n </Dialog>\n );\n}\n\nfunction DetailField({ label, value }: { label: string; value: string }) {\n return (\n <div>\n <p className=\"text-[10px] font-medium uppercase tracking-wider text-muted-foreground\">\n {label}\n </p>\n <p className=\"mt-0.5 break-words text-foreground/90\">{value}</p>\n </div>\n );\n}\n"],"names":["__iconNode","Network","createLucideIcon","TYPE_COLORS","getTypeColor","type","isDarkMode","GraphPage","canvasRef","useRef","containerRef","loading","setLoading","useState","nodes","setNodes","edges","setEdges","searchQuery","setSearchQuery","tooltip","setTooltip","detailOpen","setDetailOpen","detailNode","setDetailNode","detailMemory","setDetailMemory","detailLoading","setDetailLoading","detailError","setDetailError","stateRef","useEffect","connectionCount","useCallback","nodeId","edgeList","count","e","initPositions","nodeList","canvasW","canvasH","s","cx","cy","node","i","angle","r","x","y","runLayout","w","h","iters","iter","area","k","repForce","attForce","forces","n","j","pi","pj","dx","dy","dist","f","fx","fy","ps","pt","fs","ft","gravity","p","damp","a","resizeCanvas","canvas","container","dpr","screenToGraph","sx","sy","findNodeAt","gx","gy","draw","ts","ctx","dark","focus","neighbors","activeEdgeIdx","pulse","alpha","searchQ","isHovered","_a","isSelected","_b","isNeighbor","v","breathe","fontSize","text","metrics","padX","padY","bx","by","bw","bh","_c","updateMotion","openNodeDetail","mem","api","err","onMouseDown","rect","gp","onMouseMove","ddx","ddy","prev","onMouseUp","wasClick","clickedNode","onWheel","delta","newZoom","scaleFactor","mx","my","cancelled","init","data","cw","ch","running","loop","handleResize","legendEntries","jsxs","jsx","Loader2","Search","NodeDetailDialog","formatTs","d","open","onOpenChange","memory","error","connections","color","fullLabel","summary","detail","Dialog","DialogContent","DialogHeader","DialogTitle","DetailField","label","value"],"mappings":"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","x_google_ignoreList":[0]}
|