vue 在移动端的富文本 vue-html5-editor 实现

一、vue-html5-editor

在安装好脚手架的依赖后,要执行 npm install vue-html5-editor --save-dev 来安装这个富文本插件,由于这个富文本插件的图标是依赖font-awesome.css的,所以要npm install font-awesome.css 安装这个css然后在main.js中引入这个css   import   "font-awesome/css/font-awesome.css",也可以引入 font-awesome.min.css 哦。

1. 使用vue cli创建项目: vue init  webpack 项目名称

2. 安装 vue-html5-editor : npm install vue-html5-editor --save-dev

3. 在main.js中把VueHtml5Editor注册成为全局组件 ==>> 代码比较多,可以创建一个单独的工具组件,参考:https://blog.csdn.net/qq_25324335/article/details/79161134  和 https://blog.csdn.net/Dora_5537/article/details/88316056,当然,也可以作为一个局部组件使用

import VueHtml5Editor from 'vue-html5-editor'
Vue.use(VueHtml5Editor, {
  // 全局组件名称,使用new VueHtml5Editor(options)时该选项无效 
  // global component name
  name: "vue-html5-editor",
  // 是否显示模块名称,开启的话会在工具栏的图标后台直接显示名称
  // if set true,will append module name to toolbar after icon
  showModuleName: false,
  // 自定义各个图标的class,默认使用的是font-awesome提供的图标
  // custom icon class of built-in modules,default using font-awesome
  icons: {
      text: "fa fa-pencil",
      color: "fa fa-paint-brush",
      font: "fa fa-font",
      align: "fa fa-align-justify",
      list: "fa fa-list",
      link: "fa fa-chain",
      unlink: "fa fa-chain-broken",
      tabulation: "fa fa-table",
      image: "fa fa-file-image-o",
      hr: "fa fa-minus",
      eraser: "fa fa-eraser",
      undo: "fa-undo fa",
      "full-screen": "fa fa-arrows-alt",
      info: "fa fa-info",
  },
  // 配置图片模块
  // config image module
  image: {
      // 文件最大体积,单位字节  max file size
      sizeLimit: 512 * 1024,
      // 上传参数,默认把图片转为base64而不上传
      // upload config,default null and convert image to base64
      upload: {
          url: null,
          headers: {},
          params: {},
          fieldName: {}
      },
      // 压缩参数,默认使用localResizeIMG进行压缩,设置为null禁止压缩
      // compression config,default resize image by localResizeIMG (https://github.com/think2011/localResizeIMG)
      // set null to disable compression
      compress: {
          width: 1600,
          height: 1600,
          quality: 80
      },
      // 响应数据处理,最终返回图片链接
      // handle response data,return image url
      uploadHandler(responseText){
          //default accept json data like  {ok:false,msg:"unexpected"} or {ok:true,data:"image url"}
          var json = JSON.parse(responseText)
          if (!json.ok) {
              alert(json.msg)
          } else {
              return json.data
          }
      }
  },
  // 语言,内建的有英文(en-us)和中文(zh-cn)
  //default en-us, en-us and zh-cn are built-in
  language: "zh-cn",
  // 自定义语言
  i18n: {
      //specify your language here
      "zh-cn": {
          "align": "对齐方式",
          "image": "图片",
          "list": "列表",
          "link": "链接",
          "unlink": "去除链接",
          "table": "表格",
          "font": "文字",
          "full screen": "全屏",
          "text": "排版",
          "eraser": "格式清除",
          "info": "关于",
          "color": "颜色",
          "please enter a url": "请输入地址",
          "create link": "创建链接",
          "bold": "加粗",
          "italic": "倾斜",
          "underline": "下划线",
          "strike through": "删除线",
          "subscript": "上标",
          "superscript": "下标",
          "heading": "标题",
          "font name": "字体",
          "font size": "文字大小",
          "left justify": "左对齐",
          "center justify": "居中",
          "right justify": "右对齐",
          "ordered list": "有序列表",
          "unordered list": "无序列表",
          "fore color": "前景色",
          "background color": "背景色",
          "row count": "行数",
          "column count": "列数",
          "save": "确定",
          "upload": "上传",
          "progress": "进度",
          "unknown": "未知",
          "please wait": "请稍等",
          "error": "错误",
          "abort": "中断",
          "reset": "重置"
      }
  },
  // 隐藏不想要显示出来的模块
  // the modules you don't want
  hiddenModules: [],
  // 自定义要显示的模块,并控制顺序
  // keep only the modules you want and customize the order.
  // can be used with hiddenModules together
  visibleModules: [
      "text",
      "color",
      "font",
      "align",
      "list",
      "link",
      "unlink",
      "tabulation",
      "image",
      "hr",
      "eraser",
      "undo",
      "full-screen",
      "info",
  ],
  // 扩展模块,具体可以参考examples或查看源码
  // extended modules
  modules: {
      //omit,reference to source code of build-in modules
  }
})

