@tangle-network/ui 11.10.0 → 11.11.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (130) hide show
  1. package/CHANGELOG.md +8 -0
  2. package/dist/active-sessions-store-Gt1R0rFG.js +262 -0
  3. package/dist/{active-sessions-store-CeOmXgv5.d.ts → active-sessions-store-nl70ZnMC.d.ts} +40 -41
  4. package/dist/artifact-pane-BL_DFWNl.d.ts +32 -0
  5. package/dist/artifact-pane-DMXT9a8U.js +70 -0
  6. package/dist/auth-DixfCMCk.js +154 -0
  7. package/dist/auth.d.ts +2 -74
  8. package/dist/auth.js +2 -16
  9. package/dist/branding-26d5ARIr.d.ts +14 -0
  10. package/dist/button-uhNnwdsD.js +78 -0
  11. package/dist/button-yoIv77e2.d.ts +16 -0
  12. package/dist/chat-CPLL0Fd9.js +667 -0
  13. package/dist/chat.d.ts +2 -201
  14. package/dist/chat.js +2 -31
  15. package/dist/code-block-B9miUPht.d.ts +23 -0
  16. package/dist/code-block-CngSn37j.js +165 -0
  17. package/dist/diff-preview-cySuqowW.js +533 -0
  18. package/dist/document-editor-pane-BcoABlhn.d.ts +131 -0
  19. package/dist/document-editor-pane-Cz6oEF1o.js +1287 -0
  20. package/dist/dropdown-menu-BpcLa5vF.js +101 -0
  21. package/dist/editor.d.ts +76 -78
  22. package/dist/editor.js +2 -34
  23. package/dist/file-format-BgXbr-Ib.js +160 -0
  24. package/dist/files-CYlOo0mE.js +743 -0
  25. package/dist/files.d.ts +2 -243
  26. package/dist/files.js +3 -41
  27. package/dist/focus-Cw02pNSr.js +56 -0
  28. package/dist/format-DfcLWqMa.js +54 -0
  29. package/dist/hooks.d.ts +30 -37
  30. package/dist/hooks.js +111 -46
  31. package/dist/index-2UntyjBb.d.ts +52 -0
  32. package/dist/index-COgqsFAQ.d.ts +42 -0
  33. package/dist/index-CPDET_s1.d.ts +549 -0
  34. package/dist/index-CUhfHT_V.d.ts +204 -0
  35. package/dist/index-Cg6gYAqh.d.ts +73 -0
  36. package/dist/index-Cq-EJzqW.d.ts +16 -0
  37. package/dist/index-DhYmSaLF.d.ts +245 -0
  38. package/dist/index-DjKxO357.d.ts +128 -0
  39. package/dist/index-b56ew9aF.d.ts +107 -0
  40. package/dist/index.d.ts +26 -43
  41. package/dist/index.js +35 -472
  42. package/dist/markdown-BprL96Gl.js +45 -0
  43. package/dist/markdown.d.ts +3 -18
  44. package/dist/markdown.js +3 -15
  45. package/dist/message-vhUI0c5G.d.ts +16 -0
  46. package/dist/nav.d.ts +6 -8
  47. package/dist/nav.js +29 -11
  48. package/dist/openui-artifact-renderer-D3E5bIAI.d.ts +114 -0
  49. package/dist/openui-artifact-renderer-DT4xbvWt.js +266 -0
  50. package/dist/openui.d.ts +2 -115
  51. package/dist/openui.js +2 -13
  52. package/dist/parts-5mhy9yJ3.d.ts +37 -0
  53. package/dist/primitives-DE-blUz-.js +1239 -0
  54. package/dist/primitives.d.ts +5 -525
  55. package/dist/primitives.js +9 -212
  56. package/dist/redaction-CGGB2ENG.js +74 -0
  57. package/dist/redaction.d.ts +2 -42
  58. package/dist/redaction.js +2 -7
  59. package/dist/run-OyWmIDqu.d.ts +41 -0
  60. package/dist/run-ZsIKPA6J.js +17 -0
  61. package/dist/run-group-D1InSdQu.js +410 -0
  62. package/dist/run.d.ts +3 -126
  63. package/dist/run.js +5 -40
  64. package/dist/sdk-hooks.d.ts +2 -285
  65. package/dist/sdk-hooks.js +3 -36
  66. package/dist/stores.d.ts +13 -14
  67. package/dist/stores.js +34 -76
  68. package/dist/table-DHyqDPbU.js +146 -0
  69. package/dist/tabs-ujuqAdtb.js +40 -0
  70. package/dist/text-shimmer-BUUo6I-g.js +64 -0
  71. package/dist/tool-call-feed-BeB1_4pX.d.ts +47 -0
  72. package/dist/tool-call-feed-C1W1N54c.js +109 -0
  73. package/dist/tool-call-step-Bi3_YJRV.js +434 -0
  74. package/dist/tool-display-BAuAVa43.js +158 -0
  75. package/dist/{tool-display-z4JcDmMQ.d.ts → tool-display-DgmL5rIU.d.ts} +16 -16
  76. package/dist/tool-previews.d.ts +2 -48
  77. package/dist/tool-previews.js +2 -23
  78. package/dist/types.d.ts +6 -19
  79. package/dist/types.js +0 -1
  80. package/dist/use-auto-scroll-C5Pjeqon.js +153 -0
  81. package/dist/use-sse-stream-BjVBDbxK.js +884 -0
  82. package/dist/use-sse-stream-Dm6R5YWz.d.ts +282 -0
  83. package/dist/utils-Bl_CZ0Qp.js +37 -0
  84. package/dist/{chunk-RQHJBTEU.js → utils-C_uf36nf.js} +4 -6
  85. package/dist/utils.d.ts +2 -104
  86. package/dist/utils.js +6 -44
  87. package/package.json +39 -41
  88. package/dist/artifact-pane-DpuWcAiF.d.ts +0 -33
  89. package/dist/button-CMQuQEW_.d.ts +0 -17
  90. package/dist/chunk-34A66VBG.js +0 -214
  91. package/dist/chunk-3OI2QKFD.js +0 -0
  92. package/dist/chunk-3XXBZL53.js +0 -174
  93. package/dist/chunk-42PAH5D2.js +0 -112
  94. package/dist/chunk-4CLN43XT.js +0 -45
  95. package/dist/chunk-55WHV7SS.js +0 -1604
  96. package/dist/chunk-565EATZZ.js +0 -156
  97. package/dist/chunk-5Z5ZYMOJ.js +0 -0
  98. package/dist/chunk-6BGQA4BQ.js +0 -0
  99. package/dist/chunk-BEBXZPHW.js +0 -299
  100. package/dist/chunk-C5WF4WMV.js +0 -734
  101. package/dist/chunk-HFL6R6IF.js +0 -37
  102. package/dist/chunk-HGML45QH.js +0 -104
  103. package/dist/chunk-HMAPIH7L.js +0 -595
  104. package/dist/chunk-K5XFRUS4.js +0 -1401
  105. package/dist/chunk-KFQGHD73.js +0 -198
  106. package/dist/chunk-L57WRIND.js +0 -59
  107. package/dist/chunk-LTEKI7YJ.js +0 -59
  108. package/dist/chunk-M3QZK62R.js +0 -233
  109. package/dist/chunk-ND3ZFXQK.js +0 -179
  110. package/dist/chunk-OEX7NZE3.js +0 -321
  111. package/dist/chunk-OL5GYLHV.js +0 -60
  112. package/dist/chunk-QGFYBNSO.js +0 -133
  113. package/dist/chunk-R7B3UWPF.js +0 -550
  114. package/dist/chunk-R7SUY4E3.js +0 -65
  115. package/dist/chunk-REJESC5U.js +0 -117
  116. package/dist/chunk-RQGKSCEZ.js +0 -0
  117. package/dist/chunk-SNLR2AEA.js +0 -40
  118. package/dist/chunk-WKWBTL2V.js +0 -15
  119. package/dist/chunk-X7CU776B.js +0 -1048
  120. package/dist/chunk-XU3HB5QL.js +0 -127
  121. package/dist/chunk-YTO5V6QS.js +0 -19
  122. package/dist/chunk-YU4E5J2N.js +0 -437
  123. package/dist/chunk-YZ6AK25N.js +0 -886
  124. package/dist/code-block-0kSpWMnf.d.ts +0 -25
  125. package/dist/document-editor-pane-IAEQn_Dl.d.ts +0 -128
  126. package/dist/document-editor-pane-QHDOBA43.js +0 -13
  127. package/dist/message-BHWbxBtT.d.ts +0 -15
  128. package/dist/parts-dj7AcUg0.d.ts +0 -36
  129. package/dist/run-PfLmDAox.d.ts +0 -41
  130. package/dist/tool-call-feed-D9iofJgW.d.ts +0 -46
