Tinymce - 宇宙第一富文字編輯器?[1]

嘉禾生2310發表於2019-09-19

Tinymce

tinymce是一款基礎元件十分豐富,不斷維護更新的富文字編輯器。在它的Github專案簡介中如此描述自己:

The world's #1 JavaScript library for rich text editing. Available for React, Vue and Angular

簡而言之: 我是宇宙第一的編輯器,我支援當前最流行的三個框架。

我會分成3篇文章介紹:

  1. 編輯器的基本使用和一些簡單外掛的配置
  2. 一些複雜外掛的配置,和整合Vue
  3. 編寫自定義外掛

Why Tinymce

  • 基礎元件豐富,簡單配置即可使用;
  • 本身有收費版和免費版,可盈利性保證了其持續維護和創新,開發版其實也完全夠用;
  • 提供的開發擴充API也比較簡單,適合持續整合;
  • 開發文件雖然是英文版,但言簡意賅,示例豐富,並且跟隨版本實時更新,對比市面上其他編輯器好太多了

開始使用

本文使用的版本是 5.0.13

安裝

Tinymce的核心檔案和外掛、皮膚、主題樣式等檔案都是分離的,使用時,只需在HTML中引入核心檔案(tinymce.js)即可。

<script src="https://fe.120yibao.com/common/tinymce/5.0.13/tinymce.min.js"></script>
複製程式碼

在生成新的編輯器例項時,需要傳入配置檔案,tinymce會根據配置自動引入對應的外掛、皮膚、主題檔案,預設使用相對路徑(相對於與tinymce.js)的方式。

const editor = Tinymce.init({
    //會自動引入link外掛
    // https://fe.120yibao.com/common/tinymce/5.0.13/plugins/link/plugin.min.js
    plugins: ['link'],  
    //會自動引入silver主題
    // https://fe.120yibao.com/common/tinymce/5.0.13/themes/silver/theme.min.js
    theme: 'silver',
    //會自動引入oxide皮膚
    // https://fe.120yibao.com/common/tinymce/5.0.13/skins/ui/oxide/skin.min.css
    skin: "oxide"
})
複製程式碼

而這些相對路徑的關係,跟npm包的對應關係是一樣的。

npm i tinymce
複製程式碼

我們看下npm包的目錄結構

.
├── jquery.tinymce.js
├── jquery.tinymce.min.js
├── plugins
│   ├── advlist
│   │   ├── index.js
│   │   ├── plugin.js
│   │   └── plugin.min.js
│   ├── anchor
│   │   ├── index.js
│   │   ├── plugin.js
│   │   └── plugin.min.js
│   ├── autolink
│   │   ├── index.js
│   │   ├── plugin.js
│   │   └── plugin.min.js
├── skins
│   ├── content
│   │   ├── default
│   │   │   ├── content.css
│   │   │   └── content.min.css
│   │   ├── document
│   │   │   ├── content.css
│   │   │   └── content.min.css
│   │   └── writer
│   │       ├── content.css
│   │       └── content.min.css
│   └── ui
│       ├── oxide
│       │   ├── content.css
│       │   ├── content.inline.css
│       │   ├── content.inline.min.css
│       │   ├── content.min.css
│       │   ├── content.mobile.css
│       │   ├── content.mobile.min.css
│       │   ├── fonts
│       │   │   └── tinymce-mobile.woff
│       │   ├── skin.css
│       │   ├── skin.min.css
│       │   ├── skin.mobile.css
│       │   └── skin.mobile.min.css
│       └── oxide-dark
│           ├── content.css
│           ├── content.inline.css
│           ├── content.inline.min.css
│           ├── content.min.css
│           ├── content.mobile.css
│           ├── content.mobile.min.css
│           ├── fonts
│           │   └── tinymce-mobile.woff
│           ├── skin.css
│           ├── skin.min.css
│           ├── skin.mobile.css
│           └── skin.mobile.min.css
├── themes
│   ├── mobile
│   │   ├── index.js
│   │   ├── theme.js
│   │   └── theme.min.js
│   └── silver
│       ├── index.js
│       ├── theme.js
│       └── theme.min.js
├── tinymce.js
└── tinymce.min.js

複製程式碼

CDN

所以,如果要使用CDN的方式使用tinymce的話,直接安裝這個目錄格式上傳即可。

npm

也可以使用npm進行引入,但是每個外掛、主題、皮膚都要單獨引入,比較麻煩,不建議使用。

// Import TinyMCE
import tinymce from 'tinymce/tinymce';

// A theme is also required
import 'tinymce/themes/silver';

// Any plugins you want to use has to be imported
import 'tinymce/plugins/paste';
import 'tinymce/plugins/link';

