摘要:前言本文將介紹筆者在的項目中使用百度的富文本編輯器的過程。以百度官網的為例,控制臺輸入為該編輯器注冊點擊事件,當點擊加粗按鈕時,控制臺輸出為了避免點擊工具條時觸發事件,筆者將自定義的事件全部注釋了。
前言
本文將介紹筆者在React的項目中使用百度的富文本編輯器Ueditor的過程。注意本文不提供一條龍式的使用方法,只是將使用過程中的一些實現思路進行總結,供以參考。react項目中導入ueditor,會存在各種不正交的問題,需要注意。
引入首先在ueditor官網下載最新安裝包,然后在項目入口的html中導入(導入方式不一,可以采用import的方式,需要自行度娘。但是無論哪種引入方式,只要想自定義功能,不正交問題就難以避免QAQ)。不管三七二十一先跑起來再說。。
ueditor demo ······
在React項目中使用ueditor要注意
導入的路徑,筆者使用的是項目經webpack打包之后的相對路徑。
導入順序,配置文件要先于源碼。
筆者這種引入方式存在緩存問題,所以修改ueditor.all.js后需要及時清理緩存,測試新的代碼。
封裝/** * 封裝UEditor */ import React from "react"; import "./index.less"; class UEditor extends React.Component { constructor(props) { super(props); this.editor = {}; this.id = ""; } ······ componentDidMount() { let UE = window.UE; let id = this.id; if (id) { try { /* 加載之前先執行刪除操作,否則如果存在頁面切換, 再切回帶編輯器頁面重新加載時不刷新無法渲染出編輯器 */ UE.delEditor(id); } catch (e) {} let ueditor = UE.getEditor(id, { toolbars: [ ["bold", "italic", "underline", "kityformula", "diyimg"] ], initialContent: "", autoHeightEnabled: false, autoFloatEnabled: false, elementPathEnabled: false, wordCount: false, enableAutoSave: false, initialFrameWidth: this.props.width, initialFrameHeight: this.props.height }); } } render() { this.id = this.props.id; return ; } } export default UEditor;
筆者在項目中使用了加粗,斜體,下劃線,插入圖片,公式等功能,想要自定義配置均可參照ueditor.config.js修改。具體的將一一介紹,最后實現效果如下:
問題總結: 1. 禁止自動增高,改用滾動條autoHeightEnabled: false initialFrameWidth:this.props.width initialFrameHeight:this.props.height
autoHeightEnabled可以阻止自動增高,然后再自定義容器寬度和高度。
2. 自定義全局樣式,如容器的padding,p標簽的line-height等解決方法:ueditor.all.js的第6800多行的render方法,在其中可以自定義全局樣式。
3. 導航條切換后,無法再次渲染解決方法:在每次ueditor實例化之前,先刪除對應的id
UE.delEditor(id);
原因分析:
從實例化和卸載實例的源碼來看:
getEditor:
UE.getEditor = function (id, opt) { var editor = instances[id]; if (!editor) { editor = instances[id] = new UE.ui.Editor(opt); editor.render(id);//渲染編輯器 } return editor; };
delEditor:
UE.delEditor = function (id) { var editor; if (editor = instances[id]) { editor.key && editor.destroy(); delete instances[id] } };
UE在全局管理了一個實例池,每次實例化都會根據id檢索,然后生成實例。從getEditor的源碼中可以看出,ueditor的一個實例在第一次初始化時存在一個editor.render(),這是將此id的實例渲染到對應的id容器上。然而,當用戶tab切換編輯器再切回來時,此時由于該實例已在實例池中存在,于是直接執行return editor,所以少了editor.render()這一步,于是不能重新渲染。所以,在Ueditor組件每次實例化之前,先進行delEditor卸載。這里需要注意,從delEditor中可以看出ueditor卸載實例時調用了實例的destroy方法。從destroy的注釋來看:銷毀編輯器實例,使用textarea代替 ,這解釋了為什么在切換編輯器或者卸載編輯器時,會出現編輯器變為textarea的情況,如圖所示:
4. 模擬placeholder實現預置文案解決方法:在UE的實例中自定義方法,實現填充文字模擬placeholder的效果,代碼如下:
//模擬placeholder和控制toolbar顯示隱藏 UE.Editor.prototype.initDiy = function (placeholder) { var _editor = this; //獲取焦點 _editor.addListener("focus", function () { UE.isEditored = true; var Text = `${placeholder}
` var localHtml = _editor.getContent(); if (localHtml === Text) { _editor.setContent("");//點擊時清空 _editor.focus(true); } //使得其他工具條display置為none var list = document.querySelectorAll(".edui-editor-toolbarbox"); list.forEach((ele) => { ele.style.display = "none"; }); var toolbar = findKey(_editor.key); toolbar.style.display = "block"; }); // 插入圖片時存在問題 // _editor.addListener("blur", function () { // var localHtml = _editor.getContent(); // if (localHtml === "") { // _editor.setContent(`${placeholder}
`); // } // // window.activeEditor = _editor.key; // }); _editor.ready(function () { // _editor.fireEvent("blur"); _editor.setContent(`${placeholder}
`);//填充預置文案 }); } //尋找工具條 function findKey(key) { let ele = document.querySelector(`#${key}`); let toolbar = ele.querySelector(".edui-editor-toolbarbox"); return toolbar; }
原來,筆者實現的效果是點擊時清空,失焦時還原。但是,在做自定義工具條時產生了bug(在5中我會細說),因此我采用了另一種方案:初始時設置預設文案,當用戶聚焦時清空預設,用戶失焦后不再恢復該預設文案。也就是將blur事件注釋了。。。
5. 工具條顯示在編輯器頭部,顯示為懸浮效果,默認隱藏,聚焦時出現實現思路:將themes/default/css/ueditor.css中加入:
.edui-default .edui-editor-toolbarbox { position: absolute; ······ top: -36px; }
首先實現頭部偏移,然后通過控制toolbar對應dom元素的display來隱藏工具條。實現效果如下:
下面解釋一下為什么編輯器失焦的時候不恢復預置文案:
從4中的代碼可以看出,我們是通過觸發focus和blur事件分別清空和填充編輯器的內容。但是當我們點擊工具條時,編輯器就會觸發blur事件?。∮谑蔷蜁霈F各種bug。以百度官網的ueditor為例,控制臺輸入:
為該編輯器注冊點擊事件,當點擊加粗按鈕時,控制臺輸出:
為了避免點擊工具條時觸發blur事件,筆者將自定義的blur事件全部注釋了。
6. 自定義按鈕和七牛云圖片上傳首先,在ueditor.config.js中找到toolbars數組,增加一個diyimg字符串,然后在zh-cn.js找到labelMap數組,在末尾加上"diyimg": "插入圖片" 。最后,在ueditor.all.js中找到btnCmds數組,加入diyimg字符串。初始化時使用這個字符串,工具條上就會顯示一個按鈕,但是我們發現他顯示的是這樣的:
這是因為ueditor默認使用加粗的icon作為自定義按鈕的默認icon,所以為了使用默認的插入圖片的圖標,我們需要到themes/default/css/ueditor.css中,在最后一行加入:
/*自定義圖片上傳按鈕 */ .edui-default .edui-toolbar .edui-for-diyimg .edui-icon { background-position: -380px 0px;//這個位置是“插入圖片”的icon,其他圖標可自行調整 }
添加后,顯示效果如下:
圖標正常顯示后,需要為該圖標添加相應的點擊事件,在ueditor.all.js中加入:
//圖片上傳 UE.commands["diyimg"] = { execCommand : function(){ const upload = async(e) => { ······//完成圖片上傳的代碼 } const fileInput = document.getElementById("diyimg");//獲取dom上隱藏的一個input標簽 fileInput.onchange = upload; fileInput.click();//觸發input標簽實現文件上傳 return true; }, queryCommandState:function(){ } };
筆者這里不贅述圖片上傳的代碼,度娘上很多,我簡單說說實現的思路:
先實現一個插入圖片的按鈕,然后為該按鈕注冊相應的事件diyimg,然后在頁面中添加一個input file標簽并隱藏,diyimg事件會觸發該標簽的點擊事件,彈出文件上傳彈窗,此時選擇文件點擊后會觸發onchange事件,執行相應的圖片上傳代碼。上傳成功到服務器后,服務器會返回圖片對應的url,此時拿到該url填入對應編輯器實例,執行編輯器的插入圖片的代碼:
this.execCommand("insertimage", { src: res.data.downloadUrl,//回調傳來的url width:"60" // height:"45" });7. 給在編輯器內部的img等標簽添加內聯樣式
ueditor默認存在xss過濾?。?!這里以給img標簽添加style=“vertical-top”為例。
首先要找到ueditor.config.js,在其中搜索xss,在第403行左右有代碼:
img: [src", "alt", "title", "width", "height", "id", "_src", "loadingclass", "class", "data-latex"],
往數組里加入style字符串,然后在ueditor.all.js中搜索UE.commands["insertimage"] ,在第約11172行找到str,往里面加入內聯樣式即可。
一些吐槽: 1. 在react項目里使用script形式引入,感覺格格不入 2. 為了實現placeholder,各個事件之間存在不正交的現象。諸如點擊按鈕,卻觸發了編輯器的失焦事件 3. 在使用自定義的字數限制功能時,筆者使用ueditor的contentChange去檢測內容字數,但是contentChange事件是定時的,所以計算字數會有問題。
文章版權歸作者所有,未經允許請勿轉載,若此文章存在違規行為,您可以聯系管理員刪除。
轉載請注明本文地址:http://specialneedsforspecialkids.com/yun/108422.html
摘要:前言本文將介紹筆者在的項目中使用百度的富文本編輯器的過程。以百度官網的為例,控制臺輸入為該編輯器注冊點擊事件,當點擊加粗按鈕時,控制臺輸出為了避免點擊工具條時觸發事件,筆者將自定義的事件全部注釋了。 前言 本文將介紹筆者在React的項目中使用百度的富文本編輯器Ueditor的過程。注意本文不提供一條龍式的使用方法,只是將使用過程中的一些實現思路進行總結,供以參考。react項目中導入...
VSCode使ReactVue代碼調試變得更爽 在前段開發中,大家會遇見調試 Vue/React 代碼,現在就給大家總結都有哪幾種: 先找代碼問題,在console.log 打印日志,用 Chrome Devtools 的 debugger 來調試,用 VSCode 的 debugger 來調試?! 】吹绞遣皇遣煌?,不僅效率大大提升就連體驗也是超級幫的,這種體驗讓人超級爽到爆炸?! 『芏?..
這是講 ahooks 源碼的第一篇文章,簡要就是以下幾點: 加深對 React hooks 的理解。 學習如何抽象自定義 hooks。構建屬于自己的 React hooks 工具庫。 培養閱讀學習源碼的習慣,工具庫是一個對源碼閱讀不錯的選擇?! ∽ⅲ罕鞠盗袑?ahooks 的源碼解析是基于v3.3.13。自己 folk 了一份源碼,主要是對源碼做了一些解讀,可見詳情?! 〉谝黄饕榻B a...
在這里為大家介紹,實現多張圖自動輪播可以用react-slick插件,下面一起看看: 一、進入官網查看文檔(Docs) react-slick官網 二、安裝插件(Quick Start) //npm安裝 npminstallreact-slick--save //yarn安裝 yarnaddreact-slick 三、范例使用(Examples) 在examples在擴...
用vite作為項目打包工具,這是為什么?其中最主要的原因是 ——vite在開發環境基于ESM規范實現的Nobundle模式,節省了代碼打包的時間?! ‘斍按虬男枨笕稳挥?,且ESM規范兼容性越來越好,進入生產環境大面積可用的狀態也不是不可能?! ‘斏a環境打包將不再是剛需時?! ×硪环矫?,從HTTP協議的角度看,在HTTP/1.1時代,多個模塊被打包成一個文件能減少瀏覽器并發請求數,達到優化目...
閱讀 2117·2023-04-26 00:41
閱讀 1151·2021-09-24 10:34
閱讀 3578·2021-09-23 11:21
閱讀 4064·2021-09-22 15:06
閱讀 1562·2019-08-30 15:55
閱讀 903·2019-08-30 15:54
閱讀 1833·2019-08-30 15:48
閱讀 555·2019-08-29 13:58