# Vue 2 组件与 API markstream-vue2 提供与 markstream-vue 相同强大的组件,但专为 Vue 2 构建。所有组件都兼容 Vue 2.6+(配合 `@vue/composition-api`)和 Vue 2.7+。 ## TypeScript 类型导出 `markstream-vue2` 同步导出渲染器与组件 props 类型: ```ts import type { CodeBlockNodeProps, D2BlockNodeProps, InfographicBlockNodeProps, MermaidBlockNodeProps, NodeRendererProps, PreCodeNodeProps, } from 'markstream-vue2' import type { CodeBlockNode } from 'stream-markdown-parser' ``` 说明: - `NodeRendererProps` 对应 `` props。 - `CodeBlockNodeProps` / `MermaidBlockNodeProps` / `D2BlockNodeProps` / `InfographicBlockNodeProps` / `PreCodeNodeProps` 的 `node` 统一为 `CodeBlockNode`(用 `language: 'mermaid'` / `language: 'd2'` / `language: 'd2lang'` / `language: 'infographic'` 区分渲染器)。 ## 主组件:MarkdownRender 在 Vue 2 中渲染 markdown 内容的主要组件。 ### Props `MarkdownRender` 在 Vue 2 中的 props 与 Vue 3 版本一致;模板中使用 kebab-case。 #### 核心 props | 属性 | 类型 | 默认值 | 描述 | |------|------|---------|-------------| | `content` | `string` | - | 要渲染的 Markdown 内容 | | `nodes` | `BaseNode[]` | - | 预解析的 AST 节点(通常为 `ParsedNode[]`) | | `custom-id` | `string` | - | 作用域标识,用于 `setCustomComponents` 与 `[data-custom-id="..."]` | | `final` | `boolean` | `false` | 标记输入结束,停止输出 streaming `loading` 节点 | | `parse-options` | `ParseOptions` | - | 解析选项与 token hooks(仅在传入 `content` 时生效) | | `custom-html-tags` | `string[]` | - | 作为自定义节点输出的 HTML-like 标签(如 `thinking`) | | `custom-markdown-it` | `(md: MarkdownIt) => MarkdownIt` | - | 自定义 MarkdownIt 实例 | | `debug-performance` | `boolean` | `false` | 输出解析/渲染耗时与虚拟化统计(仅 dev) | | `is-dark` | `boolean` | `false` | 暗色主题标记,转发给重型节点并在根容器加 `.dark` | | `index-key` | `number \| string` | - | 列表渲染时的 key 前缀 | | `typewriter` | `boolean` | `true` | 非代码节点进入动画 | | `show-tooltips` | `boolean` | `true` | 全局控制 `LinkNode` 与代码块节点 tooltip | #### 流式与重节点开关 | 属性 | 默认值 | 描述 | |------|---------|-------------| | `render-code-blocks-as-pre` | `false` | 将非 Mermaid/Infographic/D2 的 `code_block` 渲染为 `
` |
| `code-block-stream` | `true` | 随内容到达流式更新代码块 |
| `viewport-priority` | `true` | 将 Monaco/Mermaid/D2/KaTeX 等重型工作延迟到接近视口时 |
| `defer-nodes-until-visible` | `true` | 重型节点先占位,接近可视区再渲染(仅非虚拟化模式) |

#### 性能(虚拟化与批次渲染)

| 属性 | 默认值 | 描述 |
|------|---------|-------------|
| `max-live-nodes` | `320` | DOM 最大保留节点数(设为 `0` 关闭虚拟化) |
| `live-node-buffer` | `60` | 视窗前后 overscan 缓冲 |
| `batch-rendering` | `true` | 在关闭虚拟化时启用批次渲染 |
| `initial-render-batch-size` | `40` | 批次渲染前先渲染的节点数量 |
| `render-batch-size` | `80` | 每个批次渲染的节点数量 |
| `render-batch-delay` | `16` | 每次批次前的额外延迟(ms) |
| `render-batch-budget-ms` | `6` | 自适应批次缩小前的预算(ms) |
| `render-batch-idle-timeout-ms` | `120` | `requestIdleCallback` 超时(ms) |

#### 代码块全局配置

| 属性 | 类型 | 描述 |
|------|------|-------------|
| `code-block-dark-theme` | `any` | 转发到每个 `CodeBlockNode` 的 Monaco 深色主题 |
| `code-block-light-theme` | `any` | 转发到每个 `CodeBlockNode` 的 Monaco 浅色主题 |
| `code-block-monaco-options` | `Record` | 转发到 `stream-monaco` 的选项,包括 `diffHunkActionsOnHover`、`diffHunkHoverHideDelayMs`、`onDiffHunkAction` 这类 diff 悬浮操作配置 |
| `code-block-min-width` | `string \| number` | 转发到 `CodeBlockNode` 的最小宽度 |
| `code-block-max-width` | `string \| number` | 转发到 `CodeBlockNode` 的最大宽度 |
| `code-block-props` | `Record` | 额外转发到每个 `CodeBlockNode` 的 props |
| `mermaid-props` | `Partial>` | 额外转发到 Mermaid 围栏和自定义 `mermaid` 渲染器的 props |
| `d2-props` | `Partial>` | 额外转发到 D2 围栏和自定义 `d2` 渲染器的 props |
| `infographic-props` | `Partial>` | 额外转发到 infographic 围栏和自定义 `infographic` 渲染器的 props |
| `themes` | `string[]` | 转发到 `stream-monaco` 的主题列表 |

#### 重型渲染器 props 透传

`MarkdownRender` 可以直接给重型图表节点传调优参数:

```vue