// Initialize the app
tinymce.init({
  selector: '#tiny',
  plugins: ['paste', 'link']
});
複製程式碼

快速開始

<template>
	<div class="default-tinymce">
		<textarea id="editor"></textarea>
	</div>
</template>
<script>
import Tinymce from 'tinymce'
export default {
  name: 'DefaultTinymce',
  mounted () {
    Tinymce.init({
      selector: '#editor'
    })
  }
}
</script>
複製程式碼
  • 此示例只配置了唯一的必填配置selector,即textarta元素的標識,此引數值支援類似於CSS選擇器的引數格式。

  • 此示例除了使用了入口檔案(tinymce.js),也會引入預設的主題和皮膚檔案。

  • 初始化成功後,textarea的值會與一個iframe繫結,在富文字編輯區域的操作,其實都是在iframe中的操作,而內容則會自動同步到textarea裡。

三種模式

tinymce 有三種模式可選:經典模式(classic,預設)、行內模式(inline)、清爽模式(Distraction-free)。

經典模式是最常見的,也就是工具欄搭配輸入區域,通過工具欄的按鈕插入、修改、格式化內容,我們也選用這種模式作為業務的主要模式。

後兩種模式也各有特點,但是與我們實際的應用場景不太匹配,故再次不多做介紹。有興趣可以自行了解。

多個編輯器

如果一個頁面中需要多個編輯器,有兩種方法:

一個是結合className選擇器,使用一次 tinymceinit 方法,生成多個例項,多個例項會共用一套配置;

示例程式碼:

<template>
	<div class="default-tinymce">
        <h2>編輯器1</h2>
		<textarea class="editor"></textarea>
        <h2>編輯器2</h2>
		<textarea class="editor"></textarea>
	</div>
</template>
<script>
import Tinymce from 'tinymce'
export default {
  mounted () {
    Tinymce.init({
      selector: '.editor'
    })
  }
}
</script>

複製程式碼

另一種是,需要幾個編輯器,便使用tinymceinit 方法生成幾種例項,生成的例項彼此無關

示例程式碼:

<template>
	<div class="default-tinymce">
        <h2>編輯器1</h2>
		<textarea class="editor1"></textarea>
        <h2>編輯器2</h2>
		<textarea class="editor2"></textarea>
	</div>
</template>
<script>
import Tinymce from 'tinymce'
export default {
  mounted () {
    Tinymce.init({
      selector: '.editor1'
    })
    Tinymce.init({
      selector: '.editor2'
    })
  }
}
</script>

複製程式碼

編輯器配置

配置語言

可以將編輯器的語言配置為中文

tinymce.init({
    selector: '#myTextarea',
    language: 'zh_CN'
})

複製程式碼
  • 可以設定language_url,覆蓋預設地址。
tinymce.init({
    selector: '#myTextarea',
    language_url: 'https://fe.120yibao.com/common/tinymce/5.0.13/langs/zh_CN_01.js'
})
複製程式碼
  • 也可以在專案中配置語言檔案:
import Language from './language'
Tinymce.addI18n('zh_CN_01', Language)

tinymce.init({
    selector: '#myTextarea',
    language: 'zh_CN_01'
})
複製程式碼

附:官方多語言檔案下載地址

基礎配置

以下配置大致涵蓋了tinymce的基礎配置,具體我會分章節在下面說明

tinymce.init({
    selector: '#myTextarea',
    // 編輯器的皮膚,有 oxide oxide-dark
    skin: 'dark',
    // 編輯器寬高
    width: 600,
    height: 300,
    // 用到的外掛
    plugins: [
      'advlist autolink link image lists charmap print preview hr anchor pagebreak spellchecker',
      'searchreplace wordcount visualblocks visualchars code fullscreen insertdatetime media nonbreaking',
      'save table contextmenu directionality emoticons template paste textcolor'
    ],
    // 編輯區域內容樣式
    content_css: 'css/content.css',
    // 工具欄的配置項
    toolbar: 'insertfile undo redo | styleselect | bold italic | alignleft aligncenter alignright alignjustify | bullist numlist outdent indent | link image | print preview media fullpage | forecolor backcolor emoticons'
  });
複製程式碼

使用外掛

除了預設的配置,如果想擴充編輯器的功能,tinymce提供的方式就是外掛。

官方的外掛很豐富,文件也很詳細,大多數情況下,我只需要官方提供的外掛即可。

啟用外掛也很簡單,只需要做了相應配置即可。

比如,我們想要擴充一個檢視編輯器內容HTML原始碼的功能,只需要如下配置:

tinymce.init({
  selector: '#editor',
  plugins: 'code'
})

複製程式碼

menubar的位置,多了一個Tool的分組,分組裡有一個source code的項,點選即可檢視原始碼

