@blade-hq/agent-react 2612.0.0-beta.0 → 2612.0.0-beta.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (180) hide show
  1. package/README.md +88 -258
  2. package/dist/chat/AgentLoopBlock.d.ts +14 -0
  3. package/dist/{components → chat}/AskUserQuestionBlock.d.ts +3 -7
  4. package/dist/chat/AssistantTurnBlock.d.ts +50 -0
  5. package/dist/chat/AttachmentPreviewDialog.d.ts +26 -0
  6. package/dist/chat/ChatPanel.d.ts +64 -0
  7. package/dist/chat/CompactionCard.d.ts +6 -0
  8. package/dist/chat/ConnectionBanner.d.ts +10 -0
  9. package/dist/chat/CurrentPlanPanel.d.ts +20 -0
  10. package/dist/chat/FileDeliveryCards.d.ts +26 -0
  11. package/dist/chat/FinalArtifactCards.d.ts +8 -0
  12. package/dist/chat/ImageLightbox.d.ts +11 -0
  13. package/dist/chat/LightComposer.d.ts +7 -0
  14. package/dist/chat/LiteMessageList.d.ts +82 -0
  15. package/dist/chat/MessageActions.d.ts +6 -0
  16. package/dist/chat/MessageContextPills.d.ts +6 -0
  17. package/dist/chat/MessageFileAttachmentList.d.ts +13 -0
  18. package/dist/chat/MessageList.d.ts +54 -0
  19. package/dist/chat/PostChatFollowupBlock.d.ts +11 -0
  20. package/dist/{components → chat}/RenderErrorBoundary.d.ts +0 -1
  21. package/dist/chat/ResultFeedback.d.ts +11 -0
  22. package/dist/chat/SessionReplayBar.d.ts +12 -0
  23. package/dist/chat/TextAttachmentPills.d.ts +10 -0
  24. package/dist/chat/ToolCallBlock.d.ts +48 -0
  25. package/dist/chat/ToolUiCard.d.ts +6 -0
  26. package/dist/chat/TurnNavRail.d.ts +17 -0
  27. package/dist/chat/UserMessageBubble.d.ts +20 -0
  28. package/dist/chat/WorkflowRunBlock.d.ts +13 -0
  29. package/dist/chat/ai-elements/reasoning.d.ts +32 -0
  30. package/dist/chat/ai-elements/shimmer.d.ts +15 -0
  31. package/dist/chat/assistant-turn-questions.d.ts +14 -0
  32. package/dist/chat/card/CardContext.d.ts +7 -0
  33. package/dist/chat/chat-theme.d.ts +19 -0
  34. package/dist/chat/customization.d.ts +214 -0
  35. package/dist/chat/display-utils.d.ts +48 -0
  36. package/dist/{components/PostChatFollowupBlock.d.ts → chat/followup-interaction.d.ts} +5 -17
  37. package/dist/chat/index.d.ts +100 -0
  38. package/dist/chat/lib/citations.d.ts +30 -0
  39. package/dist/chat/lib/code-language.d.ts +5 -0
  40. package/dist/chat/lib/loopback.d.ts +8 -0
  41. package/dist/chat/lib/markdown-asset-url.d.ts +5 -0
  42. package/dist/chat/lib/preview-dispatch.d.ts +24 -0
  43. package/dist/chat/lib/skill-name.d.ts +9 -0
  44. package/dist/chat/lib/skill-visibility.d.ts +8 -0
  45. package/dist/chat/lib/ui-meta.d.ts +5 -0
  46. package/dist/chat/lib/use-async-value.d.ts +8 -0
  47. package/dist/chat/markdown/ExternalAnchor.d.ts +9 -0
  48. package/dist/chat/markdown/MarkdownContent.d.ts +40 -0
  49. package/dist/chat/markdown/text.d.ts +11 -0
  50. package/dist/chat/message-list-blocks.d.ts +92 -0
  51. package/dist/chat/plan/PlanSummaryCard.d.ts +10 -0
  52. package/dist/chat/plan/extract-plan-messages.d.ts +4 -0
  53. package/dist/chat/plan/parse-plan-messages.d.ts +10 -0
  54. package/dist/chat/plan/parse-plan-tree.d.ts +16 -0
  55. package/dist/chat/plan/types.d.ts +56 -0
  56. package/dist/chat/reasoning-visibility.d.ts +2 -0
  57. package/dist/chat/runtime/actions.d.ts +22 -0
  58. package/dist/chat/runtime/background-task-dismissals.d.ts +10 -0
  59. package/dist/chat/runtime/composer-channels.d.ts +46 -0
  60. package/dist/chat/runtime/environment.d.ts +152 -0
  61. package/dist/chat/runtime/input-cache-reset.d.ts +8 -0
  62. package/dist/chat/runtime/input-services.d.ts +111 -0
  63. package/dist/chat/runtime/session-source.d.ts +49 -0
  64. package/dist/chat/runtime/use-chat-actions.d.ts +19 -0
  65. package/dist/chat/runtime/use-session-replay.d.ts +16 -0
  66. package/dist/chat/scroll-anchor.d.ts +46 -0
  67. package/dist/chat/tool-renderers/BashRenderer.d.ts +2 -0
  68. package/dist/chat/tool-renderers/FileEditRenderer.d.ts +2 -0
  69. package/dist/chat/tool-renderers/FileReadRenderer.d.ts +2 -0
  70. package/dist/chat/tool-renderers/KbSearchRenderer.d.ts +2 -0
  71. package/dist/chat/tool-renderers/SearchRenderer.d.ts +2 -0
  72. package/dist/chat/tool-renderers/SubmitResultRenderer.d.ts +2 -0
  73. package/dist/chat/tool-renderers/kb-search-result.d.ts +19 -0
  74. package/dist/chat/tool-renderers/registry.d.ts +5 -0
  75. package/dist/chat/tool-renderers/shared.d.ts +30 -0
  76. package/dist/chat/tool-renderers/write-preview-scroll.d.ts +5 -0
  77. package/dist/chat-OCLOVB3H.css +175 -0
  78. package/dist/chat.css +175 -0
  79. package/dist/chunk-6ZDOQEWK.js +49365 -0
  80. package/dist/chunk-6ZDOQEWK.js.map +1 -0
  81. package/dist/chunk-FQQJP2GJ.js +26986 -0
  82. package/dist/chunk-FQQJP2GJ.js.map +1 -0
  83. package/dist/{chunk-G3PMV62Z.js → chunk-PR4QN5HX.js} +9 -2
  84. package/dist/chunk-WCMGQJLE.js +258 -0
  85. package/dist/chunk-WCMGQJLE.js.map +1 -0
  86. package/dist/components/AgentChat.d.ts +3 -3
  87. package/dist/components/ChatView.d.ts +2 -2
  88. package/dist/components/ConnectorPanel.d.ts +1 -1
  89. package/dist/components/ContextCard.d.ts +1 -1
  90. package/dist/components/LlmChat.d.ts +1 -1
  91. package/dist/components/McpAppCard.d.ts +1 -1
  92. package/dist/components/PlanUpdateBlock.d.ts +0 -8
  93. package/dist/components/PluginConnectorList.d.ts +1 -1
  94. package/dist/components/ReplayBar.d.ts +1 -1
  95. package/dist/components/SessionPluginConfigDialog.d.ts +1 -1
  96. package/dist/components/SessionPluginConfigForm.d.ts +1 -1
  97. package/dist/components/SessionPluginIcon.d.ts +1 -1
  98. package/dist/components/SessionPluginSelector.d.ts +1 -1
  99. package/dist/components/SessionQueuePanel.d.ts +1 -1
  100. package/dist/components/ToolUiCardView.d.ts +1 -1
  101. package/dist/components/plugin-config-draft.d.ts +1 -1
  102. package/dist/components/plugin-config-schema.d.ts +1 -1
  103. package/dist/components/plugin-connector.d.ts +1 -1
  104. package/dist/components/use-session-plugin-activation.d.ts +1 -1
  105. package/dist/context.d.ts +11 -2
  106. package/dist/embed/blade-chat-element.d.ts +14 -1
  107. package/dist/embed/entry.d.ts +8 -78
  108. package/dist/hooks/use-replay.d.ts +1 -1
  109. package/dist/hooks/use-turn-navigation.d.ts +1 -1
  110. package/dist/host.d.ts +54 -0
  111. package/dist/index.d.ts +11 -69
  112. package/dist/index.js +12 -63525
  113. package/dist/index.js.map +1 -1
  114. package/dist/internal.d.ts +60 -0
  115. package/dist/internal.js +656 -0
  116. package/dist/internal.js.map +1 -0
  117. package/dist/lib/mount-renderers.d.ts +25 -0
  118. package/dist/lib/use-effect-event.d.ts +3 -0
  119. package/dist/rich-input/BackgroundTasksPill.d.ts +3 -0
  120. package/dist/rich-input/ChatInput.d.ts +59 -0
  121. package/dist/rich-input/ComposerAttachmentViewport.d.ts +3 -0
  122. package/dist/rich-input/ConnectButton.d.ts +24 -0
  123. package/dist/rich-input/FileCompletionMenu.d.ts +44 -0
  124. package/dist/rich-input/FileSizeLimitDialog.d.ts +9 -0
  125. package/dist/rich-input/ModelSelector.d.ts +10 -0
  126. package/dist/rich-input/PlanningToggle.d.ts +7 -0
  127. package/dist/rich-input/ProgressCircle.d.ts +12 -0
  128. package/dist/rich-input/ReasoningModeSelect.d.ts +9 -0
  129. package/dist/rich-input/SkillCompletionMenu.d.ts +9 -0
  130. package/dist/rich-input/SkillStatusBar.d.ts +15 -0
  131. package/dist/rich-input/extensions/file-mention.d.ts +12 -0
  132. package/dist/rich-input/extensions/kb-mention.d.ts +18 -0
  133. package/dist/rich-input/extensions/skill-mention.d.ts +48 -0
  134. package/dist/rich-input/extensions/workflow-mention.d.ts +10 -0
  135. package/dist/rich-input/index.d.ts +48 -0
  136. package/dist/rich-input/input-keyboard.d.ts +13 -0
  137. package/dist/rich-input/lib/attachment-upload.d.ts +10 -0
  138. package/dist/rich-input/lib/background-tasks-view.d.ts +31 -0
  139. package/dist/rich-input/lib/client-query.d.ts +32 -0
  140. package/dist/rich-input/lib/composer-content.d.ts +42 -0
  141. package/dist/rich-input/lib/image-input-availability.d.ts +3 -0
  142. package/dist/rich-input/lib/kb-suggestions.d.ts +37 -0
  143. package/dist/rich-input/lib/reasoning-levels.d.ts +1 -0
  144. package/dist/rich-input/lib/session-data.d.ts +20 -0
  145. package/dist/rich-input/lib/skill-suggestions.d.ts +19 -0
  146. package/dist/rich-input/lib/token-estimate.d.ts +2 -0
  147. package/dist/rich-input/lib/token-pressure.d.ts +8 -0
  148. package/dist/rich-input/lib/upload-results.d.ts +8 -0
  149. package/dist/rich-input/lib/user-home.d.ts +33 -0
  150. package/dist/rich-input/model/model-data.d.ts +6 -0
  151. package/dist/rich-input/model/resolve-model.d.ts +59 -0
  152. package/dist/rich-input/model/use-composer-model.d.ts +24 -0
  153. package/dist/rich-input/services.d.ts +22 -0
  154. package/dist/rich-input/use-dismiss-skill-suggestions-on-mode-change.d.ts +3 -0
  155. package/dist/rich-input/use-input-history.d.ts +14 -0
  156. package/dist/rich-input/voice/VoiceWaveform.d.ts +10 -0
  157. package/dist/rich-input/voice/use-tiptap-voice-input.d.ts +47 -0
  158. package/dist/rich-input/voice/use-voice-input.d.ts +2 -0
  159. package/dist/rich-input/voice/voice-input-support.d.ts +5 -0
  160. package/dist/rich-input.js +29853 -0
  161. package/dist/rich-input.js.map +1 -0
  162. package/dist/style.css +30 -64
  163. package/dist/style.full.css +210 -65
  164. package/dist/{webapi-W3IB5DO4.js → webapi-E7K2CNM7.js} +2 -2
  165. package/package.json +12 -3
  166. package/public-api.md +206 -3603
  167. package/dist/components/AgentLoopBlock.d.ts +0 -8
  168. package/dist/components/AgentTaskCard.d.ts +0 -12
  169. package/dist/components/AssistantTurnBlock.d.ts +0 -36
  170. package/dist/components/ChatSurface.d.ts +0 -199
  171. package/dist/components/ConnectionBanner.d.ts +0 -8
  172. package/dist/components/MarkdownContent.d.ts +0 -30
  173. package/dist/components/MessageList.d.ts +0 -62
  174. package/dist/components/Shimmer.d.ts +0 -7
  175. package/dist/components/ToolCallBlock.d.ts +0 -41
  176. package/dist/components/TurnNavRail.d.ts +0 -23
  177. package/dist/components/UserMessageBubble.d.ts +0 -25
  178. package/dist/components/display-utils.d.ts +0 -4
  179. /package/dist/{chunk-G3PMV62Z.js.map → chunk-PR4QN5HX.js.map} +0 -0
  180. /package/dist/{webapi-W3IB5DO4.js.map → webapi-E7K2CNM7.js.map} +0 -0
