vue-quill-edtior實(shí)現(xiàn)@用戶和視頻插入紀(jì)錄

一活翩、插入視頻

主要是用了blots/block/embed 插入的換行的塊級(jí)元素

import { Quill } from 'vue-quill-editor';
const BlockEmbed = Quill.import('blots/block/embed');
class Video extends BlockEmbed {
  static create(value) {
    let node = super.create()
    node.setAttribute('src', value.url || '')
    node.setAttribute('controls', value.controls || '')
    node.setAttribute('width', value.width || '')
    node.setAttribute('height', value.height || '')
    node.setAttribute('videoCover', value.videoCover || '')
    node.setAttribute('videoTime', value.videoTime || '')
    node.setAttribute('size', value.size || '')
    node.setAttribute('webkit-playsinline', true)
    node.setAttribute('playsinline', true)
    node.setAttribute('x5-playsinline', true)
    node.setAttribute('controlslist', value.controlslist || '')
    return node;
  }
  static value (node) {
    return {
      url: node.getAttribute('src'),
      controls: node.getAttribute('controls'),
      width: node.getAttribute('width'),
      height: node.getAttribute('height'),
      videoCover: node.getAttribute('videoCover'),
      videoTime: node.getAttribute('videoTime'),
      size: node.getAttribute('size'),
      controlslist: node.getAttribute('controlslist'),
    };
  }
}
Video.blotName = 'video'; 
Video.className = 'ql-video';
Video.tagName = 'video'; 
export default Video;

使用方法:

import Video from './video';
Quill.register(Video, true);
// 具體插入視頻的方法
insertEle(url) {
      let quill = this.$refs.myTextEditor.quill;
      let length = quill.selection.savedRange.index;
      quill.insertEmbed(length, 'video', {
        url,
        controls: 'controls',
        width: '100%',
        height: 'auto',
        videoCover: this.videoCover,
        videoTime: this.videoTime,
        size: this.videoSize
      });
      // 調(diào)整光標(biāo)到最后
      quill.setSelection(length + 1);
},

二丧荐、插入@用戶

實(shí)踐過兩種方式缆瓣,但是第一種有很多坑(比如刪除的時(shí)候光標(biāo)會(huì)提前之類的)
第一種也紀(jì)錄一下吧,主要用的是blots/embed

import { Quill } from 'vue-quill-editor';

const Embed = Quill.import('blots/embed');

class EmbedBlot extends Embed {
  static create(value) {
    let node = super.create();
    if(typeof value === "string"){ //編輯回顯處理
      // 匹配到需要的span內(nèi)容  
      const res = value.match(/<span class="atUser" (.*?)>(.*?)<\/span>/g);
      node.innerHTML = res;
      return node;
    }
    EmbedBlot.buildSpan(value, node);
    return node;
  }

  static value(node) {
    return node.innerHTML;
  }

  static buildSpan(value, node) {
    let emojiSpan = document.createElement('span');
    emojiSpan.classList.add(this.emojiClass);
    emojiSpan.innerText = value.text;
    emojiSpan.setAttribute('id', value.id);
    node.appendChild(emojiSpan);
  }
}

EmbedBlot.blotName = 'atTag';
EmbedBlot.emojiClass = 'atUser'
EmbedBlot.tagName = 'span';

export default EmbedBlot;

第二種是最完美的方法虹统,插入一個(gè)行內(nèi)元素:

import { Quill } from 'vue-quill-editor';
const Parchment = Quill.imports.parchment;
class EmbedTag extends Parchment.Embed {
  static create(value) {
    // 正常span標(biāo)簽就直接返回node對(duì)象
    if(value.nodeName==='SPAN'){
      return value;
    }
    const node = super.create(value);
    node.contentEditable = 'false';
    this.contentNode = document.createElement('span');
    this.contentNode.classList.add('atUser');
    this.contentNode.setAttribute("id",value.id)
    this.contentNode.innerText = value.text;
    node.appendChild(this.contentNode);
    return node;
  }
  static value(node) {
    return node;
  }
}
EmbedTag.blotName = "atTag" 
EmbedTag.tagName = "SPAN"
EmbedTag.className = "customTag"; // 這個(gè)一定要加弓坞,不然富文本中其他樣式用到了span標(biāo)簽的也會(huì)讀取這個(gè)自定義blot,比如會(huì)導(dǎo)致我背景顏色取消的時(shí)候找不到原始方法報(bào)錯(cuò)。车荔。渡冻。。忧便。
export default EmbedTag;

使用方法:


import atTag from './atTag';
Quill.register(atTag, true); 

// 插入@用戶方法
addTagUser(obj){
      const {nick,beanId} = obj;
      let text = nick?`@${nick} `: '';
      let quill = this.$refs.myTextEditor.quill;
      let length = quill.selection.savedRange.index; // 獲取原來光標(biāo)位置
      quill.insertEmbed(length, 'atTag', {
        id: beanId,
        text,
      },Quill.sources.USER);
      quill.setSelection(length + 1, Quill.sources.USER);
 },

