代码块

PreviousNext

Display code with syntax highlighting.

Loading…

功能特性

  • 代码块的语法高亮显示
  • 支持多种编程语言
  • 可自定义语言选择
  • 正确处理缩进
  • 通过 CodeBlockRules.markdown({ on }) 支持 Markdown 代码围栏快捷输入

套件使用

安装

最快捷添加代码块功能的方式是使用 CodeBlockKit,它包含预配置的 CodeBlockPluginCodeLinePluginCodeSyntaxPlugin,同时带上三反引号 input rule、语法高亮和 Plate UI 组件。

'use client';
 
import { CodeBlockRules } from '@platejs/code-block';
import {
  CodeBlockPlugin,
  CodeLinePlugin,
  CodeSyntaxPlugin,
} from '@platejs/code-block/react';
import { all, createLowlight } from 'lowlight';
 
import {
  CodeBlockElement,
  CodeLineElement,
  CodeSyntaxLeaf,
} from '@/components/ui/code-block-node';
 
const lowlight = createLowlight(all);
 
export const CodeBlockKit = [
  CodeBlockPlugin.configure({
    inputRules: [CodeBlockRules.markdown({ on: 'match' })],
    node: { component: CodeBlockElement },
    options: { lowlight },
    shortcuts: { toggle: { keys: 'mod+alt+8' } },
  }),
  CodeLinePlugin.withComponent(CodeLineElement),
  CodeSyntaxPlugin.withComponent(CodeSyntaxLeaf),
];
'use client';
 
import { CodeBlockRules } from '@platejs/code-block';
import {
  CodeBlockPlugin,
  CodeLinePlugin,
  CodeSyntaxPlugin,
} from '@platejs/code-block/react';
import { all, createLowlight } from 'lowlight';
 
import {
  CodeBlockElement,
  CodeLineElement,
  CodeSyntaxLeaf,
} from '@/components/ui/code-block-node';
 
const lowlight = createLowlight(all);
 
export const CodeBlockKit = [
  CodeBlockPlugin.configure({
    inputRules: [CodeBlockRules.markdown({ on: 'match' })],
    node: { component: CodeBlockElement },
    options: { lowlight },
    shortcuts: { toggle: { keys: 'mod+alt+8' } },
  }),
  CodeLinePlugin.withComponent(CodeLineElement),
  CodeSyntaxPlugin.withComponent(CodeSyntaxLeaf),
];

添加套件

将套件添加到你的插件中:

import { createPlateEditor } from 'platejs/react';
import { CodeBlockKit } from '@/components/editor/plugins/code-block-kit';
 
const editor = createPlateEditor({
  plugins: [
    // ...其他插件,
    ...CodeBlockKit,
  ],
});
import { createPlateEditor } from 'platejs/react';
import { CodeBlockKit } from '@/components/editor/plugins/code-block-kit';
 
const editor = createPlateEditor({
  plugins: [
    // ...其他插件,
    ...CodeBlockKit,
  ],
});

手动使用

安装

pnpm add @platejs/code-block lowlight
pnpm add @platejs/code-block lowlight

添加插件

在创建编辑器时,将代码块插件包含到 Plate 插件数组中。

import { CodeBlockPlugin, CodeLinePlugin, CodeSyntaxPlugin } from '@platejs/code-block/react';
import { createPlateEditor } from 'platejs/react';
 
const editor = createPlateEditor({
  plugins: [
    // ...其他插件,
    CodeBlockPlugin,
    CodeLinePlugin,
    CodeSyntaxPlugin,
  ],
});
import { CodeBlockPlugin, CodeLinePlugin, CodeSyntaxPlugin } from '@platejs/code-block/react';
import { createPlateEditor } from 'platejs/react';
 
const editor = createPlateEditor({
  plugins: [
    // ...其他插件,
    CodeBlockPlugin,
    CodeLinePlugin,
    CodeSyntaxPlugin,
  ],
});

配置插件

配置带有语法高亮和自定义组件的插件。

包含所有语言的基础设置:

import { CodeBlockRules } from '@platejs/code-block';
import { CodeBlockPlugin, CodeLinePlugin, CodeSyntaxPlugin } from '@platejs/code-block/react';
import { all, createLowlight } from 'lowlight';
import { createPlateEditor } from 'platejs/react';
import { CodeBlockElement, CodeLineElement, CodeSyntaxLeaf } from '@/components/ui/code-block-node';
 
// 创建包含所有语言的 lowlight 实例
const lowlight = createLowlight(all);
 
const editor = createPlateEditor({
  plugins: [
    // ...其他插件,
    CodeBlockPlugin.configure({
      inputRules: [CodeBlockRules.markdown({ on: 'match' })],
      node: { component: CodeBlockElement },
      options: { lowlight },
      shortcuts: { toggle: { keys: 'mod+alt+8' } },
    }),
    CodeLinePlugin.withComponent(CodeLineElement),
    CodeSyntaxPlugin.withComponent(CodeSyntaxLeaf),
  ],
});
import { CodeBlockRules } from '@platejs/code-block';
import { CodeBlockPlugin, CodeLinePlugin, CodeSyntaxPlugin } from '@platejs/code-block/react';
import { all, createLowlight } from 'lowlight';
import { createPlateEditor } from 'platejs/react';
import { CodeBlockElement, CodeLineElement, CodeSyntaxLeaf } from '@/components/ui/code-block-node';
 