@@ -0,0 +1,46 @@
1
+ export declare const ENTRY_SCROLL_MARGIN_PX = 24;
2
+ export declare function calculateStickyAwareMargin(statusHeight?: number, statusBottomGap?: number): number;
3
+ export declare function normalizeScrollEntryKey(value: string | null | undefined): string | null;
4
+ export declare function calculateAnchoredScrollTop({ scrollTop, containerTop, targetTop, margin, }: {
5
+ scrollTop: number;
6
+ containerTop: number;
7
+ targetTop: number;
8
+ margin?: number;
9
+ }): number;
10
+ export declare function calculateTrailingSpacerHeight({ targetScrollTop, scrollHeight, clientHeight, currentScrollTop, }: {
11
+ targetScrollTop: number;
12
+ scrollHeight: number;
13
+ clientHeight: number;
14
+ /** 当前滚动位置:空白不能收到把它挤出可滚动范围,否则浏览器会把页面拽回去。 */
15
+ currentScrollTop?: number;
16
+ }): number;
17
+ /** 交还跟随时允许的位置误差:顶置落位有取整误差,太严格会漏掉正常情况。 */
18
+ export declare const PIN_HANDOVER_TOLERANCE_PX = 24;
19
+ /**
20
+ * 尾部空白收完时是否把“跟随到底”交还给滚动库。
21
+ * 只有用户还停在顶置位置(或更靠下)才交还;他自己往上翻去看前文时不打扰。
22
+ */
23
+ export declare function shouldHandOverToFollow({ currentScrollTop, targetScrollTop, tolerance, }: {
24
+ currentScrollTop: number;
25
+ targetScrollTop: number;
26
+ tolerance?: number;
27
+ }): boolean;
28
+ export declare const NEW_TURN_SCROLL_DURATION_MS = 320;
29
+ /** 距离小于这个像素数时看不出动画,直接落位。 */
30
+ export declare const NEW_TURN_SCROLL_MIN_DISTANCE_PX = 8;
31
+ /** 距离超过这么多屏时直接跳过去:长距离滚动动画只会让人更晕。 */
32
+ export declare const NEW_TURN_SCROLL_MAX_SCREENS = 3;
33
+ /** 滚动位置偏离动画写入值超过这么多像素,就认定是用户在自己滚。 */
34
+ export declare const MANUAL_SCROLL_TOLERANCE_PX = 2;
35
+ export declare function shouldAnimateNewTurnScroll({ fromScrollTop, targetScrollTop, clientHeight, prefersReducedMotion, }: {
36
+ fromScrollTop: number;
37
+ targetScrollTop: number;
38
+ clientHeight: number;
39
+ prefersReducedMotion?: boolean;
40
+ }): boolean;
41
+ export declare function calculateAnimatedScrollTop({ fromScrollTop, targetScrollTop, elapsedMs, durationMs, }: {
42
+ fromScrollTop: number;
43
+ targetScrollTop: number;
44
+ elapsedMs: number;
45
+ durationMs?: number;
46
+ }): number;
@@ -0,0 +1,2 @@
1
+ import type { ToolRendererProps } from "./registry";
2
+ export declare function BashRenderer({ toolCall }: ToolRendererProps): import("react/jsx-runtime").JSX.Element;
@@ -0,0 +1,2 @@
1
+ import type { ToolRendererProps } from "./registry";
2
+ export declare function FileEditRenderer({ toolCall }: ToolRendererProps): import("react/jsx-runtime").JSX.Element;
@@ -0,0 +1,2 @@
1
+ import type { ToolRendererProps } from "./registry";
2
+ export declare function FileReadRenderer({ toolCall }: ToolRendererProps): import("react/jsx-runtime").JSX.Element;
@@ -0,0 +1,2 @@
1
+ import type { ToolRendererProps } from "./registry";
2
+ export declare function KbSearchRenderer({ toolCall }: ToolRendererProps): import("react/jsx-runtime").JSX.Element;
@@ -0,0 +1,2 @@
1
+ import type { ToolRendererProps } from "./registry";
2
+ export declare function SearchRenderer({ toolCall }: ToolRendererProps): import("react/jsx-runtime").JSX.Element;
@@ -0,0 +1,2 @@
1
+ import type { ToolRendererProps } from "./registry";
2
+ export declare function SubmitResultRenderer({ toolCall }: ToolRendererProps): import("react/jsx-runtime").JSX.Element;
@@ -0,0 +1,19 @@
1
+ /** kb_search 工具结果里的一条命中(与后端 `KnowledgeHit.to_payload` 对齐)。 */
2
+ export interface KbSearchHit {
3
+ n: number;
4
+ kbName: string;
5
+ title: string;
6
+ path: string;
7
+ page: number | null;
8
+ heading: string | null;
9
+ text: string;
10
+ previewUrl: string | null;
11
+ }
12
+ export interface KbSearchResult {
13
+ summary: string | null;
14
+ query: string | null;
15
+ hits: KbSearchHit[];
16
+ }
17
+ export declare function parseKbSearchResult(result: unknown): KbSearchResult | null;
18
+ /** 折叠时的标题:「🔍 在《X》检索到 N 条」。结果没回来或出错时退回工具名。 */
19
+ export declare function formatKbSearchLabel(result: unknown): string | null;
@@ -0,0 +1,5 @@
1
+ import type { ComponentType } from "react";
2
+ import type { ToolRendererProps } from "../customization";
3
+ export type { ToolRendererProps };
4
+ type ToolRenderer = ComponentType<ToolRendererProps>;
5
+ export declare function getRenderer(toolName: string): ToolRenderer | null;
@@ -0,0 +1,30 @@
1
+ /**
2
+ * 从工具结果中提取纯文本。如果 result 是多模态 list 则提取 text parts;
3
+ * 如果是 string 则原样返回。
4
+ */
5
+ export declare function getResultText(result: unknown): string | null;
6
+ /**
7
+ * 从工具结果提取图片资源及尺寸,供鉴权加载与预留布局使用。
8
+ */
9
+ export declare function getResultImages(result: unknown): {
10
+ url: string;
11
+ width?: number;
12
+ height?: number;
13
+ }[];
14
+ export declare function parseJsonValue(value?: string | null): unknown;
15
+ export declare function isPlainObject(value: unknown): value is Record<string, unknown>;
16
+ export declare function getStringValue(data: Record<string, unknown> | null, key: string): string | null;
17
+ export declare function getNumberValue(data: Record<string, unknown> | null, key: string): number | null;
18
+ export declare function getBooleanValue(data: Record<string, unknown> | null, key: string): boolean;
19
+ export declare function extractErrorMessage(value?: unknown): string | null;
20
+ export declare function getFileName(filePath?: string | null): string;
21
+ export declare function getCodeLanguage(filePath?: string | null): string | null;
22
+ export declare function formatBytes(size?: number | null): string | null;
23
+ interface CodePreviewProps {
24
+ content: string;
25
+ filePath?: string | null;
26
+ emptyLabel?: string;
27
+ className?: string;
28
+ }
29
+ export declare function CodePreview({ content, filePath, emptyLabel, className, }: CodePreviewProps): import("react/jsx-runtime").JSX.Element;
30
+ export {};
@@ -0,0 +1,5 @@
1
+ import type { ToolCallInfo } from "@blade-hq/agent-client/internal";
2
+ type ScrollContainer = Pick<HTMLElement, "scrollHeight" | "scrollTop">;
3
+ export declare function shouldFollowWritePreview(toolName: string, status: ToolCallInfo["status"]): boolean;
4
+ export declare function scrollWritePreviewToLatest(preview: ScrollContainer): void;
5
+ export {};
@@ -0,0 +1,175 @@
1
+ /*
2
+ * 聊天组件共用的非 Tailwind 规则(Markdown 排版、入场动画、扫光)。内置 Web 与插件经 agent/style.css
3
+ * 引入这一份;<blade-chat> 与 npm 样式由 scripts/gen-embed-styles.mjs 放进 blade-chat-overrides 层。
4
+ * 只写聊天组件自己用到的规则,页面级补丁不放这里。
5
+ */
6
+
7
+ [data-theme="light"] .prose-invert {
8
+ --tw-prose-body: hsl(var(--foreground));
9
+ --tw-prose-headings: hsl(var(--foreground));
10
+ --tw-prose-links: hsl(var(--primary));
11
+ --tw-prose-bold: hsl(var(--foreground));
12
+ --tw-prose-code: hsl(var(--primary));
13
+ --tw-prose-pre-bg: hsl(var(--muted));
14
+ --tw-prose-pre-code: hsl(var(--foreground));
15
+ --tw-prose-quotes: hsl(var(--muted-foreground));
16
+ --tw-prose-counters: hsl(var(--muted-foreground));
17
+ --tw-prose-bullets: hsl(var(--muted-foreground));
18
+ }
19
+
20
+ [data-theme="light"] .prose pre {
21
+ background: hsl(var(--muted));
22
+ }
23
+
24
+ [data-theme="light"] .prose code:not(pre code) {
25
+ color: hsl(var(--primary));
26
+ }
27
+
28
+ /* --- chat markdown density: 收紧块间距,避免松散 ---------------- */
29
+ /* typography 插件默认 p/li/heading 外边距偏大(1.25em/0.5em),聊天里读起来太松。
30
+ plain 选择器特异性高于插件的 :where(),可直接覆盖。 */
31
+ .chat-prose p {
32
+ margin-top: 0.5em;
33
+ margin-bottom: 0.5em;
34
+ }
35
+ .chat-prose > p:first-child,
36
+ .chat-prose > ul:first-child,
37
+ .chat-prose > ol:first-child {
38
+ margin-top: 0;
39
+ }
40
+ .chat-prose > p:last-child,
41
+ .chat-prose > ul:last-child,
42
+ .chat-prose > ol:last-child {
43
+ margin-bottom: 0;
44
+ }
45
+ .chat-prose ul,
46
+ .chat-prose ol {
47
+ margin-top: 0.4em;
48
+ margin-bottom: 0.4em;
49
+ padding-left: 1.4em;
50
+ }
51
+ .chat-prose li {
52
+ margin-top: 0.2em;
53
+ margin-bottom: 0.2em;
54
+ }
55
+ .chat-prose li p {
56
+ margin-top: 0;
57
+ margin-bottom: 0;
58
+ }
59
+ .chat-prose ul ul,
60
+ .chat-prose ol ol,
61
+ .chat-prose ul ol,
62
+ .chat-prose ol ul {
63
+ margin-top: 0.2em;
64
+ margin-bottom: 0.2em;
65
+ }
66
+ .chat-prose h1 {
67
+ font-size: 1.4em;
68
+ margin: 1em 0 0.5em;
69
+ }
70
+ .chat-prose h2 {
71
+ font-size: 1.2em;
72
+ margin: 1em 0 0.45em;
73
+ }
74
+ .chat-prose h3,
75
+ .chat-prose h4 {
76
+ font-size: 1.05em;
77
+ margin: 0.9em 0 0.4em;
78
+ }
79
+ .chat-prose blockquote {
80
+ margin-top: 0.6em;
81
+ margin-bottom: 0.6em;
82
+ }
83
+ .chat-prose hr {
84
+ margin-top: 1.2em;
85
+ margin-bottom: 1.2em;
86
+ }
87
+
88
+ /* 未闭合的加粗/斜体/行内代码,在闭合符真正到达前先按最终标签
89
+ * 渲染、只用透明度标出"待确认"——内容和标签结构全程不变,闭合符到达后
90
+ * 这条规则自然不再匹配,恢复完全不透明,DOM 节点没有被替换过。这个属性
91
+ * 只由 MarkdownRenderer 引擎自己产出,不区分调用方用的是哪套 prose 外壳
92
+ * (`.chat-prose`/`.prose`/`.lite-chat-markdown`/无外壳),不按外壳类名
93
+ * 逐个补,直接全局生效。 */
94
+ [data-markdown-pending="true"] {
95
+ opacity: 0.6;
96
+ }
97
+
98
+ /* 宽表格(多列或者有超长不可断行内容)要横向自己滚,不能把聊天区撑宽。
99
+ * 原来 streamdown 的表格外壳自带 overflow-x-auto,新引擎换成
100
+ * `.blade-chat-table-wrapper` 这个 class,但那只是引擎自己 SDK 包
101
+ * (`@blade-hq/agent-react`)样式表里的 scoped 规则,挂在
102
+ * `.blade-chat-markdown` 之下——内置 Web 这边套的是 `.chat-prose`/
103
+ * `.prose`/`.lite-chat-markdown` 这几套外壳,从来没有 `.blade-chat-markdown`,
104
+ * 那条规则永远匹配不上,得在这里再补一条不依赖外壳类名的全局规则。 */
105
+ .blade-chat-table-wrapper {
106
+ max-width: 100%;
107
+ min-width: 0;
108
+ overflow-x: auto;
109
+ }
110
+
111
+ /* Message entrance animation */
112
+ @keyframes msg-in {
113
+ from {
114
+ opacity: 0;
115
+ transform: translateY(5px);
116
+ }
117
+ to {
118
+ opacity: 1;
119
+ transform: translateY(0);
120
+ }
121
+ }
122
+
123
+ .msg-animate {
124
+ animation: msg-in 0.15s ease-out forwards;
125
+ }
126
+
127
+ /* Running-state sweep, borrowed from deepseek-harness's ReasoningRow. */
128
+ .status-sweep::after {
129
+ content: "";
130
+ position: absolute;
131
+ inset-block: 0;
132
+ left: 0;
133
+ width: 260px;
134
+ background: linear-gradient(
135
+ 90deg,
136
+ transparent,
137
+ hsl(var(--primary) / 0.08) 50%,
138
+ transparent
139
+ );
140
+ animation: status-sweep 2.6s ease-out infinite;
141
+ pointer-events: none;
142
+ z-index: 0;
143
+ }
144
+
145
+ @keyframes status-sweep {
146
+ 0% { transform: translateX(-100%); }
147
+ 90%, 100% { transform: translateX(500%); }
148
+ }
149
+
150
+ @media (prefers-reduced-motion: reduce) {
151
+ .status-sweep::after {
152
+ animation: none;
153
+ }
154
+ }
155
+
156
+ /* 流式等待的扫光文字(ai-elements/shimmer.tsx) */
157
+ @keyframes blade-shimmer-sweep {
158
+ from {
159
+ background-position: 100% center;
160
+ }
161
+ to {
162
+ background-position: 0% center;
163
+ }
164
+ }
165
+
166
+ @media (prefers-reduced-motion: reduce) {
167
+ @keyframes blade-shimmer-sweep {
168
+ from {
169
+ background-position: 0% center;
170
+ }
171
+ to {
172
+ background-position: 0% center;
173
+ }
174
+ }
175
+ }
package/dist/chat.css ADDED
@@ -0,0 +1,175 @@
1
+ /*
2
+ * 聊天组件共用的非 Tailwind 规则(Markdown 排版、入场动画、扫光)。内置 Web 与插件经 agent/style.css
3
+ * 引入这一份;<blade-chat> 与 npm 样式由 scripts/gen-embed-styles.mjs 放进 blade-chat-overrides 层。
4
+ * 只写聊天组件自己用到的规则,页面级补丁不放这里。
5
+ */
6
+
7
+ [data-theme="light"] .prose-invert {
8
+ --tw-prose-body: hsl(var(--foreground));
9
+ --tw-prose-headings: hsl(var(--foreground));
10
+ --tw-prose-links: hsl(var(--primary));
11
+ --tw-prose-bold: hsl(var(--foreground));
12
+ --tw-prose-code: hsl(var(--primary));
13
+ --tw-prose-pre-bg: hsl(var(--muted));
14
+ --tw-prose-pre-code: hsl(var(--foreground));
15
+ --tw-prose-quotes: hsl(var(--muted-foreground));
16
+ --tw-prose-counters: hsl(var(--muted-foreground));
17
+ --tw-prose-bullets: hsl(var(--muted-foreground));
18
+ }
19
+
20
+ [data-theme="light"] .prose pre {
21
+ background: hsl(var(--muted));
22
+ }
23
+
24
+ [data-theme="light"] .prose code:not(pre code) {
25
+ color: hsl(var(--primary));
26
+ }
27
+
28
+ /* --- chat markdown density: 收紧块间距,避免松散 ---------------- */
29
+ /* typography 插件默认 p/li/heading 外边距偏大(1.25em/0.5em),聊天里读起来太松。
30
+ plain 选择器特异性高于插件的 :where(),可直接覆盖。 */
31
+ .chat-prose p {
32
+ margin-top: 0.5em;
33
+ margin-bottom: 0.5em;
34
+ }
35
+ .chat-prose > p:first-child,
36
+ .chat-prose > ul:first-child,
37
+ .chat-prose > ol:first-child {
38
+ margin-top: 0;
39
+ }
40
+ .chat-prose > p:last-child,
41
+ .chat-prose > ul:last-child,
42
+ .chat-prose > ol:last-child {
43
+ margin-bottom: 0;
44
+ }
45
+ .chat-prose ul,
46
+ .chat-prose ol {
47
+ margin-top: 0.4em;
48
+ margin-bottom: 0.4em;
49
+ padding-left: 1.4em;
50
+ }
51
+ .chat-prose li {
52
+ margin-top: 0.2em;
53
+ margin-bottom: 0.2em;
54
+ }
55
+ .chat-prose li p {
56
+ margin-top: 0;
57
+ margin-bottom: 0;
58
+ }
59
+ .chat-prose ul ul,
60
+ .chat-prose ol ol,
61
+ .chat-prose ul ol,
62
+ .chat-prose ol ul {
63
+ margin-top: 0.2em;
64
+ margin-bottom: 0.2em;
65
+ }
66
+ .chat-prose h1 {
67
+ font-size: 1.4em;
68
+ margin: 1em 0 0.5em;
69
+ }
70
+ .chat-prose h2 {
71
+ font-size: 1.2em;
72
+ margin: 1em 0 0.45em;
73
+ }
74
+ .chat-prose h3,
75
+ .chat-prose h4 {
76
+ font-size: 1.05em;
77
+ margin: 0.9em 0 0.4em;
78
+ }
79
+ .chat-prose blockquote {
80
+ margin-top: 0.6em;
81
+ margin-bottom: 0.6em;
82
+ }
83
+ .chat-prose hr {
84
+ margin-top: 1.2em;
85
+ margin-bottom: 1.2em;
86
+ }
87
+
88
+ /* 未闭合的加粗/斜体/行内代码,在闭合符真正到达前先按最终标签
89
+ * 渲染、只用透明度标出"待确认"——内容和标签结构全程不变,闭合符到达后
90
+ * 这条规则自然不再匹配,恢复完全不透明,DOM 节点没有被替换过。这个属性
91
+ * 只由 MarkdownRenderer 引擎自己产出,不区分调用方用的是哪套 prose 外壳
92
+ * (`.chat-prose`/`.prose`/`.lite-chat-markdown`/无外壳),不按外壳类名
93
+ * 逐个补,直接全局生效。 */
94
+ [data-markdown-pending="true"] {
95
+ opacity: 0.6;
96
+ }
97
+
98
+ /* 宽表格(多列或者有超长不可断行内容)要横向自己滚,不能把聊天区撑宽。
99
+ * 原来 streamdown 的表格外壳自带 overflow-x-auto,新引擎换成
100
+ * `.blade-chat-table-wrapper` 这个 class,但那只是引擎自己 SDK 包
101
+ * (`@blade-hq/agent-react`)样式表里的 scoped 规则,挂在
102
+ * `.blade-chat-markdown` 之下——内置 Web 这边套的是 `.chat-prose`/
103
+ * `.prose`/`.lite-chat-markdown` 这几套外壳,从来没有 `.blade-chat-markdown`,
104
+ * 那条规则永远匹配不上,得在这里再补一条不依赖外壳类名的全局规则。 */
105
+ .blade-chat-table-wrapper {
106
+ max-width: 100%;
107
+ min-width: 0;
108
+ overflow-x: auto;
109
+ }
110
+
111
+ /* Message entrance animation */
112
+ @keyframes msg-in {
113
+ from {
114
+ opacity: 0;
115
+ transform: translateY(5px);
116
+ }
117
+ to {
118
+ opacity: 1;
119
+ transform: translateY(0);
120
+ }
121
+ }
122
+
123
+ .msg-animate {
124
+ animation: msg-in 0.15s ease-out forwards;
125
+ }
126
+
127
+ /* Running-state sweep, borrowed from deepseek-harness's ReasoningRow. */
128
+ .status-sweep::after {
129
+ content: "";
130
+ position: absolute;
131
+ inset-block: 0;
132
+ left: 0;
133
+ width: 260px;
134
+ background: linear-gradient(
135
+ 90deg,
136
+ transparent,
137
+ hsl(var(--primary) / 0.08) 50%,
138
+ transparent
139
+ );
140
+ animation: status-sweep 2.6s ease-out infinite;
141
+ pointer-events: none;
142
+ z-index: 0;
143
+ }
144
+
145
+ @keyframes status-sweep {
146
+ 0% { transform: translateX(-100%); }
147
+ 90%, 100% { transform: translateX(500%); }
148
+ }
149
+
150
+ @media (prefers-reduced-motion: reduce) {
151
+ .status-sweep::after {
152
+ animation: none;
153
+ }
154
+ }
155
+
156
+ /* 流式等待的扫光文字(ai-elements/shimmer.tsx) */
157
+ @keyframes blade-shimmer-sweep {
158
+ from {
159
+ background-position: 100% center;
160
+ }
161
+ to {
162
+ background-position: 0% center;
163
+ }
164
+ }
165
+
166
+ @media (prefers-reduced-motion: reduce) {
167
+ @keyframes blade-shimmer-sweep {
168
+ from {
169
+ background-position: 0% center;
170
+ }
171
+ to {
172
+ background-position: 0% center;
173
+ }
174
+ }
175
+ }