简体中文 | English
Cherry Markdown Writer 是一款 Javascript Markdown 编辑器,具有开箱即用、轻量简洁、易于扩展等特点。它可以运行在浏览器或服务端(NodeJs)。
- 完整版
- 基础
- 移动端
- 多实例
- 无工具栏
- 纯预览模式
- XSS 测试(默认禁用,需配置后允许)
- IMG WYSIWYG
- 表格编辑
- 自动编号标题
- 流式输入模式(AI chat 场景)
- 流式输入模式 - 可选插件懒加载
- VIM 编辑模式
- 使用自带或自定义的 Mermaid.js
- 自定义代码块外层容器
开发者可以用非常简单的方式调用并实例化 Cherry Markdown 编辑器,实例化的编辑器默认支持绝大多数常用的 markdown 语法(例如标题、目录、流程图、公式等)。
当 Cherry Markdown 编辑器默认支持的语法无法满足需求时,可以进行二次开发或功能扩展。Cherry 基于纯 JavaScript 实现,不依赖 Angular、Vue、React 等框架(框架仅作为容器环境)。
开启流式渲染后,cherry会对以下语法进行自动补全,避免出现Markdown源码,以达到在流式输出过程中稳定输出的效果(demo):
- 标题
- 加粗、斜体
- 超链接
- 图片、音视频
- 行内代码块
- 段落代码块
- 行内公式
- 段落公式
- 无序列表
- 表格
- mermaid画图
- 脚注
- 图片缩放、对齐与引用
- 根据表格内容生成图表
- 字体颜色与字号调整
- 字体背景色、上标与下标
- 插入清单(checklist)
- 插入音视频
- 流程图(mermaid)、公式(数学)
- 信息面板
- 从富文本复制并粘贴为 Markdown
- 经典换行与常规换行支持
- 多光标编辑
- 图片尺寸编辑
- Mermaid 图表尺寸编辑与对齐布局(拖拽缩放、支持居中/左/右/浮动对齐)
- 表格编辑
- 根据表格内容生成图表(表格 -> 图表)
- 导出为图片或 PDF
- 浮动工具栏:在新行行首出现
- 气泡工具栏:选中文本时出现
- 设置快捷键
- 悬浮目录
- 主题切换
- 输入联想
- AI Chat场景流式输出场景特别支持
- 局部渲染
- 局部更新
Cherry Markdown 内置安全钩子,通过白名单过滤和 DomPurify 进行扫描过滤。
提供多种主题样式可选。
点击查看功能演示 Features demo
通过 yarn
yarn add cherry-markdown通过 npm
npm install cherry-markdown --save如果需要启用 mermaid 绘图和表格转图表功能,需要同时安装 mermaid 与 echarts。
Cherry Markdown 内置了 mermaid,如果希望使用指定版本的 mermaid,可以参考 wiki
<link href="cherry-editor.min.css" />
<div id="markdown-container"></div>
<script src="cherry-editor.min.js"></script>
<script>
new Cherry({
id: 'markdown-container',
value: '# welcome to cherry editor!',
});
</script>import 'cherry-markdown/dist/cherry-markdown.css';
import Cherry from 'cherry-markdown';
const cherryInstance = new Cherry({
id: 'markdown-container',
value: '# welcome to cherry editor!',
});const { default: CherryEngine } = require('cherry-markdown/dist/cherry-markdown.engine.core.common');
const cherryEngineInstance = new CherryEngine();
const htmlContent = cherryEngineInstance.makeHtml('# welcome to cherry editor!');由于 mermaid 库体积较大,cherry 提供了不内置 mermaid 的核心构建包,可按需引入。
import 'cherry-markdown/dist/cherry-markdown.css';
import Cherry from 'cherry-markdown/dist/cherry-markdown.core';
const cherryInstance = new Cherry({
id: 'markdown-container',
value: '# welcome to cherry editor!',
});// 导入 Cherry 引擎核心构建包
// 引擎的配置项与 Cherry 相同,以下内容仅介绍 Cherry 核心包的用法
import CherryEngine from 'cherry-markdown/dist/cherry-markdown.engine.core';
const cherryEngineInstance = new CherryEngine();
const htmlContent = cherryEngineInstance.makeHtml('# welcome to cherry editor!');
// --> <h1>welcome to cherry editor!</h1>核心构建包不包含 mermaid 依赖,需要手动引入相关插件。
import 'cherry-markdown/dist/cherry-markdown.css';
import Cherry from 'cherry-markdown/dist/cherry-markdown.core';
import CherryMermaidPlugin from 'cherry-markdown/dist/addons/cherry-code-block-mermaid-plugin';
import mermaid from 'mermaid';
// 插件注册必须在 Cherry 实例化之前完成
Cherry.usePlugin(CherryMermaidPlugin, {
mermaid, // 传入 mermaid 对象
// mermaidAPI: mermaid.mermaidAPI, // 也可以传入 mermaid API
// 同时可以在这里配置 mermaid 的行为,参考 mermaid 官方文档
// theme: 'neutral',
// sequence: { useMaxWidth: false, showSequenceNumbers: true }
});
const cherryInstance = new Cherry({
id: 'markdown-container',
value: '# welcome to cherry editor!',
});从 mermaid v10.0.0 开始,渲染逻辑由同步改为异步,afterChange 或 afterInit 事件后,mermaid 代码块先渲染为占位符,再异步渲染替换。
如果需要在异步渲染完成后获取渲染结果,可以参考如下示例:
const cherryInstance = new Cherry({
id: 'markdown-container',
// 使用模板字符串,内部直接包含 mermaid 的代码块
value: `
```mermaid
graph LR
A[公司] -->| 下 班 | B(菜市场)
B --> C{看见<br>卖西瓜的}
C -->|Yes| D[买一个包子]
C -->|No| E[买一斤包子]
```
`,
callback: {
afterAsyncRender: (md, html) => {
// md 是 markdown 源码,html 是渲染结果
}
}
});Cherry 提供了专为流式输出场景优化的构建包,该包不包含 mermaid、CodeMirror 等大型依赖,可实现按需懒加载,非常适合 AI Chat 等场景。
import 'cherry-markdown/dist/cherry-markdown.css';
import Cherry from 'cherry-markdown/dist/cherry-markdown.stream';
// 流式输出包默认不包含以下依赖,可按需加载:
// - mermaid(流程图)
// - CodeMirror(代码编辑器)
const cherryInstance = new Cherry({
id: 'markdown-container',
});
cherryInstance.setMarkdown('# welcome to cherry editor!');import 'cherry-markdown/dist/cherry-markdown.css';
import Cherry from 'cherry-markdown/dist/cherry-markdown.stream';
import CherryMermaidPlugin from 'cherry-markdown/dist/addons/cherry-code-block-mermaid-plugin';
import mermaid from 'mermaid';
// 插件注册必须在 Cherry 实例化之前完成
Cherry.usePlugin(CherryMermaidPlugin, {
mermaid,
mermaidAPI: mermaid,
});
const cherryInstance = new Cherry({
id: 'markdown-container',
});| 构建包 | 文件 | 包含 Mermaid | 包含 CodeMirror | 适用场景 |
|---|---|---|---|---|
| 完整包 | cherry-markdown.js |
✅ | ✅ | 通用场景 |
| 核心包 | cherry-markdown.core.js |
❌ | ✅ | 不需要 Mermaid |
| 流式输出包 | cherry-markdown.stream.js |
❌ | ❌ | AI Chat 流式输出 |
注意:MathJax/KaTeX 为外部依赖,通过 CDN 动态加载,不包含在任何构建包中。
强烈推荐使用动态引入(Dynamic import),下面给出 webpack 动态引入的示例。
import 'cherry-markdown/dist/cherry-markdown.css';
import Cherry from 'cherry-markdown/dist/cherry-markdown.core';
const registerPlugin = async () => {
const [{ default: CherryMermaidPlugin }, mermaid] = await Promise.all([
import('cherry-markdown/src/addons/cherry-code-block-mermaid-plugin'),
import('mermaid'),
]);
Cherry.usePlugin(CherryMermaidPlugin, {
mermaid, // 传入mermaid引用
});
};
registerPlugin().then(() => {
// 插件注册必须在 Cherry 实例化之前完成
const cherryInstance = new Cherry({
id: 'markdown-container',
value: '# welcome to cherry editor!',
});
});所有配置项基本都在 /src/Cherry.config.js 中进行了标注,详见:配置项全解
点击查看 Wiki 示例
正在开发中,可查看 packages/client/ 目录。
详见 自定义语法文档
cherry 支持五种工具栏位置,每个位置都可以扩展自定义工具按钮,详情见: 自定义工具栏按钮。
已经添加了基础的 Vitest 配置,但是相关测试用例还未完善,欢迎大家提交提供丰富的测试用例。
欢迎加入我们,一起打造强大的 Markdown 编辑器。在实现新功能或提交特性前,请先阅读:
