700字范文,内容丰富有趣,生活中的好帮手!
700字范文 > vue 富文本编辑器 quill (含代码高亮 自定义字体 汉化 鼠标悬浮提示 组件封装等)

vue 富文本编辑器 quill (含代码高亮 自定义字体 汉化 鼠标悬浮提示 组件封装等)

时间:2019-02-06 21:29:31

相关推荐

vue 富文本编辑器 quill (含代码高亮 自定义字体 汉化 鼠标悬浮提示 组件封装等)

基本使用

安装依赖

npm i quill

.vue文件

<div ref="editor" :style="finalStyle"></div>

import Quill from "quill";import "quill/dist/quill.snow.css";

let Options = {theme: "snow",placeholder: "请在这里输入",modules: {toolbar: {container: [// [{ 'header': 1 }, { 'header': 2 }], // 标题 —— 独立平铺[{header: [1, 2, 3, 4, 5, 6, false]}], // 标题 —— 下拉选择[{size: ["small", false, "large", "huge"]}], // 字体大小[{list: "ordered"}, {list: "bullet"}], // 有序、无序列表["blockquote", "code-block"], // 引用 代码块// 链接按钮需选中文字后点击["link", "image", "video"], // 链接、图片、视频[{align: []}], // 对齐方式// text direction[{indent: "-1"}, {indent: "+1"}], // 缩进["bold", "italic", "underline", "strike"], // 加粗 斜体 下划线 删除线[{color: []}, {background: []}], // 字体颜色、字体背景颜色[{'script': 'sub'}, {'script': 'super'}],// 下标/上标[{'font': []}],//字体["clean"], // 清除文本格式]}}}new Quill(this.$refs.editor, Options)

代码高亮

需安装依赖

npm i highlight.js

import hljs from 'highlight.js'import 'highlight.js/styles/monokai-sublime.css'

在Options的modules里添加如下的syntax

modules: {syntax: {highlight: text => {return hljs.highlightAuto(text).value; // 这里就是代码高亮需要配置的地方}},

自定义字体

// 自定义字体let fontList = ['SimSun', 'SimHei', 'Microsoft-YaHei', 'KaiTi', 'FangSong']Quill.import('formats/font').whitelist = fontList; //将字体加入到白名单

在Options的toolbar里传入fontList

[{'font': fontList}],//字体

汉化

主要通过css实现

.ql-snow .ql-tooltip[data-mode="link"]::before {content: "请输入链接地址:";}.ql-snow .ql-tooltip.ql-editing a.ql-action::after {border-right: 0px;content: "保存";padding-right: 0px;}.ql-snow .ql-tooltip[data-mode="video"]::before {content: "请输入视频地址:";}.ql-snow .ql-picker.ql-size .ql-picker-label::before,.ql-snow .ql-picker.ql-size .ql-picker-item::before {content: "14px";}.ql-snow .ql-picker.ql-size .ql-picker-label[data-value="small"]::before,.ql-snow .ql-picker.ql-size .ql-picker-item[data-value="small"]::before {content: "10px";}.ql-snow .ql-picker.ql-size .ql-picker-label[data-value="large"]::before,.ql-snow .ql-picker.ql-size .ql-picker-item[data-value="large"]::before {content: "18px";}.ql-snow .ql-picker.ql-size .ql-picker-label[data-value="huge"]::before,.ql-snow .ql-picker.ql-size .ql-picker-item[data-value="huge"]::before {content: "32px";}.ql-snow .ql-picker.ql-header .ql-picker-label::before,.ql-snow .ql-picker.ql-header .ql-picker-item::before {content: "文本";}.ql-snow .ql-picker.ql-header .ql-picker-label[data-value="1"]::before,.ql-snow .ql-picker.ql-header .ql-picker-item[data-value="1"]::before {content: "标题1";}.ql-snow .ql-picker.ql-header .ql-picker-label[data-value="2"]::before,.ql-snow .ql-picker.ql-header .ql-picker-item[data-value="2"]::before {content: "标题2";}.ql-snow .ql-picker.ql-header .ql-picker-label[data-value="3"]::before,.ql-snow .ql-picker.ql-header .ql-picker-item[data-value="3"]::before {content: "标题3";}.ql-snow .ql-picker.ql-header .ql-picker-label[data-value="4"]::before,.ql-snow .ql-picker.ql-header .ql-picker-item[data-value="4"]::before {content: "标题4";}.ql-snow .ql-picker.ql-header .ql-picker-label[data-value="5"]::before,.ql-snow .ql-picker.ql-header .ql-picker-item[data-value="5"]::before {content: "标题5";}.ql-snow .ql-picker.ql-header .ql-picker-label[data-value="6"]::before,.ql-snow .ql-picker.ql-header .ql-picker-item[data-value="6"]::before {content: "标题6";}.ql-snow .ql-picker.ql-font .ql-picker-label[data-value=SimSun]::before,.ql-snow .ql-picker.ql-font .ql-picker-item[data-value=SimSun]::before {content: "宋体";}.ql-font-SimSun {font-family: "SimSun";}.ql-snow .ql-picker.ql-font .ql-picker-label[data-value=SimHei]::before,.ql-snow .ql-picker.ql-font .ql-picker-item[data-value=SimHei]::before {content: "黑体";}.ql-font-SimHei {font-family: "SimHei";}.ql-snow .ql-picker.ql-font .ql-picker-label[data-value=Microsoft-YaHei]::before,.ql-snow .ql-picker.ql-font .ql-picker-item[data-value=Microsoft-YaHei]::before {content: "微软雅黑";}.ql-font-Microsoft-YaHei {font-family: "Microsoft YaHei";}.ql-snow .ql-picker.ql-font .ql-picker-label[data-value=KaiTi]::before,.ql-snow .ql-picker.ql-font .ql-picker-item[data-value=KaiTi]::before {content: "楷体";}.ql-font-KaiTi {font-family: "KaiTi";}.ql-snow .ql-picker.ql-font .ql-picker-label[data-value=FangSong]::before,.ql-snow .ql-picker.ql-font .ql-picker-item[data-value=FangSong]::before {content: "仿宋";}.ql-font-FangSong {font-family: "FangSong";}

鼠标悬浮提示

new Quill 后执行方法即可

new Quill(this.$refs.editor, Options);this.addQuillTitle();

addQuillTitle() {const titleConfig = {'ql-bold': '加粗','ql-color': '颜色','ql-font': '字体','ql-code': '插入代码','ql-italic': '斜体','ql-link': '添加链接','ql-background': '背景颜色','ql-size': '字体大小','ql-strike': '删除线','ql-script': '上标/下标','ql-underline': '下划线','ql-blockquote': '引用','ql-header': '标题','ql-indent': '缩进','ql-list': '列表','ql-align': '文本对齐','ql-direction': '文本方向','ql-code-block': '代码块','ql-formula': '公式','ql-image': '图片','ql-video': '视频','ql-clean': '清除字体样式'}let oToolBar = document.querySelector('.ql-toolbar')if (!oToolBar) {return}let aButton = oToolBar.querySelectorAll('button')let aSelect = oToolBar.querySelectorAll('select')aButton.forEach(function (item) {if (item.className === 'ql-script') {item.value === 'sub' ? item.title = '下标' : item.title = '上标'} else if (item.className === 'ql-indent') {item.value === '+1' ? item.title = '向右缩进' : item.title = '向左缩进'} else {item.title = titleConfig[item.classList[0]]}})aSelect.forEach(function (item) {item.parentNode.title = titleConfig[item.classList[0]]})}

组件封装

pub-editor_quill.vue

<template><div ref="editor" :style="finalStyle"></div></template><script>import Quill from "quill";import "quill/dist/quill.snow.css";import hljs from 'highlight.js'import 'highlight.js/styles/monokai-sublime.css'export default {watch: {value(newVal) {if (newVal && newVal !== this.newValue) {// 父组件传入新值,且父组件传入的新值不为子组件当前的值(子组件的内容发生改变时传给父组件的值)时this.newValue = newValthis.quill.pasteHTML(newVal)} else if (!newVal) {this.quill.setText('')}},disabled(newVal) {this.quill.enable(!newVal)}},props: {hideTool: {type: Boolean,default: false},value: String,disabled: {type: Boolean,default: false},editorStyle: {type: Object,default: () => {return {minHeight: '100px'}}},disabledStyle: {type: Object,default: () => {// 与elementui表单禁用风格一致return {background: "#f5f7fa",color: "#c0c4cc",cursor: "not-allowed",borderRadius: "4px",border: "1px solid #dcdfe6"}}},options: {type: Object,required: false,default: () => ({})},},methods: {disEditor() {this.finalStyle = Object.assign({}, this.finalStyle, this.disabledStyle)},init() {if (JSON.stringify(this.editorStyle) !== "{}") {this.finalStyle = this.editorStyle}// 自定义字体let fontList = ['SimSun', 'SimHei', 'Microsoft-YaHei', 'KaiTi', 'FangSong']Quill.import('formats/font').whitelist = fontList; //将字体加入到白名单let defaultOptions = {theme: "snow",placeholder: "请在这里输入",modules: {syntax: {highlight: text => {return hljs.highlightAuto(text).value; // 这里就是代码高亮需要配置的地方}},toolbar: {container: [// [{ 'header': 1 }, { 'header': 2 }], // 标题 —— 独立平铺[{header: [1, 2, 3, 4, 5, 6, false]}], // 标题 —— 下拉选择[{size: ["small", false, "large", "huge"]}], // 字体大小[{list: "ordered"}, {list: "bullet"}], // 有序、无序列表["blockquote", "code-block"], // 引用 代码块// 链接按钮需选中文字后点击["link", "image", "video"], // 链接、图片、视频[{align: []}], // 对齐方式// text direction[{indent: "-1"}, {indent: "+1"}], // 缩进["bold", "italic", "underline", "strike"], // 加粗 斜体 下划线 删除线[{color: []}, {background: []}], // 字体颜色、字体背景颜色[{'script': 'sub'}, {'script': 'super'}],// 下标/上标[{'font': fontList}],//字体["clean"], // 清除文本格式]}}}let finalOptions = Object.assign({}, defaultOptions, this.options)if (this.hideTool) {finalOptions.modules.toolbar = null}this.quill = new Quill(this.$refs.editor, finalOptions);this.addQuillTitle();if (this.value) {this.quill.pasteHTML(this.value)}// 调整光标到最后this.quill.setSelection(this.quill.getLength() + 1);this.quill.enable(!this.disabled)if (this.disabled) {this.disEditor()}this.quill.on('selection-change', range => {if (!range) {this.$emit('blur', this.quill)} else {this.$emit('focus', this.quill)}})this.quill.on('text-change', () => {let html = this.$refs.editor.children[0].innerHTMLif (html === '<p><br></p>') html = ''this.newValue = htmlthis.$emit('input', this.newValue)this.$emit('change', {html: this.newValue,text: this.quill.getText()})})},addQuillTitle() {const titleConfig = {'ql-bold': '加粗','ql-color': '颜色','ql-font': '字体','ql-code': '插入代码','ql-italic': '斜体','ql-link': '添加链接','ql-background': '背景颜色','ql-size': '字体大小','ql-strike': '删除线','ql-script': '上标/下标','ql-underline': '下划线','ql-blockquote': '引用','ql-header': '标题','ql-indent': '缩进','ql-list': '列表','ql-align': '文本对齐','ql-direction': '文本方向','ql-code-block': '代码块','ql-formula': '公式','ql-image': '图片','ql-video': '视频','ql-clean': '清除字体样式'}let oToolBar = document.querySelector('.ql-toolbar')if (!oToolBar) {return}let aButton = oToolBar.querySelectorAll('button')let aSelect = oToolBar.querySelectorAll('select')aButton.forEach(function (item) {if (item.className === 'ql-script') {item.value === 'sub' ? item.title = '下标' : item.title = '上标'} else if (item.className === 'ql-indent') {item.value === '+1' ? item.title = '向右缩进' : item.title = '向左缩进'} else {item.title = titleConfig[item.classList[0]]}})aSelect.forEach(function (item) {item.parentNode.title = titleConfig[item.classList[0]]})}},mounted() {this.init()},beforeDestroy() {this.quill = nulldelete this.quill},data() {return {quill: null,newValue: null,finalStyle: {}}},}</script><style>.ql-snow .ql-tooltip[data-mode="link"]::before {content: "请输入链接地址:";}.ql-snow .ql-tooltip.ql-editing a.ql-action::after {border-right: 0px;content: "保存";padding-right: 0px;}.ql-snow .ql-tooltip[data-mode="video"]::before {content: "请输入视频地址:";}.ql-snow .ql-picker.ql-size .ql-picker-label::before,.ql-snow .ql-picker.ql-size .ql-picker-item::before {content: "14px";}.ql-snow .ql-picker.ql-size .ql-picker-label[data-value="small"]::before,.ql-snow .ql-picker.ql-size .ql-picker-item[data-value="small"]::before {content: "10px";}.ql-snow .ql-picker.ql-size .ql-picker-label[data-value="large"]::before,.ql-snow .ql-picker.ql-size .ql-picker-item[data-value="large"]::before {content: "18px";}.ql-snow .ql-picker.ql-size .ql-picker-label[data-value="huge"]::before,.ql-snow .ql-picker.ql-size .ql-picker-item[data-value="huge"]::before {content: "32px";}.ql-snow .ql-picker.ql-header .ql-picker-label::before,.ql-snow .ql-picker.ql-header .ql-picker-item::before {content: "文本";}.ql-snow .ql-picker.ql-header .ql-picker-label[data-value="1"]::before,.ql-snow .ql-picker.ql-header .ql-picker-item[data-value="1"]::before {content: "标题1";}.ql-snow .ql-picker.ql-header .ql-picker-label[data-value="2"]::before,.ql-snow .ql-picker.ql-header .ql-picker-item[data-value="2"]::before {content: "标题2";}.ql-snow .ql-picker.ql-header .ql-picker-label[data-value="3"]::before,.ql-snow .ql-picker.ql-header .ql-picker-item[data-value="3"]::before {content: "标题3";}.ql-snow .ql-picker.ql-header .ql-picker-label[data-value="4"]::before,.ql-snow .ql-picker.ql-header .ql-picker-item[data-value="4"]::before {content: "标题4";}.ql-snow .ql-picker.ql-header .ql-picker-label[data-value="5"]::before,.ql-snow .ql-picker.ql-header .ql-picker-item[data-value="5"]::before {content: "标题5";}.ql-snow .ql-picker.ql-header .ql-picker-label[data-value="6"]::before,.ql-snow .ql-picker.ql-header .ql-picker-item[data-value="6"]::before {content: "标题6";}.ql-snow .ql-picker.ql-font .ql-picker-label[data-value=SimSun]::before,.ql-snow .ql-picker.ql-font .ql-picker-item[data-value=SimSun]::before {content: "宋体";}.ql-font-SimSun {font-family: "SimSun";}.ql-snow .ql-picker.ql-font .ql-picker-label[data-value=SimHei]::before,.ql-snow .ql-picker.ql-font .ql-picker-item[data-value=SimHei]::before {content: "黑体";}.ql-font-SimHei {font-family: "SimHei";}.ql-snow .ql-picker.ql-font .ql-picker-label[data-value=Microsoft-YaHei]::before,.ql-snow .ql-picker.ql-font .ql-picker-item[data-value=Microsoft-YaHei]::before {content: "微软雅黑";}.ql-font-Microsoft-YaHei {font-family: "Microsoft YaHei";}.ql-snow .ql-picker.ql-font .ql-picker-label[data-value=KaiTi]::before,.ql-snow .ql-picker.ql-font .ql-picker-item[data-value=KaiTi]::before {content: "楷体";}.ql-font-KaiTi {font-family: "KaiTi";}.ql-snow .ql-picker.ql-font .ql-picker-label[data-value=FangSong]::before,.ql-snow .ql-picker.ql-font .ql-picker-item[data-value=FangSong]::before {content: "仿宋";}.ql-font-FangSong {font-family: "FangSong";}</style>

使用方法

<pub-editor_quillv-model="content"@blur="onEditorBlur()"@focus="onEditorFocus()"@change="onEditorChange()"/>

data() {return {content: '编辑器的初始值',}},

本内容不代表本网观点和政治立场,如有侵犯你的权益请联系我们处理。
网友评论
网友评论仅供其表达个人看法,并不表明网站立场。