【vue3】wangEditor 5在vue3中的使用
实现效果:
将wangEditor富文本编辑器进行封装,父组件可以使用子组件富文本编辑器中的数据用于api对接。
1.安装
官网:https://www.wangeditor.com
# Vue2 安装
yarn add @wangeditor/editor-for-vue
# 或者 npm install @wangeditor/editor-for-vue --save
# Vue3 安装
yarn add @wangeditor/editor-for-vue@next
# 或者 npm install @wangeditor/editor-for-vue@next --save
2.创建编辑器vue文件
commonEdit.vue
<template>
<div style="border: 1px solid #ccc">
<Toolbar
:editor="editorRef"
:defaultConfig="toolbarConfig"
:mode="mode"
style="border-bottom: 1px solid #ccc"
/>
<Editor
v-model="valueHtml"
:defaultConfig="editorConfig"
:mode="mode"
@onCreated="handleCreated"
@onChange="handleChange"
style="height: 500px; overflow-y: hidden;"
/>
</div>
</template>
<script setup lang="ts">
import { watch,onBeforeUnmount,nextTick, ref, shallowRef, onMounted,onBeforeMount } from 'vue'
//@ts-ignore
import { Editor, Toolbar } from '@wangeditor/editor-for-vue'
import '@wangeditor/editor/dist/css/style.css' // 引入 css
// Props:使用属性,子组件接收父组件传递的内容
const props = defineProps({
content: { type: String, default: '' }
})
// Emits:使用事件,将子组件内容传递给父组件。父组件使用 update(content: string)
const emit = defineEmits<{ (e: 'update', content: string): void }>()
const mode = ref('default')
// 编辑器实例,必须用 shallowRef
const editorRef = shallowRef()
// 内容 HTML
const valueHtml = ref('')
const toolbarConfig = {}
const editorConfig = {
placeholder: '请输入内容...' ,
MENU_CONF:{} as any
}
// 上传图片配置
editorConfig.MENU_CONF['uploadImage'] = {
// form-data fieldName ,默认值 'wangeditor-uploaded-image'。传给后端接口的参数名,重要!
fieldName: 'file',
server: 'http://localhost:8080/files/wangEditorUpload'
}
const handleCreated = (editor:any) => {
editorRef.value = editor // 记录 editor 实例,重要!
}
const handleChange = () => {
valueHtml.value = editorRef.value.getHtml()
emit('update', valueHtml.value)
}
// 监听 props 变化,监听父组件传来的content
watch(() => props.content, (newVal:string) => {
nextTick(() => {
if (editorRef.value) {
// console.log(" 当前编辑器的状态:", editorRef.value);
// 富文本编辑器按 html 格式回显
editorRef.value.setHtml(newVal)
valueHtml.value = newVal
}
})
}
)
onMounted(async() => {
await nextTick(); // 延迟渲染,确保 DOM 更新完成
if(props.content) {
valueHtml.value = props.content
}
})
// 组件销毁时,也及时销毁编辑器
onBeforeUnmount(() => {
const editor = editorRef.value
if (editor == null) return
editor.destroy()
})
</script>
3.父组件中引用
<template>
<el-form :model="form" label-width="auto" style="max-width: 800px">
<el-form-item label="文章标题">
<el-input v-model="form.title" />
</el-form-item>
<el-form-item label="文章内容">
<commonEdit :content="form.html" @update="update"/>
</el-form-item>
<el-form-item label="文章简介">
<el-input v-model="form.desc" type="textarea" />
</el-form-item>
<el-form-item>
<el-button type="primary" @click="onSubmit(form)">提交</el-button>
<el-button>取消</el-button>
</el-form-item>
</el-form>
</template>
<script lang="ts" setup>
import commonEdit from '../components/commonEdit.vue';
import { reactive } from 'vue'
import { addArticle } from '../api';
import router from '../router';
// do not use same name with ref
const form = reactive({
title: '',
desc: '',
html:'',
})
const onSubmit = (data:any) => {
console.log(data);
addArticle(data)
router.push('/article')
}
// 更新富文本编辑器内容
const update = (content:string) => {
form.html=content
};
</script>