艱辛摸索過程紀(jì)錄:
需求:想實(shí)現(xiàn)一個(gè)@用戶 和 表情包的功能族吻,需要支持高亮 和一鍵刪除功能。
主要用到了contentEditable=false這個(gè)屬性,讓元素可以一鍵刪除呼奢,但是發(fā)現(xiàn)<span contenteditable='false'>@花兒與少年</span>這種寫法宜雀,點(diǎn)擊元素后面沒有光標(biāo),無法聚焦握础,后來發(fā)現(xiàn)了<span contenteditable="false"><span class="atUser" id="2825639815600373760">@夢(mèng)與千尋 </span></span>這種包一層的話辐董,就可以聚焦光標(biāo)了(在發(fā)現(xiàn)這種寫法之前,試過很多種的辦法禀综,這里就不描述了简烘,只是這樣說出來顯得很單薄簡(jiǎn)單),這種也可以應(yīng)用于自定義的輸入框中實(shí)現(xiàn)插入表情包等需要高亮和一鍵刪除的需求定枷。
記錄一下:上面說里面包一層span的寫法孤澎,后面又發(fā)現(xiàn)可以不用包一層也可以聚焦,之前不聚焦大致是因?yàn)榻o了span標(biāo)簽display:inline-block屬性導(dǎo)致的欠窒。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末覆旭,一起剝皮案震驚了整個(gè)濱河市,隨后出現(xiàn)的幾起案子岖妄,更是在濱河造成了極大的恐慌型将,老刑警劉巖,帶你破解...
    沈念sama閱讀 216,324評(píng)論 6 498
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件荐虐,死亡現(xiàn)場(chǎng)離奇詭異七兜,居然都是意外死亡,警方通過查閱死者的電腦和手機(jī)福扬,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 92,356評(píng)論 3 392
  • 文/潘曉璐 我一進(jìn)店門腕铸,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人铛碑,你說我怎么就攤上這事狠裹。” “怎么了亚茬?”我有些...
    開封第一講書人閱讀 162,328評(píng)論 0 353
  • 文/不壞的土叔 我叫張陵酪耳,是天一觀的道長(zhǎng)。 經(jīng)常有香客問我刹缝,道長(zhǎng),這世上最難降的妖魔是什么颈将? 我笑而不...
    開封第一講書人閱讀 58,147評(píng)論 1 292
  • 正文 為了忘掉前任梢夯,我火速辦了婚禮,結(jié)果婚禮上晴圾,老公的妹妹穿的比我還像新娘颂砸。我一直安慰自己,他們只是感情好,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,160評(píng)論 6 388
  • 文/花漫 我一把揭開白布人乓。 她就那樣靜靜地躺著勤篮,像睡著了一般。 火紅的嫁衣襯著肌膚如雪色罚。 梳的紋絲不亂的頭發(fā)上碰缔,一...
    開封第一講書人閱讀 51,115評(píng)論 1 296
  • 那天,我揣著相機(jī)與錄音戳护,去河邊找鬼金抡。 笑死,一個(gè)胖子當(dāng)著我的面吹牛腌且,可吹牛的內(nèi)容都是我干的梗肝。 我是一名探鬼主播,決...
    沈念sama閱讀 40,025評(píng)論 3 417
  • 文/蒼蘭香墨 我猛地睜開眼铺董,長(zhǎng)吁一口氣:“原來是場(chǎng)噩夢(mèng)啊……” “哼巫击!你這毒婦竟也來了?” 一聲冷哼從身側(cè)響起精续,我...
    開封第一講書人閱讀 38,867評(píng)論 0 274
  • 序言:老撾萬榮一對(duì)情侶失蹤喘鸟,失蹤者是張志新(化名)和其女友劉穎,沒想到半個(gè)月后驻右,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體什黑,經(jīng)...
    沈念sama閱讀 45,307評(píng)論 1 310
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,528評(píng)論 2 332
  • 正文 我和宋清朗相戀三年堪夭,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了愕把。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點(diǎn)故事閱讀 39,688評(píng)論 1 348
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡森爽,死狀恐怖恨豁,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情爬迟,我是刑警寧澤橘蜜,帶...
    沈念sama閱讀 35,409評(píng)論 5 343
  • 正文 年R本政府宣布,位于F島的核電站付呕,受9級(jí)特大地震影響计福,放射性物質(zhì)發(fā)生泄漏。R本人自食惡果不足惜徽职,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,001評(píng)論 3 325
  • 文/蒙蒙 一象颖、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧姆钉,春花似錦说订、人聲如沸抄瓦。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,657評(píng)論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽钙姊。三九已至,卻和暖如春埂伦,著一層夾襖步出監(jiān)牢的瞬間煞额,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 32,811評(píng)論 1 268
  • 我被黑心中介騙來泰國(guó)打工赤屋, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留立镶,地道東北人。 一個(gè)月前我還...
    沈念sama閱讀 47,685評(píng)論 2 368
  • 正文 我出身青樓类早,卻偏偏與公主長(zhǎng)得像媚媒,于是被迫代替她去往敵國(guó)和親。 傳聞我的和親對(duì)象是個(gè)殘疾皇子涩僻,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,573評(píng)論 2 353