// 创建包含所有语言的 lowlight 实例
const lowlight = createLowlight(all);
 
const editor = createPlateEditor({
  plugins: [
    // ...其他插件,
    CodeBlockPlugin.configure({
      inputRules: [CodeBlockRules.markdown({ on: 'match' })],
      node: { component: CodeBlockElement },
      options: { lowlight },
      shortcuts: { toggle: { keys: 'mod+alt+8' } },
    }),
    CodeLinePlugin.withComponent(CodeLineElement),
    CodeSyntaxPlugin.withComponent(CodeSyntaxLeaf),
  ],
});

自定义语言设置(优化包体积):

为了优化包体积,你可以只注册特定语言:

import { createLowlight } from 'lowlight';
import css from 'highlight.js/lib/languages/css';
import js from 'highlight.js/lib/languages/javascript';
import ts from 'highlight.js/lib/languages/typescript';
import html from 'highlight.js/lib/languages/xml';
 
// 创建 lowlight 实例
const lowlight = createLowlight();
 
// 只注册需要的语言
lowlight.register('html', html);
lowlight.register('css', css);
lowlight.register('js', js);
lowlight.register('ts', ts);
 
const editor = createPlateEditor({
  plugins: [
    // ...其他插件,
    CodeBlockPlugin.configure({
      inputRules: [CodeBlockRules.markdown({ on: 'match' })],
      node: { component: CodeBlockElement },
      options: {
        lowlight,
        defaultLanguage: 'js', // 设置默认语言(可选)
      },
      shortcuts: { toggle: { keys: 'mod+alt+8' } },
    }),
    CodeLinePlugin.withComponent(CodeLineElement),
    CodeSyntaxPlugin.withComponent(CodeSyntaxLeaf),
  ],
});
import { createLowlight } from 'lowlight';
import css from 'highlight.js/lib/languages/css';
import js from 'highlight.js/lib/languages/javascript';
import ts from 'highlight.js/lib/languages/typescript';
import html from 'highlight.js/lib/languages/xml';
 
// 创建 lowlight 实例
const lowlight = createLowlight();
 
// 只注册需要的语言
lowlight.register('html', html);
lowlight.register('css', css);
lowlight.register('js', js);
lowlight.register('ts', ts);
 
const editor = createPlateEditor({
  plugins: [
    // ...其他插件,
    CodeBlockPlugin.configure({
      inputRules: [CodeBlockRules.markdown({ on: 'match' })],
      node: { component: CodeBlockElement },
      options: {
        lowlight,
        defaultLanguage: 'js', // 设置默认语言(可选)
      },
      shortcuts: { toggle: { keys: 'mod+alt+8' } },
    }),
    CodeLinePlugin.withComponent(CodeLineElement),
    CodeSyntaxPlugin.withComponent(CodeSyntaxLeaf),
  ],
});
  • node.component: 指定 CodeBlockElement 来渲染代码块容器
  • inputRules:注册三反引号围栏规则。on: 'match' 表示围栏完成时立即提交,on: 'break' 表示围栏完成后按 Enter 再提交。
  • options.lowlight: 用于语法高亮的 lowlight 实例
  • options.defaultLanguage: 未指定语言时使用的默认语言
  • shortcuts.toggle: 定义切换代码块的键盘快捷键

完整运行时模型请参阅 Plugin Input Rules

  • withComponent: 为代码行和语法高亮指定组件

转换为工具栏按钮

你可以将此项目添加到转换为工具栏按钮中,将块转换为代码块:

{
  icon: <FileCodeIcon />,
  label: '代码',
  value: KEYS.codeBlock,
}
{
  icon: <FileCodeIcon />,
  label: '代码',
  value: KEYS.codeBlock,
}

插入工具栏按钮

你可以将此项目添加到插入工具栏按钮中,插入代码块元素:

{
  icon: <FileCodeIcon />,
  label: '代码',
  value: KEYS.codeBlock,
}
{
  icon: <FileCodeIcon />,
  label: '代码',
  value: KEYS.codeBlock,
}

插件

CodeBlockPlugin

Options

    未指定语言时使用的默认语言。设为 null 可默认禁用语法高亮。

    用于高亮的 lowlight 实例。如果未提供,将禁用语法高亮。

API

isCodeBlockEmpty

Returnsboolean

    判断选区是否在空代码块中。

isSelectionAtCodeBlockStart

Returnsboolean

    判断选区是否位于代码块第一行开头。

indentCodeLine

如果选区已展开或光标左侧无非空白字符,则缩进代码行。默认缩进为 2 个空格。

OptionsIndentCodeLineOptions

    要缩进的代码行。

    代码行的缩进大小。

    • 默认值: 2

insertCodeBlock

通过将节点设为代码行并用代码块包裹来插入代码块。如果光标不在块开头,则在代码块前插入换行。

Parameters

    插入节点的选项。

insertCodeLine

插入以指定缩进深度开头的代码行。

Parameters

    代码行的缩进深度。

    • 默认值: 0

outdentCodeLine

减少代码行的缩进,如果存在则移除两个空白字符。

OptionsOutdentCodeLineOptions

    要减少缩进的代码行。

    包含要减少缩进代码行的代码块。

toggleCodeBlock

切换编辑器中的代码块。

unwrapCodeBlock

解除编辑器中的代码块包裹。