編輯器
Editor Code Block
程式碼區塊;語言選擇與語法上色。
安裝
Terminal
pnpm dlx shadcn-vue add @admin/editor-code-blockimport { createCodeBlockExtension, editorCodeBlockClass } from '@/registry/admin/ui/editor-code-block'本包以 @tiptap/extension-code-block-lowlight(highlight.js)取代 StarterKit 內建的 codeBlock,註冊 lowlight/common 的常用語言,並在每個區塊右上角掛上可搜尋的語言下拉。lowlight 隨安裝一併帶入,不用另裝。
用法
啟用要兩步:先 :starter-kit="{ codeBlock: false }" 關掉內建 codeBlock,再把 createCodeBlockExtension() 加進 :extensions。上色配色由 editorCodeBlockClass 提供,append 到 :ui 的 base。
<script setup lang="ts">import type { JSONContent } from '@tiptap/core'import { ref } from 'vue'import { cn } from '@/lib/utils'import { baseProseClass } from '@/components/admin/editor'import { createCodeBlockExtension, editorCodeBlockClass} from '@/components/admin/editor-code-block'import { AdminEditorToolbar, defaultEditorItems } from '@/components/admin/editor-toolbar'import { AdminRichEditor, starterKitProseClass } from '@/components/admin/rich-editor'const value = ref<JSONContent | string>( "<p>點程式碼區塊右上角的下拉可切換語言,選好即時上色:</p><pre><code class=\"language-typescript\">function greet(name: string): string {\n return 'Hello, ' + name\n}\nconsole.log(greet('TPI'))</code></pre>")// opt-in:關掉 starter-kit 內建 codeBlock,改用本擴展(含語言下拉 + lowlight 上色)const extensions = [createCodeBlockExtension()]</script><template> <admin-rich-editor v-slot="{ editor, handlers }" v-model="value" :extensions="extensions" :starter-kit="{ codeBlock: false }" :ui="{ base: cn(baseProseClass, starterKitProseClass, editorCodeBlockClass) }" > <admin-editor-toolbar :editor :handlers="handlers" :items="defaultEditorItems" /> </admin-rich-editor></template><script setup lang="ts">import { ref } from 'vue'import { cn } from '@/lib/utils'import { baseProseClass } from '@/registry/admin/ui/editor'import { createCodeBlockExtension, editorCodeBlockClass } from '@/registry/admin/ui/editor-code-block'import { AdminEditorToolbar, defaultEditorItems } from '@/registry/admin/ui/editor-toolbar'import { AdminRichEditor, starterKitProseClass } from '@/registry/admin/ui/rich-editor'const value = ref('<pre><code class="language-typescript">const x = 1</code></pre>')const extensions = [createCodeBlockExtension()]</script><template> <admin-rich-editor v-slot="{ editor, handlers }" v-model="value" :extensions="extensions" :starter-kit="{ codeBlock: false }" :ui="{ base: cn(baseProseClass, starterKitProseClass, editorCodeBlockClass) }" > <admin-editor-toolbar :editor :handlers="handlers" :items="defaultEditorItems" /> </admin-rich-editor></template>啟用後:
- toolbar 的程式碼區塊按鈕照舊建立/取消區塊
- 區塊右上角的下拉切換語言,選好就上色;預設「純文字」不上色
- 存檔輸出標準的
<pre><code class="language-<lang>">,純文字則是language-plaintext - 唯讀(
:editable="false")時下拉收起,程式碼仍照原語言上色
預設語言
新建區塊預設為純文字,要換個預設語言就傳 defaultLanguage:
const extensions = [createCodeBlockExtension({ defaultLanguage: 'typescript' })]注意事項
- 一定要先關掉內建
codeBlock:本擴展跟 StarterKit 的codeBlock同名,同時存在會讓 TipTap 拋duplicate node: codeBlock。 - 顏色不寫進內容:語法色是顯示層的 decoration,存檔只留純碼與
languageclass,前台各自於 render 時再上色。 - 前台要一致上色:把
editorCodeBlockClass一起 append 到前台唯讀 viewer 容器的:class,顏色才會跟編輯器一致。
API 參考
| 匯出 | 說明 |
|---|---|
createCodeBlockExtension(options?) | 回傳配置好 lowlight 與語言下拉的 code block extension,傳入 <AdminRichEditor :extensions> |
editorCodeBlockClass | 語法上色的 class 字串(hljs-* 對應 admin tokens),append 到 :ui 的 base 或前台 viewer 容器 |
| 選項 | 型別 | 預設 | 說明 |
|---|---|---|---|
defaultLanguage | string | 'plaintext' | 新建區塊的預設語言 |