4. VueHtml5Editor富文本的icon图标是由font-awesome控制,所以在项目中引入 font-awesome

        4.1 安装: cnpm install font-awesome --save

        4.2 main.js 中引入样式:

                      import 'font-awesome/css/font-awesome.css'  或者 import 'font-awesome/css/font-awesome.min.css'

5. 使用: 

<template>  
    <div class="content">  
        <vue-html5-editor :content="content" :height="400"  @change="updateData"></vue-html5-editor>  
      
    </div>  
</template>  
   
<script>  
    export default {  
        data(){  
          return {content: '测试文章内容'}  
        },  
        methods: {  
          updateData(e = ''){  
            this.content = e;  
            console.info(e);  
          }  
        }  
    }  
</script> 

<style scoped>  
      
</style> 

6. 效果

7. 常见配置修改

        7.1 自定义工具类,不想要显示这么多的工具,则只要修改配置visibleModules即可(main.js里面)

        

        7.2 工具类的样式修改 ==>> 在移动端我们通常希望工具栏可以固定不动,并且显示在页面最下方,这时候我们就需要去修改她的源码了    node_modules / vue-html5-editor / dist / vue-html5-editor.js

        a. 修改 __$styleInject

__$styleInject(".vue-html5-editor,.vue-html5-editor *{box-sizing:border-box}.vue-html5-editor{font-size:14px;line-height:1.5;background-color:#fff;color:#333;border:1px solid #ddd;text-align:left;border-radius:5px;overflow:hidden}.vue-html5-editor.full-screen{position:fixed!important;top:0!important;left:0!important;bottom:0!important;right:0!important;border-radius:0}.vue-html5-editor>.toolbar{position:relative;background-color:inherit}.vue-html5-editor>.toolbar>ul{list-style:none;padding:0;margin:0;border-bottom:1px solid #ddd}.vue-html5-editor>.toolbar>ul>li{display:inline-block;cursor:pointer;text-align:center;line-height:36px;padding:0 10px}.vue-html5-editor>.toolbar>ul>li .icon{height:16px;width:16px;display:inline-block;vertical-align:middle}.vue-html5-editor>.toolbar>.dashboard{background-color:inherit;border-bottom:1px solid #ddd;padding:10px;position:absolute;top:100%;left:0;right:0;overflow:auto}.vue-html5-editor>.toolbar>.dashboard input[type=text],.vue-html5-editor>.toolbar>.dashboard input[type=number],.vue-html5-editor>.toolbar>.dashboard select{padding:6px 12px;color:inherit;background-color:transparent;border:1px solid #ddd;border-radius:5px}.vue-html5-editor>.toolbar>.dashboard input[type=text]:hover,.vue-html5-editor>.toolbar>.dashboard input[type=number]:hover,.vue-html5-editor>.toolbar>.dashboard select:hover{border-color:#bebebe}.vue-html5-editor>.toolbar>.dashboard input[type=text][disabled],.vue-html5-editor>.toolbar>.dashboard input[type=text][readonly],.vue-html5-editor>.toolbar>.dashboard input[type=number][disabled],.vue-html5-editor>.toolbar>.dashboard input[type=number][readonly],.vue-html5-editor>.toolbar>.dashboard select[disabled],.vue-html5-editor>.toolbar>.dashboard select[readonly]{background-color:#eee;opacity:1}.vue-html5-editor>.toolbar>.dashboard input[type=text][disabled],.vue-html5-editor>.toolbar>.dashboard input[type=number][disabled],.vue-html5-editor>.toolbar>.dashboard select[disabled]{cursor:not-allowed}.vue-html5-editor>.toolbar>.dashboard button{color:inherit;background-color:inherit;padding:6px 12px;white-space:nowrap;vertical-align:middle;cursor:pointer;-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none;border:1px solid #ddd;border-radius:5px;margin-right:4px;margin-bottom:4px}.vue-html5-editor>.toolbar>.dashboard button:hover{border-color:#bebebe}.vue-html5-editor>.toolbar>.dashboard button[disabled]{cursor:not-allowed;opacity:.68}.vue-html5-editor>.toolbar>.dashboard button:last-child{margin-right:0}.vue-html5-editor>.toolbar>.dashboard label{font-weight:bolder}.vue-html5-editor>.content{overflow:auto;padding:10px}.vue-html5-editor>.content:focus{outline:0}",undefined);

        改为:

