tinymce编辑器自定义功能插件
antd3+vit,集成富文本编辑器,需要实现自定义的上下文菜单和工具栏菜单。
包括如何在tinymce编辑器的工具栏增加图标以及自定义功能实现,(PS:我用的编辑器是5.x版本的,6.x版本的插件文件可能是plugin.min.js,但原理相同)
一 在项目中引入tinymce
kotlin
npm install tinymce@^5.10.3 -S
npm install @tinymce/tinymce-vue@^6.0.1 -S
二 依赖包移动
以上两条命令通过npm拉取了tinymce的依赖包,可以在node_modules 中找到 tinymce文件夹,将tinymce目录拷贝到public目录下,其中skins是必需的,其他按需引入,根据名称可知道用途。 需要汉化的可以在官网下载语言包,汉化包地址,下载完成后将解压后的文件夹存放在与刚才那些文件相同的位置.
那么打开你的plugins文件夹,里面的内容就是你tinymce的功能插件了。
三 注册你的自定义插件
如果你是像我一样将将npm包中的tinymce文件夹复制到公共文件夹下引用的话,那么在你页面中引用的时候,需要指定tinymce.baseURL的路径,不然无法加载自定义的插件,页面上的插件都是核心编辑器自带的。
js
import tinymce from 'tinymce/tinymce'
import Editor from '@tinymce/tinymce-vue'
... //省略vue中间的一大堆代码
onBeforeMount(() => {
tinymce.baseURL = "tinymce";
});
四 新增工具栏按钮
4.1 新增插件定义js
那么打开你的plugins文件夹,里面的内容就是你tinymce的功能插件了,可以新增一个名为custom_plugin的文件夹,即我们自定义的插件。 在custom_plugin文件夹中新建plugin.js文件,在其中写入我们的插件逻辑,如
js
;(function () {
tinymce.PluginManager.add('custom_plugin', function (editor) {
// 在这里添加你的插件逻辑
editor.ui.registry.addButton('custom_button', {
text: 'custom_button',
// icon: '',
tooltip: '自定义',
onAction: function () {
window.alert('自定义插件')
},
})
})
})()
- 初始化编辑器时引入我们之前写好的插件,如下。需要注意的就是plugins属性中填入你的插件文件夹名字,而toolbar中填入你插件中注册好的方法。插件的名称与文件夹的名称需要一致。
4.2 新增工具栏插件引用
js
tinymce.init({
selector: 'textarea', // 选择你的 textarea 元素
plugins: 'custom_plugin', // 你的插件名称
toolbar: 'custom_button', // 将你的按钮添加到工具栏
// 其他初始化选项...
});
- 效果图如下:
4.3 优化图标
当然,你不希望只是用文字来点击,你希望图标代替,使用自定义的图标也很简单。
公共文件夹中tinymce/icons/default/icons.js文件中存放着所有tinymce中使用的图标。
在icons.js中加入你的图标,推荐使用svg代码,阿里巴巴矢量图标库里的图标可以满足99.99%的需求了,链接在这里: 阿里巴巴矢量图标库
js
tinymce.IconManager.add('default', {
icons: {
'custom-button':
'<svg t="1690962765928" class="icon" viewBox="0 0 1024 1024" version="1.1" xmlns="http://www.w3.org/2000/svg" p-id="3494" width="24" height="24"><path d="M1009.992 464.055c-6.551-6.944-18.336-15.222-37.281-15.222l-49.371 0c-38.996-25.66-120.146-79.334-133.599-89.515-11.267-8.528-18.037-15.434-20.123-20.527-1.656-4.044-1.621-10.133-1.405-21.439 0.065-3.444 0.14-7.348 0.14-11.519 0-62.287-42.817-102.91-50.405-109.618-6.619-6.281-69.046-65.429-99.237-90.858-36.233-30.516-78.03-39.091-82.678-39.968-1.957-0.37-3.944-0.556-5.937-0.556l-207 0c-47.593 0-81.063 32.921-89.606 42.268L9.148 304.64l-0.389-0.056c-0.209 1.445-5.091 35.838-2.612 75.772 3.679 59.291 21.385 100.722 52.625 123.142 38.728 27.793 63.563 91.347 69.852 113.441 3.922 13.951 16.632 23.343 30.78 23.342 1.419 0 2.854-0.095 4.294-0.289 6.367-0.857 63.158-9.331 96.358-42.532 40.682-40.681 116.825-177.352 125.373-192.802l-55.999-30.985c-22.023 39.797-85.546 149.45-114.629 178.532-8.286 8.287-22.122 14.338-34.708 18.369-3.126-7.871-6.994-16.877-11.632-26.421-20.155-41.479-44.506-72.651-72.375-92.652-14.304-10.265-23.537-36.589-26-74.123-1.002-15.274-0.677-29.789-0.025-41.099l207.183-182.431c1.268-1.117 2.124-1.947 3.188-3.234 5.468-6.17 23.464-21.782 42.665-21.782l203.4 0c7.638 1.93 31.333 8.924 50.985 25.476 29.77 25.071 96.204 88.133 96.872 88.767 0.503 0.478 1.021 0.939 1.555 1.383 0.284 0.237 28.444 24.723 28.444 61.374 0 3.562-0.065 6.987-0.128 10.3-0.285 14.963-0.58 30.436 6.169 46.914 6.764 16.516 19.323 31.104 40.723 47.302 18.784 14.217 132.207 88.775 145.078 97.23 5.218 3.428 11.325 5.254 17.568 5.254l45.725 0 0 55.486-118.379 115.162c-0.723 0.704-0.585 0.491-1.022 1.011-2.803 2.556-22.901 19.341-66.99 19.341l-327.156 0c-11.386-0.487-53.997 1.231-100.804 48.039-20.792 20.791-199.636 208.854-207.239 216.85l46.379 44.103c1.856-1.953 185.888-195.471 206.115-215.698 27.152-27.153 48.025-29.224 51.947-29.365 1.254 0.214 1.035 0.071 2.758 0.071l328 0c71.04 0 106.152-31.842 112.987-38.815l127.718-124.248c6.193-6.024 9.687-14.297 9.687-22.937l0-81.681C1023.647 493.763 1022.647 477.47 1009.992 464.055zM959.501 498.675c0.007-0.35 0.025-0.662 0.041-0.932C959.524 498.053 959.51 498.364 959.501 498.675zM640.5 417.487l0-67.497c0-16.568-14.119-29.999-31.535-29.999-17.417 0-31.536 13.431-31.536 29.999l0 67.497c0 16.568 14.119 29.999 31.536 29.999C626.381 447.486 640.5 434.055 640.5 417.487z" fill="#272636" p-id="3495"></path></svg>',
},
})
- 图标引用: public/tinymce/plugins/custom_plugin/plugin.js。
js
;(function () {
tinymce.PluginManager.add('custom_plugin', function (editor) {
// 在这里添加你的插件逻辑
editor.ui.registry.addButton('custom_button', {
text: '',
icon: 'custom-button',
tooltip: '自定义',
onAction: function () {
window.alert('自定义插件')
},
})
})
})()
- 效果图
- 至此,新增工具栏按钮完成。
五 新增自定义上下文菜单
5.1 新增插件定义js
那么打开你的plugins文件夹,里面的内容就是你tinymce的功能插件了,可以新增一个名为fileman的文件夹,即我们自定义的插件。 在fileman文件夹中新建plugin.js文件,在其中写入我们的插件逻辑,如 public/tinymce/plugins/fileman/plugin.js。
- 其中addMenuItem是注册新增菜单。
js
;(function () {
tinymce.PluginManager.add("fileman", function (editor) {
editor.ui.registry.addMenuItem("fileman", {
icon: "image",
text: "测试",
shortcut: "Ctrl+J",
onAction: function (e) {
console.log(e);
// fileman.launch("editor");
console.log(`fileman自定义菜单被点击`);
// 取消默认的e功能
// e.preventDefault();
console.log(`fileman自定义菜单被点击3`);
},
context: "insert",
prependToContext: true,
});
});
})()
5.2 新增上下文菜单插件引用
js
tinymce.init({
selector: 'textarea', // 选择你的 textarea 元素
plugins: 'fileman', // 你的插件名称
contextmenu: 'fileman', // 将你的按钮添加到上下文菜单
// 其他初始化选项...
});
- 效果图如下:
六 新增自定义上下文菜单(第二种方法)
- 可以直接在当前.vue文件中注册菜单。然后在当前.vue文件中引用。
js
<script setup lang="ts">
import { onBeforeMount, reactive, ref, onMounted, defineEmits, watch } from "vue";
// import { upload } from "@/api/uploads"; // 自定义上传方法
import Editor from "@tinymce/tinymce-vue";
import tinymce from "tinymce/tinymce";
import "tinymce/themes/silver";
import "tinymce/themes/silver/theme";
// import "tinymce/models/dom";
import "tinymce/icons/default";
import "tinymce/icons/default/icons";
// 引入编辑器插件
import "tinymce/plugins/code"; //编辑源码
import "tinymce/plugins/image"; //插入编辑图片
// import "tinymce/plugins/media"; //插入视频
// import "tinymce/plugins/link"; //超链接
import "tinymce/plugins/preview"; //预览
import "tinymce/plugins/template"; //模板
import "tinymce/plugins/table"; //表格
import "tinymce/plugins/pagebreak"; //分页
import "tinymce/plugins/lists"; //列
import "tinymce/plugins/advlist"; //列
import "tinymce/plugins/quickbars"; //快速工具条
import "tinymce/plugins/wordcount"; // 字数统计插件
// import "@/assets/tinymce/langs/zh-Hans.js"; //下载后的语言包
import "tinymce/skins/content/default/content.css";
// import "./plugin/ai-smart.js";
const emits = defineEmits(["update:value"]);
onBeforeMount(() => {
tinymce.baseURL = "tinymce";
});
tinymce.PluginManager.add("fileman", function (editor) {
editor.ui.registry.addMenuItem("fileman", {
icon: "image",
text: "测试",
shortcut: "Ctrl+J",
onAction: function (e) {
console.log(e);
// fileman.launch("editor");
console.log(`fileman自定义菜单被点击`);
// 取消默认的e功能
// e.preventDefault();
console.log(`fileman自定义菜单被点击3`);
},
context: "insert",
prependToContext: true,
});
});
。。。。
tinymce.init({
selector: 'textarea', // 选择你的 textarea 元素
plugins: 'fileman', // 你的插件名称
contextmenu: 'fileman', // 将你的按钮添加到上下文菜单
// 其他初始化选项...
});
七 新增自定义上下文菜单(第三种方法)
- 可以在当前.vue文件附近新增插件,然后在.vue中引用。
- 比如新增文件 src/components/MyTiny/plugin/ai-smart.js。
- 然后在 src/components/MyTiny/index.vue中引用。
- src/components/MyTiny/plugin/ai-smart.js内容如下
js
import tinymce from "tinymce/tinymce";
;(function () {
tinymce.PluginManager.add("fileman", function (editor) {
editor.ui.registry.addMenuItem("fileman", {
icon: "image",
text: "测试",
shortcut: "Ctrl+J",
onAction: function (e) {
console.log(e);
// fileman.launch("editor");
console.log(`fileman自定义菜单被点击`);
// 取消默认的e功能
// e.preventDefault();
console.log(`fileman自定义菜单被点击3`);
},
context: "insert",
prependToContext: true,
});
});
})()
- 在.vue中引用
js
import "./plugin/ai-smart.js";
源码
本文档中示例源码已上传到这里,供参考。