| 1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495 |
- <script setup lang="ts">
- import '@wangeditor/editor/dist/css/style.css'
- import { Editor, Toolbar } from '@wangeditor/editor-for-vue'
- import type { IToolbarConfig, IEditorConfig } from '@wangeditor/editor'
- import { ACCESS_TOKEN, TOKEN_PREFIX } from '@/utils/constants'
- import { isAbsolutePath } from '@/utils/utils'
- import { useUserStore } from '@/stores/user'
- import config from '@/config/defaultSetting'
- interface Props {
- modelValue: string
- mode?: string
- height?: string
- uploadApi?: string
- fieldName?: string
- toolbarConfig?: Partial<IToolbarConfig>
- editorConfig?: Partial<IEditorConfig>
- }
- const props = withDefaults(defineProps<Props>(), {
- mode: 'simple',
- height: '300px',
- uploadApi: config.uploadApi,
- fieldName: 'file'
- })
- const emits = defineEmits(['update:modelValue', 'change'])
- // 编辑器实例,必须用 shallowRef
- const editorRef = shallowRef()
- // 内容 HTML
- const valueHtml = computed({
- get: () => props.modelValue,
- set: value => emits('update:modelValue', value)
- })
- const userStore = useUserStore()
- const editorConfig = {
- placeholder: '请输入内容...',
- MENU_CONF: {
- uploadImage: {
- server: isAbsolutePath(props.uploadApi) ? props.uploadApi : import.meta.env.VITE_BASE_API + props.uploadApi,
- headers: { [ACCESS_TOKEN]: TOKEN_PREFIX + userStore.token },
- fieldName: props.fieldName,
- // 自定义插入图片
- customInsert(res: any, insertFn: Function) {
- const file = res?.data
- insertFn(import.meta.env.VITE_BASE_PATH + file)
- }
- }
- },
- ...props.editorConfig
- }
- // 组件销毁时,也及时销毁编辑器
- onBeforeUnmount(() => {
- const editor = editorRef.value
- if (editor == null) return
- editor.destroy()
- })
- const handleCreated = (editor: any) => {
- editorRef.value = editor // 记录 editor 实例,重要!
- }
- const handleChange = (editor: any) => {
- emits('change', editor.getHtml())
- }
- defineExpose({
- editorRef
- })
- </script>
- <template>
- <div style="border: 1px solid var(--el-border-color); z-index: 2" class="w-full">
- <Toolbar
- style="border-bottom: 1px solid var(--el-border-color)"
- :editor="editorRef"
- :defaultConfig="toolbarConfig"
- :mode="mode"
- />
- <Editor
- style="overflow-y: hidden"
- :style="{ height: height }"
- v-model="valueHtml"
- :defaultConfig="editorConfig"
- :mode="mode"
- @onCreated="handleCreated"
- @onChange="handleChange"
- />
- </div>
- </template>
- <style lang="scss" scoped></style>
|