如果我們不習慣使用menubar,而是習慣使用toolbar,我們只需要如下配置:

tinymce.init({
  selector: '#editor',
  toolbar: 'code',
  plugins: 'code'
})

複製程式碼

toolbar位置上多了一個檢視原始碼的圖示,點選是相同的功能

有時候,這些基礎的功能可能滿足不了我們的需求,我們可能對這些外掛進行配置。

tinymce.init({
  selector: '#editor',
   toolbar: "numlist bullist",
  plugins: 'lists'
})

複製程式碼

示例中,我們配置了list元件,它支援無序(ul)列表和有序列表的功能,但是列表樣式是固定的,我們可以引入新的外掛advlist,並配置

tinymce.init({
  selector: '#editor',
  toolbar: 'bullist numlist',
  plugins: 'lists advlist'
})
複製程式碼

此時,我們發現我們可以選擇樣式了,有多種樣式供我們選擇,如果我們想固定某種樣式,我們可以這樣配置:

tinymce.init({
  selector: '#editor',
  toolbar: 'bullist numlist',
  plugins: 'lists advlist',
  advlist_number_styles: 'lower-alpha'
})
複製程式碼

我們發現可選項只有一個了

每個外掛有哪些配置項、配置引數和配置值,官方文件中都有詳細的描述

自定義編輯器UI

themeskin 我們直接使用預設的即可,無需折騰。

從上面的示例中,我們也知道基本上所有東西我們都可以去自定義的,比如隱藏不使用的menubar、調整按鈕在toolbar中的位置等。

tinymce.init({
  selector: '#editor',
  // 隱藏menubar
  menubar: false,
  // 隱藏 statusbar
  statusbar: false,
  // 隱藏品牌標識
  branding: false,
  // 設定最大寬高
  max_height: 500,
  max_width: 500,
  // 設定最小寬高
  min_height: 100,
  min_width: 400
})

複製程式碼

這些配置不太重要,一般一次配置之後就不會有改動。

外掛配置

這裡會寫一下編輯器用到的外掛的介紹、配置、和使用,太簡單的外掛和沒用到的外掛不在此說明。

Advanced Code Editor

此外掛為付費外掛

此外掛可美化程式碼預覽時候的檢視,並且還有收起/展開標籤的功能。配置此外掛後,需要移除code外掛。

tinymce.init({
  selector: "textarea",  // change this value according to your HTML
  plugins: "advcode",
  toolbar: "code"
});
複製程式碼

AutoLink

此外掛可在輸入形如「www.qq.com」的連結時,自動將文字轉化為超連結,空格和換行鍵都可以觸發

tinymce.init({
  selector: "textarea",  // change this value according to your HTML
  plugins: "autolink"
});
複製程式碼

nonbreaking

鍵盤的Tab鍵,預設是切換到下一個元素的focus。此可以改變這個預設行為。

需要注意的是,table外掛中也有改變改預設行為的程式碼,所以要在table外掛之後引用該外掛。

tinymce.init({
  selector: "textarea",  // change this value according to your HTML
  plugins: "nonbreaking",
  // 此配置會改變預設行為,會在游標之後新增三個空格。
  nonbreaking_force_tab: true
});
複製程式碼

autosave

此外掛會自動儲存編輯器的內容到localStorage。會同時儲存兩個欄位,一個是內容,一個是儲存時間。

可以配置自動儲存的時間間隔,一般以秒為單位;也可以配置內容儲存的過期時間,一般以分鐘為單位,超過這個時間段,資料會從localStorage中被清除。

tinymce.init({
  selector: "textarea",  // change this value according to your HTML
  plugins: "autosave",
  // 自動儲存的時間間隔
  autosave_interval: '30s',
  // 自動儲存的資料儲存的最大時間
  autosave_retention: '30m'
});
複製程式碼

powerpaste

此外掛為付費外掛

此外掛可以保留剪下板內容的樣式、文件結構。

tinymce.init({
  selector: "textarea",  // change this value according to your HTML
  plugins: "powerpaste",
  /**
   * 貼上前是否保留文字樣式
   * @param 'clean' 不保留
   * @parma 'merge' 保留
   * @parma 'prompt' 詢問使用者
   */
  powerpaste_word_import: 'prompt',
  powerpaste_html_import: 'prompt',
  /**
   * 在貼上到富文字之前,可以修改貼上的內容。內容已經DOM格式化
   * @param plugin
   * @param args
   * @returns {Promise<void>}
   */
  paste_postprocess (plugin, args) {}
});
複製程式碼

下一篇:Tinymce - 宇宙第一富文字編輯器?[2]

參考

  1. tinymce官方文件

相關文章