一、背景介绍:
wangEditor 5默认没有源码模式切换功能,但在实际应用中需要这个功能
二、插件开发
1、新建插件目录

2、根据官网API编写类文件和注册文件(https://www.wangeditor.com/v5/development.html)
sourceMenu.js
// 定义菜单类,参考官网 https://www.wangeditor.com/v5/development.html
class SourceMenu {
constructor() {
this.title = '源码' // 自定义菜单标题
this.iconSvg = "<svg t='1730795024638' class='icon' viewBox='0 0 1024 1024' version='1.1' xmlns='http://www.w3.org/2000/svg' p-id='8483' width='64' height='64'><path d='M280.746667 164.48H2.858667v822.485333h1021.013333V314.794667H442.453333L280.746667 164.48z m689.194666 765.781333H56.746667V221.226667h204.202666l161.706667 153.173333h547.328v555.861333zM510.506667 192.853333L354.517333 36.864H59.562667v56.746667H328.96l155.989333 155.989333h538.88V192.853333H510.464zM360.192 482.133333L201.386667 632.448l158.805333 147.498667 39.68-42.538667-116.266667-104.96 116.309334-107.776-39.722667-42.538667z m331.818667 297.813334l158.848-147.498667-158.848-150.314667-39.68 42.538667 116.266666 107.776-116.266666 104.96 39.68 42.538667z m-261.888 40.661333l113.408-368.64 54.186666 16.64-113.365333 368.64-54.186667-16.64z' fill='#5A5B5A' p-id='8484'></path></svg>" // 图标
this.tag = 'button'
this.active = false
}
/**
* 获取编辑器内容源码
*/
getValue(editor) {
return editor.getHtml();
}
/**
* 菜单是否需要激活,当切换为源码时菜单激活
*/
isActive(editor) {
return this.active;
}
/**
* 菜单是否需要禁用(如选中 H1 ,“引用”菜单被禁用),用不到则返回 false
*/
isDisabled(editor) {
return false;
}
/**
* 点击菜单时触发的函数
*/
exec(editor, value) {
this.active = !this.active;
if (this.isDisabled(editor)) return
editor.emit('clickSource', this.active);
}
}
export default SourceMenu;register.js
import SourceMenu from "./sourceMenu.js";
import prettier from 'prettier/standalone';
import parserHtml from 'prettier/parser-html';
/**
* 在编辑器中得到的html源码是没有格式的html字符串
* 所以需要格式化展示代码
* 格式化html代码
*/
export const parserHtmlCode = (code) => {
try {
return prettier.format(code, {
parser: 'html',
plugins: [parserHtml],
// 格式化的标签不换行 例如span标签等>格式化后会换行
htmlWhitespaceSensitivity: 'ignore'
});
} catch (e) {
console.error('格式化代码错误', e);
return code;
}
}
/**
* 将编辑器html转换为代码块内容
*/
export const parseEditorCode = (html) => {
const code = html
.replace(/ /g, '')
.replace(new RegExp('<p><br></p>', 'g'), '');
const data = parserHtmlCode(code).trim();
const textCode = data
.replace(/</g, "<")
.replace(/>/g, ">")
.replace(/ /g, " ");
return `<pre><code class="language-html">${textCode}</code></pre>`;
}
/**
* 将代码块转换为编辑器html
*/
export const parseCodeEditor = (preCode) => {
// 转码
let data = encodeURI(preCode);
// 将 转换为空格
data = data.replace(/%C2%A0/g, '%20');
// 解码
data = decodeURI(data);
const htmlStr = data
.replace('<pre><code class="language-html">', '')
.replace('</code></pre>', '')
.replace(/</ig, "<")
.replace(/>/ig, ">");
return htmlStr
.replace(new RegExp('\\n', 'g'), '')
.replace(new RegExp('<p><br></p>', 'g'), '')
.trim();
}
export const sourceConf = {
// 工具栏中的唯一key
key: 'source',
// 组件
factory: () => new SourceMenu()
};三、页面中使用
<div>
<Toolbar
style="border-bottom: 1px solid #ccc"
:editor="editor"
:default-config="toolbarConfig"
/>
<Editor
v-model="form.content"
style="height: 400px; overflow-y: hidden;"
@onCreated="onCreated"
/>
</div>
<script>
import '@wangeditor/editor/dist/css/style.css'
import { Boot } from '@wangeditor/editor';
import { Editor, Toolbar } from '@wangeditor/editor-for-vue'
import { parseCodeEditor, parseEditorCode, sourceConf } from "@/utils/wangEditor5-plug/register.js";
export default {
components: { Editor, Toolbar },
data() {
return {
editor: null,
toolbarConfig: { // 使用自定义扩展菜单'source'
insertKeys: {
index: 25,
keys: ['source']
}
},
}
},
mounted() {
},
created() {
},
beforeDestroy() {
const editor = this.editor
if (editor == null) return
editor.destroy() // 组件销毁时,及时销毁编辑器
},
methods: {
// 源码模式点击事件
clickSource(active, editor) {
let value = editor.getHtml();
// 先将编辑器内容清空
this.editor.clear();
if (active) {
// 将html代码转换为html代码块 dangerouslyInsertHtml是插入html不是重置html
this.editor.dangerouslyInsertHtml(parseEditorCode(value));
} else {
// 将html代码块转换为editor的html
this.editor.dangerouslyInsertHtml(parseCodeEditor(value));
console.log("parseCodeEditor(value)", parseCodeEditor(value))
value = parseCodeEditor(value);
}
},
onCreated(editor) {
this.editor = Object.seal(editor) // 一定要用 Object.seal() ,否则会报错
if (!this.editor.getAllMenuKeys().includes('source')) {
Boot.registerMenu(sourceConf); // 注册菜单
}
this.editor.on('clickSource', (active) => this.clickSource(active, this.editor));
}
}
}
</script>- 本文固定链接: http://ttfde.top/index.php/post/443.html
- 转载请注明: admin 于 TTF的家园 发表
《本文》有 0 条评论