__$styleInject(
    `
    .vue-html5-editor, .vue-html5-editor * {
      box-sizing: border-box
    }
    .vue-html5-editor {
      font-size: 14px;
      line-height: 1.5;
      background-color: #fff;
      color: #333;
      border: 1px solid #ddd;
      text-align: left;
      border-radius: 5px;
      overflow: hidden
    }
    .vue-html5-editor.full-screen {
      position: fixed !important;
      top: 0 !important;
      left: 0 !important;
      bottom: 0 !important;
      right: 0 !important;
      border-radius: 0
    }
    .vue-html5-editor > .toolbar {
      position: relative;
      background-color: inherit;
      border-top:1px solid #ccc
    }
    .vue-html5-editor > .toolbar > ul {
      list-style: none;
      padding: 0;
      margin: 0;
      border-bottom: 1px solid #ddd
    }
    .vue-html5-editor > .toolbar > ul > li {
      display: inline-block;
      cursor: pointer;
      text-align: center;
      line-height: 36px;
      padding: 0 10px
    }
    .vue-html5-editor > .toolbar > ul > li .icon {
      height: 16px;
      width: 16px;
      display: inline-block;
      vertical-align: middle
    }
    .vue-html5-editor > .toolbar > .dashboard {
      background-color: inherit;
      border-top: 1px solid #ddd;
      padding: 10px;
      position: absolute;
      bottom: 100%;
      left: 0;
      right: 0;
      overflow: auto
    }
    .vue-html5-editor > .toolbar > .dashboard input[type=text], .vue-html5-editor > .toolbar > .dashboard input[type=number], .vue-html5-editor > .toolbar > .dashboard select {
      padding: 6px 12px;
      color: inherit;
      background-color: transparent;
      border: 1px solid #ddd;
      border-radius: 5px
    }
    .vue-html5-editor > .toolbar > .dashboard input[type=text]:hover, .vue-html5-editor > .toolbar > .dashboard input[type=number]:hover, .vue-html5-editor > .toolbar > .dashboard select:hover {
      border-color: #bebebe
    }
    .vue-html5-editor > .toolbar > .dashboard input[type=text][disabled], .vue-html5-editor > .toolbar > .dashboard input[type=text][readonly], .vue-html5-editor > .toolbar > .dashboard input[type=number][disabled], .vue-html5-editor > .toolbar > .dashboard input[type=number][readonly], .vue-html5-editor > .toolbar > .dashboard select[disabled], .vue-html5-editor > .toolbar > .dashboard select[readonly] {
      background-color: #eee;
      opacity: 1
    }
    .vue-html5-editor > .toolbar > .dashboard input[type=text][disabled], .vue-html5-editor > .toolbar > .dashboard input[type=number][disabled], .vue-html5-editor > .toolbar > .dashboard select[disabled] {
      cursor: not-allowed
    }
    .vue-html5-editor > .toolbar > .dashboard button {
      color: inherit;
      background-color: inherit;
      padding: 6px 12px;
      white-space: nowrap;
      vertical-align: middle;
      cursor: pointer;
      -webkit-user-select: none;
      -moz-user-select: none;
      -ms-user-select: none;
      user-select: none;
      border: 1px solid #ddd;
      border-radius: 5px;
      margin-right: 4px;
      margin-bottom: 4px
    }
    .vue-html5-editor > .toolbar > .dashboard button:hover {
      border-color: #bebebe
    }
    .vue-html5-editor > .toolbar > .dashboard button[disabled] {
      cursor: not-allowed;
      opacity: .68
    }
    .vue-html5-editor > .toolbar > .dashboard button:last-child {
      margin-right: 0
    }
    .vue-html5-editor > .toolbar > .dashboard label {
      font-weight: bolder
    }
    .vue-html5-editor > .content {
      overflow: scroll;
      padding: 10px;
      max-height:500px
    }
    .vue-html5-editor > .content:focus {
      outline: 0
    }`
)

        b. 修改 template$9