package/dist/chat.d.ts CHANGED
@@ -1,201 +1,2 @@
1
- import * as React from 'react';
2
- import { ReactNode } from 'react';
3
- import * as react_jsx_runtime from 'react/jsx-runtime';
4
- import { S as SessionMessage } from './message-BHWbxBtT.js';
5
- import { S as SessionPart, a as ToolPart } from './parts-dj7AcUg0.js';
6
- import { AgentBranding } from './types.js';
7
- import { C as CustomToolRenderer } from './tool-display-z4JcDmMQ.js';
8
- import { R as Run, G as GroupedMessage } from './run-PfLmDAox.js';
9
- import { OpenUIAction } from './openui.js';
10
- import { T as ToolCallData } from './tool-call-feed-D9iofJgW.js';
11
-
12
- /**
13
- * Transcript-only container: message list + auto-scroll. Composers are
14
- * composed BELOW this by the app (the canonical one is `AgentComposer` in
15
- * `@tangle-network/sandbox-ui`) — this component never renders an input.
16
- */
17
- interface ChatContainerProps {
18
- messages: SessionMessage[];
19
- partMap: Record<string, SessionPart[]>;
20
- isStreaming: boolean;
21
- branding?: AgentBranding;
22
- className?: string;
23
- /** Custom renderer for tool details. Return ReactNode to override, null to use default. */
24
- renderToolDetail?: CustomToolRenderer;
25
- /** Presentation mode for the session view. */
26
- presentation?: "runs" | "timeline";
27
- /** Callback when an OpenUI action button is pressed within inline OpenUI blocks. */
28
- onOpenUIAction?: (action: OpenUIAction) => void;
29
- /** Enable rendering OpenUI schemas inline in the chat timeline. Defaults to true. */
30
- enableOpenUI?: boolean;
31
- /** Optional actions rendered beside each grouped assistant run. */
32
- renderRunActions?: (run: Run) => ReactNode;
33
- /** Optional actions rendered below each user message bubble. */
34
- renderUserMessageActions?: (message: SessionMessage, parts: SessionPart[]) => ReactNode;
35
- /** Optional actions rendered beside individual tool items in the run-grouped
36
- * (`runs`) presentation. */
37
- renderToolActions?: (part: ToolPart, options: {
38
- run: Run;
39
- messageId: string;
40
- partIndex: number;
41
- }) => ReactNode;
42
- /** Optional actions rendered beside individual tool items in the `timeline`
43
- * presentation, which has no run/message grouping (hence part-only). */
44
- renderTimelineToolActions?: (part: ToolPart) => ReactNode;
45
- /** In the `timeline` presentation, collapse to the first N spine rows behind
46
- * a "Show N more steps" toggle. Omit to always show every row. */
47
- collapseTimelineAfter?: number;
48
- }
49
- /**
50
- * Chat transcript container: message list + auto-scroll.
51
- * Orchestrates useRunGroups, useRunCollapseState, and useAutoScroll.
52
- */
53
- declare const ChatContainer: React.MemoExoticComponent<({ messages, partMap, isStreaming, branding, className, renderToolDetail, presentation, onOpenUIAction, enableOpenUI, renderRunActions, renderUserMessageActions, renderToolActions, renderTimelineToolActions, collapseTimelineAfter, }: ChatContainerProps) => react_jsx_runtime.JSX.Element>;
54
-
55
- interface MessageListProps {
56
- groups: GroupedMessage[];
57
- partMap: Record<string, SessionPart[]>;
58
- isCollapsed: (runId: string) => boolean;
59
- onToggleCollapse: (runId: string) => void;
60
- branding?: AgentBranding;
61
- renderToolDetail?: CustomToolRenderer;
62
- renderRunActions?: (group: Extract<GroupedMessage, {
63
- type: "run";
64
- }>["run"]) => ReactNode;
65
- renderUserMessageActions?: (message: SessionMessage, parts: SessionPart[]) => ReactNode;
66
- renderToolActions?: (part: ToolPart, options: {
67
- run: Extract<GroupedMessage, {
68
- type: "run";
69
- }>["run"];
70
- messageId: string;
71
- partIndex: number;
72
- }) => ReactNode;
73
- }
74
- /**
75
- * Maps GroupedMessage[] to UserMessage and RunGroup components.
76
- * This is the main render list for the chat view.
77
- */
78
- declare const MessageList: React.MemoExoticComponent<({ groups, partMap, isCollapsed, onToggleCollapse, branding, renderToolDetail, renderRunActions, renderUserMessageActions, renderToolActions, }: MessageListProps) => react_jsx_runtime.JSX.Element>;
79
-
80
- interface UserMessageProps {
81
- /** Session-model input: text is derived from these parts. */
82
- message?: SessionMessage;
83
- parts?: SessionPart[];
84
- /** Direct-content input (e.g. AgentTimeline): explicit text + timestamp. */
85
- content?: string;
86
- timestamp?: Date;
87
- actions?: ReactNode;
88
- }
89
- /**
90
- * The single user message bubble — a quiet, right-aligned fill on the muted
91
- * surface (no border, no loud fill, no uppercase label). The timestamp sits
92
- * beside the bubble and appears on hover, so it costs no height. Used by both
93
- * the run/message list (session-model `parts`) and AgentTimeline (direct
94
- * `content`/`timestamp`).
95
- */
96
- declare const UserMessage: React.MemoExoticComponent<({ message: _message, parts, content, timestamp, actions }: UserMessageProps) => react_jsx_runtime.JSX.Element | null>;
97
-
98
- type MessageRole = "user" | "assistant" | "system";
99
- interface ChatMessageProps {
100
- role: MessageRole;
101
- content: string;
102
- /** Inline tool call activity rendered between text chunks */
103
- toolCalls?: ReactNode;
104
- /** Whether the message is still streaming */
105
- isStreaming?: boolean;
106
- /** Timestamp */
107
- timestamp?: Date;
108
- className?: string;
109
- /** Custom user label. Default: "You" */
110
- userLabel?: string;
111
- /** Custom assistant label. Default: "Agent" */
112
- assistantLabel?: string;
113
- /** Hide the role label row entirely */
114
- hideRoleLabel?: boolean;
115
- }
116
- declare function ChatMessage({ role, content, toolCalls, isStreaming, timestamp, className, userLabel, assistantLabel, hideRoleLabel, }: ChatMessageProps): react_jsx_runtime.JSX.Element;
117
-
118
- interface ThinkingIndicatorProps {
119
- className?: string;
120
- }
121
- declare function ThinkingIndicator({ className }: ThinkingIndicatorProps): react_jsx_runtime.JSX.Element;
122
-
123
- type AgentTimelineTone = "default" | "info" | "success" | "warning" | "error";
124
- interface AgentTimelineMessageItem {
125
- id: string;
126
- kind: "message";
127
- role: MessageRole;
128
- content: string;
129
- toolCalls?: ReactNode;
130
- isStreaming?: boolean;
131
- /** Shown beside a user bubble on hover. Assistant prose carries no
132
- * timestamp of its own — the turn's user message dates the exchange. */
133
- timestamp?: Date;
134
- after?: ReactNode;
135
- }
136
- interface AgentTimelineToolItem {
137
- id: string;
138
- kind: "tool";
139
- call: ToolCallData;
140
- /** Source tool part, so a consumer's `renderToolActions` gets the real
141
- * input/output (the flat `call` is display-only). */
142
- part?: ToolPart;
143
- }
144
- interface AgentTimelineToolGroupItem {
145
- id: string;
146
- kind: "tool_group";
147
- /** Accessible name of the group. Not drawn — the rows are the label. */
148
- title?: string;
149
- calls: ToolCallData[];
150
- /** Source tool parts, parallel to `calls`. */
151
- parts?: ToolPart[];
152
- }
153
- interface AgentTimelineStatusItem {
154
- id: string;
155
- kind: "status";
156
- label: string;
157
- detail?: string;
158
- tone?: AgentTimelineTone;
159
- }
160
- interface AgentTimelineArtifactItem {
161
- id: string;
162
- kind: "artifact";
163
- title: string;
164
- description?: string;
165
- meta?: ReactNode;
166
- icon?: ReactNode;
167
- tone?: AgentTimelineTone;
168
- action?: ReactNode;
169
- onClick?: () => void;
170
- }
171
- interface AgentTimelineCustomItem {
172
- id: string;
173
- kind: "custom";
174
- /** Laid out as a run row: it takes the same horizontal bleed as tool rows,
175
- * so a `RunRowShell`-based row (reasoning) aligns its glyph with the prose
176
- * edge. */
177
- content: ReactNode;
178
- }
179
- type AgentTimelineItem = AgentTimelineMessageItem | AgentTimelineToolItem | AgentTimelineToolGroupItem | AgentTimelineStatusItem | AgentTimelineArtifactItem | AgentTimelineCustomItem;
180
- interface AgentTimelineProps {
181
- items: AgentTimelineItem[];
182
- isThinking?: boolean;
183
- emptyState?: ReactNode;
184
- className?: string;
185
- /** Optional actions rendered beside each tool item (e.g. "open in artifacts").
186
- * Receives the source tool part carried on the item. */
187
- renderToolActions?: (part: ToolPart) => ReactNode;
188
- /** When set, collapse the timeline to the first N step rows (every item
189
- * except user messages) behind a "Show N more steps" toggle. Omit to always
190
- * show every row. */
191
- collapseAfter?: number;
192
- }
193
- /**
194
- * AgentTimeline — unified mixed-content transcript for agent-backed sandbox
195
- * sessions. Renders messages, tool rows, status cards, and artifact handoffs
196
- * as one plain column: prose at the reading size, tool calls as quiet
197
- * one-liners between the paragraphs, no connector chrome.
198
- */
199
- declare function AgentTimeline({ items, isThinking, emptyState, className, renderToolActions, collapseAfter, }: AgentTimelineProps): react_jsx_runtime.JSX.Element | null;
200
-
201
- export { AgentTimeline, type AgentTimelineArtifactItem, type AgentTimelineCustomItem, type AgentTimelineItem, type AgentTimelineMessageItem, type AgentTimelineProps, type AgentTimelineStatusItem, type AgentTimelineTone, type AgentTimelineToolGroupItem, type AgentTimelineToolItem, ChatContainer, type ChatContainerProps, ChatMessage, type ChatMessageProps, MessageList, type MessageListProps, type MessageRole, ThinkingIndicator, type ThinkingIndicatorProps, UserMessage, type UserMessageProps };
1
+ import { _ as UserMessageProps, a as AgentTimelineMessageItem, b as ChatContainer, c as AgentTimelineTone, d as ThinkingIndicator, f as ThinkingIndicatorProps, g as UserMessage, h as MessageRole, i as AgentTimelineItem, l as AgentTimelineToolGroupItem, m as ChatMessageProps, n as AgentTimelineArtifactItem, o as AgentTimelineProps, p as ChatMessage, r as AgentTimelineCustomItem, s as AgentTimelineStatusItem, t as AgentTimeline, u as AgentTimelineToolItem, v as MessageList, x as ChatContainerProps, y as MessageListProps } from "./index-CUhfHT_V.js";
2
+ export { AgentTimeline, type AgentTimelineArtifactItem, type AgentTimelineCustomItem, type AgentTimelineItem, type AgentTimelineMessageItem, type AgentTimelineProps, type AgentTimelineStatusItem, type AgentTimelineTone, type AgentTimelineToolGroupItem, type AgentTimelineToolItem, ChatContainer, type ChatContainerProps, ChatMessage, type ChatMessageProps, MessageList, type MessageListProps, type MessageRole, ThinkingIndicator, type ThinkingIndicatorProps, UserMessage, type UserMessageProps };
package/dist/chat.js CHANGED
@@ -1,31 +1,2 @@
1
- import {
2
- AgentTimeline,
3
- ChatContainer,
4
- ChatMessage,
5
- MessageList,
6
- ThinkingIndicator,
7
- UserMessage
8
- } from "./chunk-C5WF4WMV.js";
9
- import "./chunk-565EATZZ.js";
10
- import "./chunk-YU4E5J2N.js";
11
- import "./chunk-R7B3UWPF.js";
12
- import "./chunk-ND3ZFXQK.js";
13
- import "./chunk-HMAPIH7L.js";
14
- import "./chunk-L57WRIND.js";
15
- import "./chunk-BEBXZPHW.js";
16
- import "./chunk-M3QZK62R.js";
17
- import "./chunk-4CLN43XT.js";
18
- import "./chunk-XU3HB5QL.js";
19
- import "./chunk-42PAH5D2.js";
20
- import "./chunk-OL5GYLHV.js";
21
- import "./chunk-3XXBZL53.js";
22
- import "./chunk-WKWBTL2V.js";
23
- import "./chunk-RQHJBTEU.js";
24
- export {
25
- AgentTimeline,
26
- ChatContainer,
27
- ChatMessage,
28
- MessageList,
29
- ThinkingIndicator,
30
- UserMessage
31
- };
1
+ import { a as MessageList, i as ThinkingIndicator, n as ChatContainer, o as UserMessage, r as AgentTimeline, t as ChatMessage } from "./chat-CPLL0Fd9.js";
2
+ export { AgentTimeline, ChatContainer, ChatMessage, MessageList, ThinkingIndicator, UserMessage };
@@ -0,0 +1,23 @@
1
+ import { HTMLAttributes, ReactNode } from "react";
2
+ //#region src/markdown/code-block.d.ts
3
+ interface CodeBlockProps extends HTMLAttributes<HTMLDivElement> {
4
+ code: string;
5
+ language?: string;
6
+ /**
7
+ * Header text. Defaults to `language`. Set this when the display name differs
8
+ * from the highlight.js language id — e.g. a file extension ("BASHRC") whose
9
+ * content highlights as a known language, or none.
10
+ */
11
+ label?: string;
12
+ showLineNumbers?: boolean;
13
+ /** Force light theme; defaults to dark */
14
+ light?: boolean;
15
+ children?: ReactNode;
16
+ }
17
+ declare const CodeBlock: import("react").MemoExoticComponent<({ code, language, label, showLineNumbers, light: lightProp, className, children, ...props }: CodeBlockProps) => import("react").JSX.Element>;
18
+ /** Copy-to-clipboard button for use inside CodeBlock. */
19
+ declare const CopyButton: import("react").MemoExoticComponent<({ text }: {
20
+ text: string;
21
+ }) => import("react").JSX.Element>;
22
+ //#endregion
23
+ export { CodeBlockProps as n, CopyButton as r, CodeBlock as t };
@@ -0,0 +1,165 @@
1
+ import { i as focusRing } from "./focus-Cw02pNSr.js";
2
+ import { t as cn } from "./utils-C_uf36nf.js";
3
+ import { memo, useCallback, useEffect, useRef, useState } from "react";
4
+ import { jsx, jsxs } from "react/jsx-runtime";
5
+ import { Check, Copy } from "lucide-react";
6
+ import SyntaxHighlighter from "react-syntax-highlighter";
7
+ //#region src/markdown/code-block.tsx
8
+ function getSyntaxTheme() {
9
+ const el = typeof document !== "undefined" ? document.documentElement : null;
10
+ const v = (name, fallback) => el ? getComputedStyle(el).getPropertyValue(name).trim() || fallback : fallback;
11
+ const comment = v("--syntax-comment", "#6B7094");
12
+ const keyword = v("--syntax-keyword", "#A78FFF");
13
+ const string = v("--syntax-string", "#10b981");
14
+ const fn = v("--syntax-function", "#6D9FFF");
15
+ const number = v("--syntax-number", "#FFB347");
16
+ const meta = v("--syntax-meta", "#8263FF");
17
+ const error = v("--syntax-error", "#FF4D6D");
18
+ const variable = v("--syntax-variable", "#C4C0D8");
19
+ const fg = v("--syntax-foreground", "#E8E6F6");
20
+ return {
21
+ "hljs-comment": {
22
+ color: comment,
23
+ fontStyle: "italic"
24
+ },
25
+ "hljs-quote": {
26
+ color: comment,
27
+ fontStyle: "italic"
28
+ },
29
+ "hljs-doctag": { color: comment },
30
+ "hljs-keyword": { color: keyword },
31
+ "hljs-selector-tag": { color: keyword },
32
+ "hljs-literal": { color: keyword },
33
+ "hljs-type": { color: keyword },
34
+ "hljs-class": { color: keyword },
35
+ "hljs-string": { color: string },
36
+ "hljs-template-tag": { color: string },
37
+ "hljs-template-variable": { color: string },
38
+ "hljs-addition": { color: string },
39
+ "hljs-regexp": { color: string },
40
+ "hljs-title": { color: fn },
41
+ "hljs-section": { color: fn },
42
+ "hljs-built_in": { color: fn },
43
+ "hljs-name": { color: fn },
44
+ "hljs-function": { color: fn },
45
+ "hljs-selector-id": { color: fn },
46
+ "hljs-selector-class": { color: fn },
47
+ "hljs-attribute": { color: fn },
48
+ "hljs-number": { color: number },
49
+ "hljs-symbol": { color: number },
50
+ "hljs-bullet": { color: number },
51
+ "hljs-link": {
52
+ color: number,
53
+ textDecoration: "underline"
54
+ },
55
+ "hljs-meta": { color: meta },
56
+ "hljs-selector-pseudo": { color: meta },
57
+ "hljs-deletion": { color: error },
58
+ "hljs-params": { color: variable },
59
+ "hljs-variable": { color: variable },
60
+ "hljs-tag": { color: variable },
61
+ "hljs-attr": { color: variable },
62
+ "hljs-subst": { color: variable },
63
+ "hljs-strong": { fontWeight: "bold" },
64
+ "hljs-emphasis": { fontStyle: "italic" },
65
+ "hljs": {
66
+ color: fg,
67
+ background: "transparent"
68
+ }
69
+ };
70
+ }
71
+ const LIGHT_THEMES = /* @__PURE__ */ new Set(["vault", "dawn"]);
72
+ function detectLightTheme() {
73
+ return typeof document !== "undefined" && LIGHT_THEMES.has(document.documentElement.getAttribute("data-sandbox-theme") ?? "");
74
+ }
75
+ function useIsLightTheme() {
76
+ const [isLight, setIsLight] = useState(detectLightTheme);
77
+ useEffect(() => {
78
+ if (typeof document === "undefined") return;
79
+ setIsLight(detectLightTheme());
80
+ const observer = new MutationObserver(() => setIsLight(detectLightTheme()));
81
+ observer.observe(document.documentElement, {
82
+ attributes: true,
83
+ attributeFilter: ["data-sandbox-theme"]
84
+ });
85
+ return () => observer.disconnect();
86
+ }, []);
87
+ return isLight;
88
+ }
89
+ const CodeBlock = memo(({ code, language, label, showLineNumbers = false, light: lightProp, className, children, ...props }) => {
90
+ const isLight = useIsLightTheme();
91
+ const light = lightProp ?? isLight;
92
+ const theme = getSyntaxTheme();
93
+ const bg = "bg-card border-border";
94
+ const headerBg = light ? "bg-muted/50 border-border" : "bg-background border-border";
95
+ const langColor = "text-muted-foreground";
96
+ const headerLabel = label ?? language;
97
+ return /* @__PURE__ */ jsxs("div", {
98
+ className: cn("group relative overflow-hidden rounded-lg border font-mono", bg, className),
99
+ ...props,
100
+ children: [
101
+ headerLabel && /* @__PURE__ */ jsxs("div", {
102
+ className: cn("flex items-center justify-between border-b px-3 py-1", headerBg),
103
+ children: [/* @__PURE__ */ jsx("span", {
104
+ className: cn("text-[calc(var(--font-size-xs)-1px)] font-mono font-medium uppercase tracking-widest", langColor),
105
+ children: headerLabel
106
+ }), children]
107
+ }),
108
+ !headerLabel && children && /* @__PURE__ */ jsx("div", {
109
+ className: "absolute right-2 top-2 z-10 flex items-center gap-2 opacity-0 transition-opacity group-hover:opacity-100",
110
+ children
111
+ }),
112
+ /* @__PURE__ */ jsx(SyntaxHighlighter, {
113
+ language: language ?? "text",
114
+ style: theme,
115
+ showLineNumbers,
116
+ lineNumberStyle: {
117
+ color: light ? "#8B92B8" : "#4A4D6A",
118
+ minWidth: "2.5em",
119
+ paddingRight: "1em"
120
+ },
121
+ customStyle: {
122
+ margin: 0,
123
+ padding: "var(--code-padding-y, 0.625rem) var(--code-padding-x, 0.75rem)",
124
+ background: "transparent",
125
+ fontSize: "var(--code-font-size, 0.8125rem)",
126
+ lineHeight: "var(--code-line-height, 1.5)",
127
+ overflowX: "auto"
128
+ },
129
+ codeTagProps: { style: { fontFamily: "var(--font-mono, 'JetBrains Mono', ui-monospace, monospace)" } },
130
+ wrapLines: false,
131
+ children: code
132
+ })
133
+ ]
134
+ });
135
+ });
136
+ CodeBlock.displayName = "CodeBlock";
137
+ /** Copy-to-clipboard button for use inside CodeBlock. */
138
+ const CopyButton = memo(({ text }) => {
139
+ const [copied, setCopied] = useState(false);
140
+ const timerRef = useRef(null);
141
+ useEffect(() => {
142
+ return () => {
143
+ if (timerRef.current) clearTimeout(timerRef.current);
144
+ };
145
+ }, []);
146
+ const handleCopy = useCallback(async () => {
147
+ try {
148
+ await navigator.clipboard.writeText(text);
149
+ setCopied(true);
150
+ if (timerRef.current) clearTimeout(timerRef.current);
151
+ timerRef.current = setTimeout(() => setCopied(false), 2e3);
152
+ } catch (err) {
153
+ console.warn("Clipboard write failed:", err);
154
+ }
155
+ }, [text]);
156
+ return /* @__PURE__ */ jsx("button", {
157
+ onClick: handleCopy,
158
+ className: cn("flex items-center justify-center w-6 h-6 rounded-md bg-muted border border-border hover:border-[var(--border-strong)] transition-colors", focusRing),
159
+ title: "Copy to clipboard",
160
+ children: copied ? /* @__PURE__ */ jsx(Check, { className: "w-3.5 h-3.5 text-emerald-500" }) : /* @__PURE__ */ jsx(Copy, { className: "w-3.5 h-3.5 text-muted-foreground" })
161
+ });
162
+ });
163
+ CopyButton.displayName = "CopyButton";
164
+ //#endregion
165
+ export { CopyButton as n, CodeBlock as t };