```

流式建议:
- 保持 `viewport-priority` 开启,避免离屏 Mermaid / Monaco / D2 在文字仍在流式更新时继续做后台工作。
- 高频 SSE 更推荐直接传 `nodes`,而不是每个 chunk 都重跑整篇 `content` 解析。
- Mermaid 常用调优项包括:`renderDebounceMs`、`contentStableDelayMs`、`previewPollDelayMs`、`previewPollMaxDelayMs`、`previewPollMaxAttempts`。

#### 事件

- `@copy`, `@handleArtifactClick`, `@click`, `@mouseover`, `@mouseout`

### 使用

```vue



```

## 代码块组件

### MarkdownCodeBlockNode

使用 Shiki 的轻量级代码高亮。

```vue



```

### CodeBlockNode

功能丰富的 Monaco 驱动代码块。

```vue



```

## 数学组件

### MathBlockNode

使用 KaTeX 渲染块级数学公式。

```vue



```

### MathInlineNode

渲染行内数学公式。

```vue



```

## Mermaid 图表

### MermaidBlockNode

渐进式 Mermaid 图表渲染。

#### 快速要点
- **Tooltip 控制**:`showTooltips` 默认 `true`;设为 `false` 可关闭头部按钮 tooltip。

```vue



```

常用流式调优 props:
- `render-debounce-ms`
- `content-stable-delay-ms`
- `preview-poll-delay-ms`
- `preview-poll-max-delay-ms`
- `preview-poll-max-attempts`

## D2 图表

### D2BlockNode

渐进式 D2 图表渲染,失败时保留上次成功的预览。

```vue



```

## 工具函数

### setCustomComponents

为特定的 markdown 节点注册自定义节点渲染器。

```js
import { setCustomComponents } from 'markstream-vue2'

// 定义自定义组件
const CustomHeading = {
  name: 'CustomHeading',
  props: ['node', 'indexKey', 'customId'],
  render(h) {
    const level = this.node.level || 1
    return h(`h${level}`, {
      class: 'custom-heading',
      attrs: { 'data-custom-id': this.customId }
    }, this.node.children.map(c => c.content))
  }
}

// 全局注册
setCustomComponents('docs', {
  heading: CustomHeading
})
```

### getMarkdown

获取配置好的 markdown-it 实例。

```js
import { getMarkdown } from 'markstream-vue2'

const md = getMarkdown('my-msg-id', {
  html: true,
  linkify: true,
  typographer: true
})

const tokens = md.parse('# Hello World')
```

### parseMarkdownToStructure

将 markdown 字符串解析为 AST 结构。

```js
import { getMarkdown, parseMarkdownToStructure } from 'markstream-vue2'

const md = getMarkdown()
const nodes = parseMarkdownToStructure('# 标题\n\n这里的内容...', md)

// 与 MarkdownRender 一起使用
// 
```

### enableKatex / enableMermaid / enableD2

(重新)启用 KaTeX、Mermaid、D2 的功能加载器。默认 loader 已经启用,仅在你手动关闭过或需要自定义 loader(如 CDN 版本)时调用。

```js
import { enableD2, enableKatex, enableMermaid } from 'markstream-vue2'

// 启用 KaTeX loader
enableKatex()

// 启用 Mermaid loader
enableMermaid()

// 启用 D2 loader
enableD2()
```

## 自定义组件 API

### Props 接口

所有自定义节点组件都接收这些 props:

```ts
interface NodeComponentProps {
  node: ParsedNode // 解析后的节点数据
  indexKey: number | string // 节点的唯一键
  customId?: string // 用于作用域的自定义 ID
  isDark?: boolean // 主题标记(来自 MarkdownRender)
  typewriter?: boolean // 进入动画标记(仅非 code 节点)
  loading?: boolean // 流式中间态(来自 node.loading)
}
```

### 示例自定义组件

```vue





```

## 流式传输支持

markstream-vue2 支持流式 markdown 内容,节点上带有 `loading` 状态:

```vue



```

## TypeScript 支持

markstream-vue2 包含完整的 TypeScript 类型定义。对于 Vue 2.6.x,配置你的 `tsconfig.json`:

```json
{
  "compilerOptions": {
    "types": ["@vue/composition-api", "markstream-vue2"],
    "moduleResolution": "node",
    "esModuleInterop": true
  }
}
```

对于 Vue 2.7+,类型会自动包含:

```ts
import type { ParsedNode } from 'markstream-vue2'
import MarkdownRender from 'markstream-vue2'

// 你的组件具有适当的类型
import { defineComponent, ref } from 'vue'

export default defineComponent({
  components: { MarkdownRender },
  setup() {
    const markdown = ref('# Hello')
    const nodes = ref([])

    return { markdown, nodes }
  }
})
```

## 与 Vue 3 版本的差异

Vue 2 版本与 Vue 3 版本保持 API 兼容,但需要注意以下几点:

1. **Composition API**:Vue 2.6.x 需要 `@vue/composition-api`,Vue 2.7+ 内置支持
2. **插槽**:使用 Vue 2 的作用域插槽语法
3. **事件名称**:在模板中使用短横线命名的事件名称
4. **v-model**:无需更改,使用方式相同

## 下一步

- 查看 [Vue 2 快速开始](/zh/guide/vue2-quick-start) 获取设置示例
- 探索 [Vue 3 组件](/zh/guide/components) 获取更多组件示例(API 相同)
- 查看 [使用与 API](/zh/guide/usage) 获取高级模式