React中使用Vditor自定義圖片詳解
阿新 • • 發佈:2020-12-28
安裝
npm install vditor -s
引用
匯入依賴包
import Vditor from "vditor";
匯入樣式
import "vditor/src/assets/scss/index.scss";
使用示例
export default class Vditor extends Component { constructor(props) { super(props); this.state = { editValue: "" }; } componentDidMount = () => { //元件掛載完成之後呼叫 注意一定要在元件掛載完成之後呼叫 否則會找不到注入的DOM this.createVidtor({ value: this.state.editValue }); } //建立編輯器 下面會詳解 createVidtor = params => { let { value } = params; value = value ? value : " "; let that = this; const vditor = new Vditor("vditor",{ height: 800,mode: "ir",//及時渲染模式 placeholder: "React Vditor",toolbar: [ "emoji","headings","bold","italic","strike","link","|","list","ordered-list","check","outdent","indent","quote","line","code","inline-code","insert-before","insert-after","upload","table","undo","redo","fullscreen","edit-mode",{ name: "more",toolbar: [ "both","code-theme","content-theme","export","outline","preview","devtools","info","help" ] },{ hotkey: "⌘-S",name: "save",tipPosition: "s",tip: "儲存",className: "right",icon: `<img style="height: 16px" src='https://img.58cdn.com.cn/escstatic/docs/imgUpload/idocs/save.svg'/>`,click() { that.saveDoc(); } },{ hotkey: "",name: "publish",tip: "釋出文章",icon: `<img style="height: 16px" src='https://img.58cdn.com.cn/escstatic/docs/imgUpload/idocs/publish.svg'/>`,click() { that.publishDoc(); } } ],after() { vditor.setValue(value); },blur() { that.saveDoc(); },upload: { accept: "image/*",multiple: false,filename(name) { return name .replace(/[^(a-zA-Z0-9\u4e00-\u9fa5\.)]/g,"") .replace(/[\?\\/:|<>\*\[\]\(\)\$%\{\}@~]/g,"") .replace("/\\s/g",""); },handler(files) { function callback(path) { let name = files[0] && files[0].name; let succFileText = ""; if (vditor && vditor.vditor.currentMode === "wysiwyg") { succFileText += `\n <img alt=${name} src="${path}">`; } else { succFileText += ` \n![${name}](${path})`; } document.execCommand("insertHTML",false,succFileText); } that.handleImageUpload(files,callback); },url(files) { that.handleImageUpload(files); } } }); this.vditor = vditor; return vditor; }; //首先需要在render裡面注入DOM,可自定義注入DOM的ID,初始化編輯器的時候使用自定義的ID即可 render() { <div className="editorWrap"> <div id="vditor" /> </div> } }
示例:
功能使用
新建物件
const vditor = new Vditor("vditor",...option);
新建物件時第一個引數ID,要對應上再render裡面注入的ID
option引數
tip:只列舉一下常用引數,其他的引數請參照 官方API
引數 | 說明 |
---|---|
height | 配置編輯器高度 |
mode | 編輯器模式 wysiwyg:所見即所得2 ir:及時渲染 sv:分屏模式 |
placeholder | 佔位符 |
toolbar | 工具欄 |
Tip:如果要自定義工具欄的話,一定要加上預設的工具欄,不然只展示自定義的了
預設工具欄
tip:此為原始碼裡面copy 不用更改可直接使用,官方已定義好了快捷鍵和功能
toolbar: [ "emoji","record",{ name: "more",toolbar: [ "both","help",],}]
對應工具欄展示:
自定義按鈕
let that = this; const vditor = new Vditor("vditor",{ toolbar: [ { hotkey: "⌘-S",click() { that.saveDoc(); } },{ hotkey: "",click() { that.publishDoc(); } } ] }); //tip:在呼叫本類封裝的方法時提前把this賦值給其他方法內的變數,在Vditor內部改變了this指向
引數 | 說明 |
---|---|
hotkey | 熱鍵配置 |
name | 功能區分(唯一性) |
tip | 懸浮提示 |
className | UI展示 right靠右 |
icon | 按鈕圖示 |
click | 點選事件 |
示例:
獲取值
saveDoc = () => { //在初始化時已經把vditor賦值到this物件上 可直接通過getValue方法獲取當前編輯器的值 let mdValue = this.vditor && this.vditor.getValue(); //獲取完值業務儲存就行 這裡不再詳細寫本人的儲存方法了 ... }
賦值
let { value } = params; value = value ? value : " "; //如果是空值的話 最好給一個空格 以免編輯器初始化時報錯 const vditor = new Vditor("vditor",{ // value: value,after() { vditor.setValue(value); } }); //tip:雖說官方也提供value直接賦值 但是在React裡面不生效,就需要在after裡面去呼叫setValue來完成賦值
自定義圖片上傳
const vditor = new Vditor("vditor",{ upload: { accept: "image/*",filename(name) { return name .replace(/[^(a-zA-Z0-9\u4e00-\u9fa5\.)]/g,"") .replace(/[\?\\/:|<>\*\[\]\(\)\$%\{\}@~]/g,"") .replace("/\\s/g",""); },handler(files) { function callback(path) { let name = files[0] && files[0].name; let succFileText = ""; if (vditor && vditor.vditor.currentMode === "wysiwyg") { succFileText += `\n <img alt=${name} src="${path}">`; } else { succFileText += ` \n![${name}](${path})`; } document.execCommand("insertHTML",succFileText); } that.handleImageUpload(files,callback); },url(files,callback) { that.handleImageUpload(files,callback); } } }); //此接口裡面呼叫的是自己的圖片上傳 業務方自行實現 handleImageUpload = (file,callback) => { const reader = new FileReader(); let formdata = new FormData(); formdata.append("files",file[0]); reader.onload = () => { // setTimeout 模擬非同步上傳圖片 // 當非同步上傳獲取圖片地址後,執行callback回撥(引數為imageUrl字串),即可將圖片地址寫入markdown new Promise(resolve => { this.props.dispatch({ type: "docManager/imageUpload",payload: { resolve,username: myInfo.userId,formdata } }); }).then(res => { let imgurl = res.result.path; callback(imgurl); }); }; reader.readAsDataURL(file[0]); };
引數 | 說明 |
---|---|
accept | 接收檔案型別(我這邊只做了圖片上傳) |
multiple | 是否多選 |
filename | 格式化檔名 |
handler | 點選數觸發方法 |
url | 配置此方法時可實現圖片貼上並上傳 |
上傳完成後介面返回的CDN地址
上傳完成後處理
handler(files) { function callback(path) { let name = files[0] && files[0].name; let succFileText = ""; //上傳完成獲取當前編輯器模式 根據不同模式拼接不同的展示標籤 if (vditor && vditor.vditor.currentMode === "wysiwyg") { succFileText += `\n <img alt=${name} src="${path}">`; } else { succFileText += ` \n![${name}](${path})`; } //拼接完直接插入到滑鼠選中位置 document.execCommand("insertHTML",succFileText); } that.handleImageUpload(files,callback); }
總結
以上是本人在接入vditor編輯器是的一些使用總結,更多相關React Vditor內容請搜尋我們以前的文章或繼續瀏覽下面的相關文章希望大家以後多多支援我們!