vue2.6+ 实现tinymce5富文本编辑器以及图片上传

  1. 安装tinymce
    npm install tinymce -S
    npm install @tinymce/tinymce-vue -S
  2. 下载中文语言包
  3. 地址:https://www.tiny.cloud/get-ti...
    下载选中的中文包

    下载完之后在项目里新建public文件夹

    1)在public目录下新建tinymce文件夹,并将下载的语言包解压到该目录下

    2)在node_modules里面找到tinymce,将skins目录复制到public/tinymce里面,目录如下:

    3.tinymce使用
    1)封装组件

    <template>
        <div class="tinymce-editor">
            <Editor
                    :id="tinymceId"
                    :init="init"
                    :disabled="disabled"
                    v-model="myValue"
                    @onClick="onClick"
            ></Editor>
        </div>
    </template>
    
    <script>
      import axios from "axios";
      import tinymce from 'tinymce/tinymce' //tinymce默认hidden,不引入不显示
      import Editor from '@tinymce/tinymce-vue'//编辑器引入
      import 'tinymce/themes/silver/theme'//编辑器主题
      import 'tinymce/icons/default'  //引入编辑器图标icon,不引入则不显示对应图标
      // 引入编辑器插件(基本免费插件都在这儿了)
      import 'tinymce/plugins/advlist'  //高级列表
      import 'tinymce/plugins/autolink'  //自动链接
      import 'tinymce/plugins/link'  //超链接
      import 'tinymce/plugins/image'  //插入编辑图片
      import 'tinymce/plugins/lists' //列表插件
      import 'tinymce/plugins/charmap'  //特殊字符
      import 'tinymce/plugins/media' //插入编辑媒体
      import 'tinymce/plugins/wordcount'// 字数统计
      import Cookies from "js-cookie";
    
      const fonts = [
        "宋体=宋体",
        "微软雅黑=微软雅黑",
        "新宋体=新宋体",
        "黑体=黑体",
        "楷体=楷体",
        "隶书=隶书",
        "Courier New=courier new,courier",
        "AkrutiKndPadmini=Akpdmi-n",
        "Andale Mono=andale mono,times",
        "Arial=arial,helvetica,sans-serif",
        "Arial Black=arial black,avant garde",
        "Book Antiqua=book antiqua,palatino",
        "Comic Sans MS=comic sans ms,sans-serif",
        "Courier New=courier new,courier",
        "Georgia=georgia,palatino",
        "Helvetica=helvetica",
        "Impact=impact,chicago",
        "Symbol=symbol",
        "Tahoma=tahoma,arial,helvetica,sans-serif",
        "Terminal=terminal,monaco",
        "Times New Roman=times new roman,times",
        "Trebuchet MS=trebuchet ms,geneva",
        "Verdana=verdana,geneva",
        "Webdings=webdings",
        "Wingdings=wingdings,zapf dingbats"
      ];
      export default {
        components: {
          Editor
        },
        props: {
          //内容
          value: {
            type: String,
            default: ''
          },
          //是否禁用
          disabled: {
            type: Boolean,
            default: false
          },
          //插件
          plugins: {
            type: [String, Array],
            default: 'advlist autolink link image lists charmap  media wordcount'
          },
          //工具栏
          toolbar: {
            type: [String, Array],
            default: 'undo redo |  formatselect | bold italic | alignleft aligncenter alignright alignjustify | bullist numlist outdent indent | lists image media table'
          }
        },
        data() {
          return {
            //初始化配置
            tinymceId: 'tinymce',
            myValue :this.value,
            init: {
              selector: '#tinymce',
              language_url: '/tinymce/langs/zh_CN.js',//汉化路径是自定义的,一般放在public或static里面
              language: 'zh_CN',
              skin_url: '/tinymce/skins/ui/oxide',//皮肤
              plugins: this.plugins,//插件
              //工具栏
              toolbar: this.toolbar,
              toolbar_location: '/',
              fontsize_formats: '12px 14px 16px 18px 20px 22px 24px 28px 32px 36px 48px 56px 72px',  //字体大小
              font_formats: fonts.join(";"),
    
              height: 500,//高度
              placeholder: '在这里输入文字',
    
              branding: false,//隐藏右下角技术支持
              //图片上传
              images_upload_handler: function (blobInfo, success, failure) {
                //文件上传的formData传递,忘记为什么要用这个了
                const isAccord = blobInfo.blob().type === 'image/jpeg' || blobInfo.blob().type === 'image/png' || blobInfo.blob().type === 'image/GIF' || blobInfo.blob().type === 'image/jpg' || blobInfo.blob().type === 'image/BMP';
                if (blobInfo.blob().size/1024/1024>2) {
                  failure("上传失败,图片大小请控制在 2M 以内")
                } else if (blobInfo.blob().type == isAccord) {
                  failure('图片格式错误')
                } else {
                  let formData = new FormData()
                  // 服务端接收文件的参数名,文件数据,文件名
                  formData.append('file', blobInfo.blob(), blobInfo.filename())
                  axios({
                    method: 'POST',
                    headers: {
                      Authorization: 'bearer ' + Cookies.get('access_token')
                    },
                    // 这里是你的上传地址
                    url:  window.SITE_CONFIG['apiURL'] + '/oss/file/upload',
                    data: formData,
                  }).then((res) => {
                    console.log(res)
                    // 这里返回的是你图片的地址
                    success(res.data.data.url)
                  }).catch(() => {
                    failure('上传失败')
                  })
                }
              }
            }
          }
        },
        watch: {
          //监听内容变化
          value(newValue) {
            this.myValue = (newValue == null ? '' : newValue)
          },
          myValue (newValue) {
            if(this.triggerChange){
              this.$emit('change', newValue)
            }else{
              this.$emit('input', newValue)
            }
          }
        },
        mounted () {
          tinymce.init({})
          // console.log(this.toolbar,'======')
        },
        methods: {
          onClick(e) {
            this.$emit('onClick', e, tinymce)
          },
          //可以添加一些自己的自定义事件,如清空内容
          clear() {
            this.myValue = ''
          }
        }
      }
    </script>

    注:当遇到报错信息 Uncaught SyntaxError: Unexpected token '<' 时,检查引入的 语言包 和 编辑器主题 的路径是否正确
    语言包的路径引入不需要加 public/static 文件夹
    4.组件注册及使用

    1)在main.js中全局注册

    import TEditor from '@/views/components/TEditor.vue'
    Vue.component('TinymceEditor',TEditor)
    

    2)在页面使用

    <el-form-item label="商品详情:" prop="detail"> <TinymceEditor v-model="dataForm.detail" >TinymceEditor>
    el-form-item>

    效果图:

    到此富文本编辑器就完美实现啦!如果需要其它插件可去官网查询。。。官方地址:http://tinymce.ax-z.cn

    文章来源: segmentfault.com,作者:NSDgrr,版权归原作者所有,如需转载,请联系作者。

    原文链接:segmentfault.com/a/1190000038567428

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值