var template$9 = "<div class=\"vue-html5-editor\" :class=\"{'full-screen':fullScreen}\" :style=\"{'z-index':zIndex}\"> <div class=\"toolbar\" :style=\"{'z-index':zIndex+1}\" ref=\"toolbar\"> <ul> <template v-for=\"module in modules\"> <li :title=\"locale[module.i18n]\" @click=\"activeModule(module)\"> <span class=\"icon\" :class=\"module.icon\"></span> <template v-if=\"showModuleName === undefined ? defaultShowModuleName : showModuleName\"> &nbsp;{{locale[module.i18n]}} </template> </li> </template> </ul> <div class=\"dashboard\" v-show=\"dashboard\" ref=\"dashboard\"> <keep-alive> <div v-show=\"dashboard\" :is=\"dashboard\"></div> </keep-alive> </div> </div> <div class=\"content\" ref=\"content\" :style=\"contentStyle\" contenteditable @click=\"toggleDashboard(dashboard)\"> </div> </div>";

        改为:

var  template$9=`  
     <div class="vue-html5-editor" :class="{'full-screen':fullScreen}" :style="{'z-index':zIndex}">  
           
         <div class="content" ref="content" :style="contentStyle" contenteditable  
              @click="toggleDashboard(dashboard)"></div>  
                
         <div class="toolbar" :style="{'z-index':zIndex+1}" ref="toolbar">  
           <ul>  
             <template v-for="module in modules">  
               <li :title="locale[module.i18n]" @click="activeModule(module)"><span class="icon"  
                                                                                    :class="module.icon"></span>  
                 <template v-if="showModuleName === undefined ? defaultShowModuleName : showModuleName">  
                    {{locale[module.i18n]}}   
                 </template>  
               </li>  
             </template>  
           </ul>  
           <div class="dashboard" v-show="dashboard" ref="dashboard">  
             <keep-alive>  
               <div v-show="dashboard" :is="dashboard"></div>  
             </keep-alive>  
           </div>  
         </div>  
           
       </div>  
     `

        7.3  vue-html5-editor默认是将图片转换为base64进行上传,但如果需要上传图片到服务器,然后进行处理,修改如下:

        a. 修改图片上传到服务器并配置图片上传地址

        b. 修改上传成功后的处理(可能需要=>根据自己后台返回结果修改)

        c. 修改请求时formData的数据结果(可能需要=>根据自己后台提交的接口参数修改)

 

8  使用时图片的处理,在移动端上,如果图片过大,会超出屏幕,这样会有点不好,所以在使用时内容change事件时需要处理一下

updateData(e = ''){  
    this.content = e;  
    console.info(e);  
    let c1 = e.replace(/<img width="100%"/g, '<img');  
    let c2 = c1.replace(/<img/g, '<img width="100%"');  
    this.content = c2; 
} 

 

参考博客:https://blog.csdn.net/qq_25324335/article/details/79161134

 

二、eleditor  

        本来想看一下eleditor这个插件的,但是它设置颜色是设置的背景颜色,如下图:

        

        不想去改它的源码,所以放弃了。

 

文章仅为本人学习过程的一个记录,仅供参考,如有问题,欢迎指出!

对博客文章的参考,若原文章博主介意,请联系删除!请原谅

  • 4
    点赞
  • 20
    收藏
    觉得还不错? 一键收藏
  • 4
    评论
评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值