Vue-html5-editor 编辑器的使用及一些问题解决
近期由于需要對(duì)公司運(yùn)營(yíng)系統(tǒng)進(jìn)行優(yōu)化和升級(jí),而原有后臺(tái)系統(tǒng)所使用的vue-quill-editor編輯器對(duì)粘貼進(jìn)來(lái)的內(nèi)容的行內(nèi)樣式全部進(jìn)行了過(guò)濾,雖然這樣可以防止XSS攻擊,但是卻完全無(wú)法滿足業(yè)務(wù)需要,為此對(duì)編輯器進(jìn)行了更換,采用Vue-html5-editor 這個(gè)編輯器。
這是一個(gè)基于Vue 2.0系列的編輯器(官方地址),還不錯(cuò),但卻存在一些問(wèn)題,以下記錄這些問(wèn)題,并提供解決辦法。
1. 復(fù)制網(wǎng)絡(luò)圖片時(shí)無(wú)法粘貼成功
主要原因是圖片鏈接存在跨域問(wèn)題。運(yùn)營(yíng)人員復(fù)制的內(nèi)容都是基于微信環(huán)境的,微信對(duì)所有的圖片鏈接地址加了crossorigin="anonymous",所以復(fù)制圖片的時(shí)候無(wú)法正常顯示出來(lái)。
解決的辦法是在編輯器的更新事件觸發(fā)時(shí),對(duì)所有的img圖片鏈接中的crossorigin="anonymous"替換為空,代碼如下:
// 更新編輯器內(nèi)容 updateData(){let obj = document.getElementsByClassName("content")[0];let html = obj.innerHTML;let filterHtml = html.replace(/crossorigin="anonymous"/g,"");this.content = filterHtml;// 編輯器封裝后,將內(nèi)容傳出去this.$emit('contentChange',filterHtml); },2. 無(wú)法從已有的圖庫(kù)中選擇圖片
此編輯器插入圖片的方式主要有兩種,一是輸入鏈接插入圖片,二是選擇本地的圖片轉(zhuǎn)成base64后插入圖片。
很顯然,沒(méi)法使用公司已經(jīng)有素材庫(kù)的圖片,為此需要對(duì)該編輯器的源碼做一些修改, 主要修改如下:
1. 將“上傳”改為“選擇”。修改文件 vue-html5-editor.js ,大約在310行的 template$3 變量中;
?
2. 將以前觸發(fā)上傳的事件改為觸發(fā)一個(gè)打開(kāi)選擇圖片的模態(tài)框,以便選擇圖庫(kù)中的圖片。修改文件vue-html5-editor.js ,大約在343行的pick事件中;
pick: function pick() {// 取消觸發(fā)上傳圖片的事件// this.$refs.file.click();// 自定義的觸發(fā)圖片選擇模態(tài)框的事件this.$parent.$parent.openModal();},?以下是圖片選擇的模態(tài)框展示:?
3. 由于從圖庫(kù)中選擇圖片獲取的僅僅是一個(gè)圖片的鏈接地址,最終也是要以圖片的形式插入編輯器中的,而編輯器插入圖片的功能本身是比較OK的,為了省事,決定借用編輯器的插入圖片功能,所以定義了一個(gè)事件,用于接收選擇的圖片地址,然后將圖片的鏈接地址賦給編輯器自帶的插入圖片的輸入鏈接框中,然后點(diǎn)擊“確定”就可以插入圖片了;
?代碼如下:
// 選擇的圖片地址 selectedImageUrl(url){let obj = this.$refs.editor.$children;// imageUrl為編輯器原有的變量obj[0].imageUrl = url; },3. 插入的圖片沒(méi)有做寬度限制
由于圖庫(kù)中有些圖片的尺寸比較大,會(huì)超出編輯器的總寬度,導(dǎo)致排版比較難看,為此在插入新圖片時(shí),需要給圖片加一個(gè)行內(nèi)樣式,即寬度為百分百。
設(shè)置圖片寬度的代碼如下:
// 設(shè)置圖片寬度 setImageWidth(){this.$nextTick(()=>{let list = document.querySelectorAll(".vue-html5-editor .content img");if(list.length){for(let i=0;i<list.length;i++){let img = list[i];img.style.width = "100%";}};}); }?同時(shí)在編輯器插入圖片的事件中調(diào)用上面這個(gè)方法,修改文件vue-html5-editor.js ,大約在 333 行的 insertImageUrl 事件中,代碼如下:
insertImageUrl: function insertImageUrl() {if (!this.imageUrl) {return}this.$parent.execCommand(Command.INSERT_IMAGE, this.imageUrl);// 對(duì)新插入的圖片設(shè)置圖片最大寬度this.$parent.$parent.setImageWidth();this.imageUrl = null; },4. 給圖片加超鏈接
由于在富文本里是有很多圖片是要加超鏈接的,這個(gè)編輯器提供的加超鏈接是真心不好用,需要用鼠標(biāo)選中文本或是圖片才能加超鏈接,運(yùn)營(yíng)人員反映相當(dāng)麻煩,而且加了鏈接也看不到是否加成功了的標(biāo)識(shí)。
實(shí)現(xiàn)思路如下:
1. 在編輯器的內(nèi)容更新時(shí),給富文本中所有的圖片加上一個(gè)data-index,并同時(shí)加上點(diǎn)擊事件。當(dāng)點(diǎn)擊當(dāng)前圖片時(shí),獲取當(dāng)前圖片的HTML、自定義的data-index,同時(shí)獲取當(dāng)前圖片的父元素,如果當(dāng)前圖片的父元素是已經(jīng)加了鏈接的A標(biāo)簽,則獲取A標(biāo)簽的鏈接地址以方便修改;
// 給圖片添加事件 addImgEvent(){let imgs = document.querySelectorAll(".vue-html5-editor img");for(let i=0;i<imgs.length;i++){let img = imgs[i];img.style.cursor="pointer";img.setAttribute("data-index",i);img.onclick = (e)=>{// 顯示加鏈接的對(duì)話框this.showImgLinkModal = true;// 區(qū)取當(dāng)前圖片的HTMLthis.imgTarget = e.target.outerHTML;// 獲取當(dāng)前圖片自定義的indexthis.imgIndex = e.target.getAttribute("data-index");// 獲取當(dāng)前元素的父元素let parent = e.target.parentElement;// 如果圖片的父元素是已經(jīng)加了鏈接的A標(biāo)簽if(parent.tagName=='A'){// 獲取A標(biāo)簽的鏈接地址,方便修改鏈接地址this.imgLink = parent.getAttribute("href");}}} },2. 確認(rèn)添加圖片鏈接時(shí),根據(jù)當(dāng)前圖片是否已經(jīng)添加了鏈接來(lái)做不同的處理。如果沒(méi)有加鏈接就加上;如果已經(jīng)加了鏈接,就更新鏈接地址;
// HTML轉(zhuǎn)換為DOM結(jié)點(diǎn) parseElement(htmlString){return new DOMParser().parseFromString(htmlString,'text/html').body.childNodes[0]; },// 確認(rèn)添加圖片鏈接 confirmAddLink(){// 加了鏈接的標(biāo)識(shí)符let span = '<span id="linkMark" style="width: 26px;height: 26px;display: block;position: absolute;top: 5px;right: 5px;background: url(data:image/png;base64,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) no-repeat center;background-size: contain; "></span>';// 當(dāng)前圖片let img = this.imgTarget;// 圖片添加鏈接后的HTMLlet a = '<a style="position:relative;display:block" href="'+this.imgLink+'">'+span+img+'</a>';// 將HTML轉(zhuǎn)換為節(jié)點(diǎn)類型let spanNode = this.parseElement(span);let aNode = this.parseElement(a);// 獲取當(dāng)前圖片let index = this.imgIndex;let imgs = document.querySelectorAll(".vue-html5-editor img");let current = imgs[index];let children = current.parentNode.children;// 如果當(dāng)前圖片父元素不是A標(biāo)簽if(current.parentNode.tagName!='A'){for(let i=0;i<children.length;i++){let item = children[i];// 如果子節(jié)點(diǎn)中的某一個(gè)節(jié)點(diǎn)等于當(dāng)前圖片對(duì)象if(item.isEqualNode(current)){// 將加了鏈接的圖片添加到當(dāng)前節(jié)點(diǎn)下一個(gè)節(jié)點(diǎn)之前current.parentNode.insertBefore(aNode, item.nextSibling);// 移除沒(méi)有加鏈接的圖片current.parentNode.removeChild(item);break;}};}else{let link = this.imgLink;// 重新給當(dāng)前圖片的父元素A標(biāo)簽設(shè)置可能更改的鏈接current.parentNode.setAttribute("href",link);// 給富文本中的圖片本身存在鏈接設(shè)置樣式,防置鏈接是原有的current.parentNode.setAttribute("style","position:relative;display:block");let hasLinkMark=false;// 判斷是否有鏈接標(biāo)識(shí)for(let i=0;i<children.length;i++){let item = children[i];if(item!=current ){if(item.tagName=='SPAN' && item.id=="linkMark"){hasLinkMark=true;}else{current.parentNode.removeChild(item); }}};// 如果沒(méi)有鏈接標(biāo)識(shí)if(!hasLinkMark){// 添加一個(gè)鏈接標(biāo)識(shí)current.parentNode.insertBefore(spanNode,children[0]);}};// 關(guān)閉添加鏈接的模態(tài)框this.closeImgLinkModal();// 更新圖片事件this.addImgEvent();this.$nextTick(()=>{let result = document.querySelectorAll(".content")[0].innerHTML;this.data.content = result;});},3. 關(guān)閉圖片添加鏈接的模態(tài)框;
// 關(guān)閉插入圖片鏈接模態(tài)框 closeImgLinkModal(){this.showImgLinkModal = false;this.imgTarget = null;this.imgIndex = null;this.imgLink = ""; },以下是加了鏈接的效果:
5. 代碼實(shí)現(xiàn)
以下是封裝好的編輯器文件代碼。
<template><div><vue-html5-editor ref="editor":height="960" :content="content" :auto-height="false" @change="updateData"></vue-html5-editor></div> </template><script> // npm install font-awesome --save import "font-awesome/css/font-awesome.css" export default {name:"editor",props: {// 打開(kāi)圖片選擇框openModal:{type:Function}},data() {return {content:"",}},mounted(){},methods: {// 更新編輯器內(nèi)容updateData(){let obj = document.getElementsByClassName("content")[0];let html = obj.innerHTML;let filterHtml = html.replace(/crossorigin="anonymous"/g,"");this.content = filterHtml;// 編輯器封裝后,將內(nèi)容傳出去this.$emit('contentChange',filterHtml);},// 選擇的圖片地址selectedImageUrl(url){let obj = this.$refs.editor.$children;// imageUrl為編輯器原有的變量obj[0].imageUrl = url;},// 設(shè)置圖片寬度setImageWidth(){this.$nextTick(()=>{let list = document.querySelectorAll(".vue-html5-editor .content img");if(list.length){for(let i=0;i<list.length;i++){let img = list[i];img.style.width = "100%";}};});}}, } </script>以下是調(diào)用編輯器的文件代碼,相關(guān)無(wú)用代碼已經(jīng)做了清除,可根據(jù)需要自行添加。
<template><div><!-- 調(diào)用編輯器 --><div class="editor-box"><my-editor ref="myEditor" @contentChange="contentChange" :openModal="openModal"></my-editor></div><!-- 圖片素材庫(kù)--><el-dialog title="選擇圖片" :visible.sync="showSelectImgModal" @close="closeModal" width="960px"><div class="img-modal"><div class="image-list"><el-uploadname="img"class="avatar-uploader"style="width:100px;height:100px;":multiple="false":headers="headers":action="uploadUrl":data="uploadData":show-file-list="false":on-success="onUploadSuccess":before-upload="onUploadBefore"accept=".jpg,.jpeg,.png,.gif,.bmp,.JPG,.JPEG,.PBG,.GIF,.BMP"><i class="el-icon-plus avatar-uploader-icon"></i></el-upload><div class="image-item" v-for="item in imageList" :key="item.id" @click="selectImage(item.path)"><el-image fit="cover" :src="item.path"></el-image></div></div></div> </el-dialog><!-- 插入鏈接--><el-dialog title="插入鏈接" :visible.sync="showImgLinkModal" @close="closeImgLinkModal" width="800px"><div style="display:flex;"><el-input placeholder="請(qǐng)輸入圖片鏈接地址" v-model="imgLink"></el-input><el-button type="primary" style="margin-left:10px;" @click="confirmAddLink">確定</el-button></div></el-dialog></div></template><script> // 引入封裝后的編輯器組件 import editor from './components/editor'; // 引入獲取Token的方法 import { getToken } from '@/utils/auth';export default {name: "myEditor",components:{'myEditor':editor},data() {return {// 編輯器的內(nèi)容content:"",// 打開(kāi)顯示圖庫(kù)showSelectImgModal:false,// 圖庫(kù)圖片列表imageList:[],// 上傳圖片地址(模擬)uploadUrl:"http://www.upload.com",// 上傳圖片驗(yàn)證headers: {authorization: getToken()},// 上傳附加參數(shù)uploadData:{},// 添加鏈接showImgLinkModal:false,// 當(dāng)前圖片imgTarget:null,// 圖片下標(biāo)imgIndex:null,// 圖片鏈接imgLink:"",};},created(){// 獲取圖片素材庫(kù)this.getImage();},mounted(){},methods: {// 內(nèi)容更新時(shí)contentChange(result){this.content = result;this.$nextTick(()=>{// 內(nèi)容更新時(shí)給圖片加事件this.addImgEvent();});},// 打開(kāi)選擇圖片openModal(){this.showSelectImgModal = true;},// 獲取微信圖片getImage(){// 獲取圖庫(kù)的接口中地址(模擬)let url = "getWechatImage";this.$http.get(url).then((result) => {if (result.code == 10000) {this.imageList = result.data;}});},// 上傳以前onUploadBefore(file){const size = file.size / 1024 / 1024;if (size>10){this.$message.error('圖片大小不能超過(guò)10MB');return false}},// 上傳成功后onUploadSuccess(res){if(res.code==10000){// 重新獲取圖片庫(kù)的圖片this.getImage();}},// 選擇圖庫(kù)圖片selectImage(url){this.$refs.myEditor.selectedImageUrl(url);this.closeModal();},// 關(guān)閉選擇圖片closeModal(){this.showSelectImgModal = false;},// 給圖片添加事件addImgEvent(){let imgs = document.querySelectorAll(".vue-html5-editor img");for(let i=0;i<imgs.length;i++){let img = imgs[i];img.style.cursor="pointer";img.setAttribute("data-index",i);img.onclick = (e)=>{// 顯示加鏈接的對(duì)話框this.showImgLinkModal = true;// 區(qū)取當(dāng)前圖片的HTMLthis.imgTarget = e.target.outerHTML;// 獲取當(dāng)前圖片自定義的indexthis.imgIndex = e.target.getAttribute("data-index");// 獲取當(dāng)前元素的父元素let parent = e.target.parentElement;// 如果圖片的父元素是已經(jīng)加了鏈接的A標(biāo)簽if(parent.tagName=='A'){// 獲取A標(biāo)簽的鏈接地址,方便修改鏈接地址this.imgLink = parent.getAttribute("href");}}}},// 關(guān)閉插入圖片鏈接模態(tài)框closeImgLinkModal(){this.showImgLinkModal = false;this.imgTarget = null;this.imgIndex = null;this.imgLink = "";},// HTML轉(zhuǎn)換為DOM結(jié)點(diǎn)parseElement(htmlString){return new DOMParser().parseFromString(htmlString,'text/html').body.childNodes[0];},// 確認(rèn)添加圖片鏈接confirmAddLink(){// 加了鏈接的標(biāo)識(shí)符let span = '<span id="linkMark" style="width: 26px;height: 26px;display: block;position: absolute;top: 5px;right: 5px;background: url(data:image/png;base64,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) no-repeat center;background-size: contain; "></span>';// 當(dāng)前圖片let img = this.imgTarget;// 圖片添加鏈接后的HTMLlet a = '<a style="position:relative;display:block" href="'+this.imgLink+'">'+span+img+'</a>';// 將HTML轉(zhuǎn)換為節(jié)點(diǎn)類型let spanNode = this.parseElement(span);let aNode = this.parseElement(a);// 獲取當(dāng)前圖片let index = this.imgIndex;let imgs = document.querySelectorAll(".vue-html5-editor img");let current = imgs[index];let children = current.parentNode.children;// 如果當(dāng)前圖片父元素不是A標(biāo)簽if(current.parentNode.tagName!='A'){for(let i=0;i<children.length;i++){let item = children[i];// 如果子節(jié)點(diǎn)中的某一個(gè)節(jié)點(diǎn)等于當(dāng)前圖片對(duì)象if(item.isEqualNode(current)){// 將加了鏈接的圖片添加到當(dāng)前節(jié)點(diǎn)下一個(gè)節(jié)點(diǎn)之前current.parentNode.insertBefore(aNode, item.nextSibling);// 移除沒(méi)有加鏈接的圖片current.parentNode.removeChild(item);break;}};}else{let link = this.imgLink;// 重新給當(dāng)前圖片的父元素A標(biāo)簽設(shè)置可能更改的鏈接current.parentNode.setAttribute("href",link);// 給富文本中的圖片本身存在鏈接設(shè)置樣式,防置鏈接是原有的current.parentNode.setAttribute("style","position:relative;display:block");let hasLinkMark=false;// 判斷是否有鏈接標(biāo)識(shí)for(let i=0;i<children.length;i++){let item = children[i];if(item!=current ){if(item.tagName=='SPAN' && item.id=="linkMark"){hasLinkMark=true;}else{current.parentNode.removeChild(item); }}};// 如果沒(méi)有鏈接標(biāo)識(shí)if(!hasLinkMark){// 添加一個(gè)鏈接標(biāo)識(shí)current.parentNode.insertBefore(spanNode,children[0]);}};// 關(guān)閉添加鏈接的模態(tài)框this.closeImgLinkModal();// 更新圖片事件this.addImgEvent();this.$nextTick(()=>{let result = document.querySelectorAll(".content")[0].innerHTML;this.data.content = result;});}}, }; </script><style lang="scss" scoped>.editor-box{width:718px;height:1000px;overflow:hidden; }.img-modal{width:100%;height:600px;overflow-y: auto;.image-list{width:100%;display: flex;flex-direction: row;justify-content: flex-start;flex-wrap: wrap;align-items: flex-start;.image-item{height:100px;width:100px;overflow: hidden;display: flex;flex-direction:column;justify-content:space-around;align-items:center;.el-image{width:100%;height:100%;cursor: pointer;}}} }</style>以下是上面代碼中獲取Token的文件代碼:
// npm inatall js-cookie --save import Cookies from 'js-cookie'const TokenKey = 'Admin-Token'export function getToken() {return Cookies.get(TokenKey) }export function setToken(token) {return Cookies.set(TokenKey, token) }export function removeToken() {return Cookies.remove(TokenKey) }?如果上面的文件作為編輯素材時(shí),可以用下面的代碼對(duì)編輯器進(jìn)行初始賦值。
this.$refs.myEditor.content = "要賦值的富文本"; // 設(shè)置內(nèi)容中圖片的寬度 this.$refs.myEditor.setImageWidth();最后是在main.js中集成編輯器的代碼。
// npm install vue-html5-editor --save import VueHtml5Editor from 'vue-html5-editor' var options = {// 全局組件名稱,使用new VueHtml5Editor(options)時(shí)該選項(xiàng)無(wú)效 name: "vue-html5-editor",// 是否顯示模塊名稱,開(kāi)啟的話會(huì)在工具欄的圖標(biāo)后臺(tái)直接顯示名稱showModuleName: false,// 自定義各個(gè)圖標(biāo)的class,默認(rèn)使用的是font-awesome提供的圖標(biāo)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",info: "fa fa-info",},// 配置圖片模塊image: {// 文件最大體積,單位字節(jié) max file sizesizeLimit: 512 * 1024,// 上傳參數(shù),默認(rèn)把圖片轉(zhuǎn)為base64而不上傳upload: {url: null,headers: {},params: {},fieldName: {}},// 壓縮參數(shù),默認(rèn)使用localResizeIMG進(jìn)行壓縮,設(shè)置為null禁止壓縮compress: {width: 1600,height: 1600,quality: 80},// 響應(yīng)數(shù)據(jù)處理,最終返回圖片鏈接uploadHandler(responseText){var json = JSON.parse(responseText)if (!json.ok) {alert(json.msg)} else {return json.data}}},// 語(yǔ)言,內(nèi)建的有英文(en-us)和中文(zh-cn)language: "zh-cn",// 自定義語(yǔ)言i18n: {"zh-cn": {"align": "對(duì)齊方式","image": "圖片","list": "列表","link": "鏈接","unlink": "去除鏈接","table": "表格","font": "文字","text": "排版","eraser": "格式清除","info": "關(guān)于","color": "顏色","please enter a url": "請(qǐng)輸入地址","create link": "創(chuàng)建鏈接","bold": "加粗","italic": "傾斜","underline": "下劃線","strike through": "刪除線","subscript": "上標(biāo)","superscript": "下標(biāo)","heading": "標(biāo)題","font name": "字體","font size": "文字大小","left justify": "左對(duì)齊","center justify": "居中","right justify": "右對(duì)齊","ordered list": "有序列表","unordered list": "無(wú)序列表","fore color": "前景色","background color": "背景色","row count": "行數(shù)","column count": "列數(shù)","save": "確定","upload": "上傳","progress": "進(jìn)度","unknown": "未知","please wait": "請(qǐng)稍等","error": "錯(cuò)誤","abort": "中斷","reset": "重置"}},// 隱藏不想要顯示出來(lái)的模塊hiddenModules: [],// 自定義要顯示的模塊,并控制順序visibleModules: ["text","color","font","align","list","link","unlink","tabulation","image","hr","eraser","undo",],// 擴(kuò)展模塊,具體可以參考examples或查看源碼modules: {} };Vue.use(VueHtml5Editor,options);總結(jié)
以上是生活随笔為你收集整理的Vue-html5-editor 编辑器的使用及一些问题解决的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。
- 上一篇: 为什么要升级PLM系统
- 下一篇: U盘启动的WinPe安装winxp(非g