blog/content/post/奇技淫巧/md-editor-v3.md
2025-04-17 02:43:09 +08:00

3.9 KiB
Raw Blame History

title description date categories tags lastmod
Vue项目中在md-editor-v3工具栏中添加自定义工具 以NEU小站中的“选择课程”工具为例 2025-04-16
奇技淫巧
md-editor-v3
Markdown
Vue
前端
NEU小站
2025-04-16T23:56:00+08:00

效果

在基于Vue3的个人项目我在md-editor-v3的工具栏中实现了一个“选择课程”工具可以帮助用户搜索并选择相应的课程然后插入一个包含课程id的组件标签。效果

实现

首先我们需要在组件处注册一个自定义工具的模板,注意使用#defToolbars,设置好图标、说明文字和点击事件,参考此处

<div class="editor-container">
<MdEditor
    v-model="formData.content"
    ref="markdownEditor"
    :theme="editorTheme"
    :toolbars="editorToolbars"
    language="zh-CN"
    preview-theme="github"
    :placeholder="editorPlaceholder"
    @onUploadImg="handleImageUpload"
>
    <!-- 自定义工具 -->
    <template #defToolbars>
        <span class="md-editor-toolbar-item" title="添加课程卡片" @click="chooseCourse">
        <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-linecap="round" stroke-linejoin="round" width="20" height="24" stroke-width="1.1">
            <path d="M22 9l-10 -4l-10 4l10 4l10 -4v6"></path>
            <path d="M6 10.6v5.4a6 3 0 0 0 12 0v-5.4"></path>
        </svg>
        </span>
    </template>
</MdEditor>
</div>

<script>
import MdEditor from 'md-editor-v3';
import 'md-editor-v3/lib/style.css';
export default {
    components: {
        MdEditor
    }
}
</script>

然后,在data()editorToolbars中添加自定义工具的配置,这里非常重要,需要用0来表示自定义工具的位置。如果有多个自定义工具则以此类推0、1、2...,类似数组下标。

editorToolbars: [
    'bold', 'italic', 'strikethrough', 'title', 'sub', 'sup', 'quote', 'unordered-list', 
    'ordered-list', 'link', 'image', 'table', 'code-block', 'inline-code', 'preview',
    'fullscreen', '-', 'revoke', 'next', '-', 0
],

这样我们的自定义图标就会出现在工具栏的对应位置。现在完成chooseCourse方法。方法内的逻辑自行定义,但是我们最终的操作一般是需要在编辑器中插入一段文本,所以需要使用编辑器提供的insert方法。

参考insert API,文档如下:

/**
 * @params selectedText 选中的内容
 */
editorRef.value?.insert((selectedText) => {
  /**
   * @return targetValue    待插入内容
   * @return select         插入后是否自动选中内容默认true
   * @return deviationStart 插入后选中内容鼠标开始位置默认0
   * @return deviationEnd   插入后选中内容鼠标结束位置默认0
   */
  return {
    targetValue: `${selectedText}`,
    select: true,
    deviationStart: 0,
    deviationEnd: 0,
  };
});

说明我们需要返回一个对象,对象中的targetValue就是我们最终插入的内容。这里给个简单的例子:

chooseCourse() {
    const id = 3;
    this.$refs.markdownEditor?.insert((selectedText) => {
        return {
            targetValue: `<CourseCard id="${id}" />\n`
        }
    })
}

这样,点击这个工具,就会在编辑器中插入<CourseCard id="3" />。具体的查询逻辑可以自行实现,这里不再赘述。