This repository has been archived on 2023-08-30. You can view files and clone it, but cannot push or open issues/pull-requests.
bytedo
/
wcui
Archived
1
0
Fork 0
wcui/src/meditor/addon/base.js

507 lines
13 KiB
JavaScript

/**
*
* @authors yutent (yutent@doui.cc)
* @date 2017-04-17 21:41:48
*
*/
'use strict'
import '../../layer/index'
function objArr(num) {
let arr = []
while (num > 0) {
arr.push({ v: 0 })
num--
}
return arr
}
function trim(str, sign) {
return str.replace(new RegExp('^' + sign + '|' + sign + '$', 'g'), '')
}
const $doc = Anot(document)
const addon = {
h1: function(elem) {
let that = this
let offset = Anot(elem).offset()
let wrap = this.selection(true) || '在此输入文本'
layer.open({
type: 7,
menubar: false,
maskClose: true,
maskColor: 'rgba(255,255,255,0)',
fixed: true,
insert: function(level) {
wrap = wrap.replace(/^(#{1,6} )?/, '#'.repeat(level) + ' ')
that.insert(wrap, true)
this.close()
},
offset: [
offset.top + 35 - $doc.scrollTop(),
'auto',
'auto',
offset.left - $doc.scrollLeft()
],
shift: {
top: offset.top - $doc.scrollTop(),
left: offset.left - $doc.scrollLeft()
},
content: `
<ul class="do-meditor-h1 do-fn-noselect">
<li :click="insert(1)" class="h1"><i class="do-meditor__icon icon-h1"></i>一级标题</li>
<li :click="insert(2)" class="h2"><i class="do-meditor__icon icon-h2"></i>二级标题</li>
<li :click="insert(3)" class="h3"><i class="do-meditor__icon icon-h3"></i>三级标题</li>
<li :click="insert(4)" class="h4"><i class="do-meditor__icon icon-h4"></i>四级标题</li>
<li :click="insert(5)" class="h5"><i class="do-meditor__icon icon-h5"></i>五级标题</li>
<li :click="insert(6)" class="h6"><i class="do-meditor__icon icon-h6"></i>六级标题</li>
</ul>`
})
},
quote: function(elem) {
let wrap = this.selection() || '在此输入文本'
wrap = '> ' + wrap
this.insert(wrap, true)
},
bold: function(elem) {
let wrap = this.selection() || '在此输入文本'
let wraped = trim(wrap, '\\*\\*')
wrap = wrap === wraped ? '**' + wrap + '**' : wraped
this.insert(wrap, true)
},
italic: function(elem) {
let wrap = this.selection() || '在此输入文本'
let wraped = trim(wrap, '_')
wrap = wrap === wraped ? '_' + wrap + '_' : wraped
this.insert(wrap, true)
},
through: function(elem) {
let wrap = this.selection() || '在此输入文本'
let wraped = trim(wrap, '~~')
wrap = wrap === wraped ? '~~' + wrap + '~~' : wraped
this.insert(wrap, true)
},
unordered: function(elem) {
let wrap = this.selection() || '在此输入文本'
wrap = '* ' + wrap
this.insert(wrap, false)
},
ordered: function(elem) {
let wrap = this.selection() || '在此输入文本'
wrap = '1. ' + wrap
this.insert(wrap, false)
},
hr: function(elem) {
this.insert('\n\n---\n\n', false)
},
link: function(elem) {
let that = this
let offset = Anot(elem).offset()
let wrap = this.selection() || ''
layer.open({
type: 7,
menubar: false,
maskClose: true,
maskColor: 'rgba(255,255,255,0)',
fixed: true,
link: '',
linkName: wrap,
linkTarget: 1,
insert: function() {
if (!this.link || !this.linkName) {
return layer.toast('链接文字和地址不能为空', 'error')
}
let val = `[${this.linkName}](${this.link} ${
this.linkTarget === 1 ? ' "target=_blank"' : ''
})`
that.insert(val, false)
this.close()
},
offset: [
offset.top + 35 - $doc.scrollTop(),
'auto',
'auto',
offset.left - $doc.scrollLeft()
],
shift: {
top: offset.top - $doc.scrollTop(),
left: offset.left - $doc.scrollLeft()
},
content: `
<div class="do-meditor-common">
<section>
<input class="txt" :duplex="linkName" placeholder="链接文字"/>
</section>
<section>
<input class="txt" :duplex="link" placeholder="链接地址"/>
</section>
<section>
<label class="label">
<input
name="link"
type="radio"
class="radio"
:duplex-number="linkTarget"
value="1"/>
新窗口打开
</label>
<label class="label">
<input
name="link"
type="radio"
class="radio"
:duplex-number="linkTarget"
value="2"/>
本窗口打开
</label>
</section>
<section>
<a
href="javascript:;"
class="do-meditor__button submit"
:click="insert">确定</a>
</section>
</div>`
})
},
time: function(elem) {
this.insert(new Date().format(), false)
},
face: function(elem) {
let that = this
let offset = Anot(elem).offset()
layer.open({
type: 7,
title: '插入表情',
fixed: true,
maskClose: true,
maskColor: 'rgba(255,255,255,0)',
arr: [
'😀',
'😅',
'😂',
'🤣',
'😇',
'😉',
'😍',
'😗',
'😋',
'😛',
'😜',
'🤨',
'🧐',
'🤓',
'😎',
'😞',
'😔',
'😭',
'😤',
'😡',
'😱',
'😰',
'😓',
'😬',
'🙄',
'😴',
'😪',
'🤮',
'😷',
'💩',
'👻',
'💀',
'🤝',
'👎',
'👍',
'🙏'
],
offset: [
offset.top + 35 - $doc.scrollTop(),
'auto',
'auto',
offset.left - $doc.scrollLeft()
],
shift: {
top: offset.top - $doc.scrollTop(),
left: offset.left - $doc.scrollLeft()
},
content: `
<ul class="do-meditor-face">
<li class="item" :for="arr">
<span :html="el" :click="insert(el)"></span>
</li>
</ul>`,
insert: function(val) {
that.insert(val, false)
}
})
},
table: function(elem) {
let that = this
let offset = Anot(elem).offset()
layer.open({
type: 7,
title: '0行 x 0列',
fixed: true,
maskClose: true,
maskColor: 'rgba(255,255,255,0)',
offset: [
offset.top + 35 - $doc.scrollTop(),
'auto',
'auto',
offset.left - $doc.scrollLeft()
],
shift: {
top: offset.top - $doc.scrollTop(),
left: offset.left - $doc.scrollLeft()
},
matrix: objArr(10).map(function() {
return objArr(10)
}),
content: `
<ul class="do-meditor-table" ref="table">
<li :for="matrix">
<span
:for="o in el"
:class="{active: o.v}"
:data="{x: $index, y: $outer.$index}"></span>
</li>
</ul>`,
success: function() {
let tb = this.$refs.table
let lastx, lasty
Anot(tb).bind('mousemove', ev => {
if (ev.target.nodeName === 'SPAN') {
let x = ev.target.dataset.x - 0
let y = ev.target.dataset.y - 0
if (x === lastx && y === lasty) {
return
}
lastx = x
lasty = y
this.title = y + 1 + '行 x ' + (x + 1) + '列'
for (let i = 0; i <= 9; i++) {
for (let j = 0; j <= 9; j++) {
this.matrix[i][j].v = i <= y && j <= x ? 1 : 0
}
}
}
})
Anot(tb).bind('mouseleave', ev => {
lastx = -1
lasty = -1
this.title = '0行 x 0列'
for (let i = 0; i <= 9; i++) {
for (let j = 0; j <= 9; j++) {
this.matrix[i][j].v = 0
}
}
})
Anot(tb).bind('click', ev => {
if (ev.target.nodeName === 'SPAN') {
let x = ev.target.dataset.x - 0 + 1
let y = ev.target.dataset.y - 0 + 1
let thead = `\n\n${'| 表头 '.repeat(x)}|\n`
let pipe = `${'| -- '.repeat(x)}|\n`
let tbody = ('| '.repeat(x) + '|\n').repeat(y)
that.insert(thead + pipe + tbody, false)
this.close()
}
})
}
})
},
image: function(elem) {
let that = this
let offset = Anot(elem).offset()
let wrap = this.selection() || ''
layer.open({
type: 7,
menubar: false,
maskClose: true,
maskColor: 'rgba(255,255,255,0)',
fixed: true,
img: '',
imgAlt: wrap,
insert: function() {
if (!this.img || !this.imgAlt) {
return layer.toast('链接文字和地址不能为空', 'error')
}
let val = `![${this.imgAlt}](${this.img})`
that.insert(val, false)
this.close()
},
offset: [
offset.top + 35 - $doc.scrollTop(),
'auto',
'auto',
offset.left - $doc.scrollLeft()
],
shift: {
top: offset.top - $doc.scrollTop(),
left: offset.left - $doc.scrollLeft()
},
content: `
<div class="do-meditor-common">
<section>
<input class="txt" :duplex="imgAlt" placeholder="图片描述"/>
</section>
<section>
<input class="txt" :duplex="img" placeholder="图片地址"/>
</section>
<section>
<a
href="javascript:;"
class="do-meditor__button submit"
:click="insert">确定</a>
</section>
</div>
`
})
},
attach: function(elem) {
this.addon.link.call(this, elem)
},
inlinecode: function(elem) {
let wrap = this.selection() || '在此输入文本'
let wraped = trim(wrap, '`')
wrap = wrap === wraped ? '`' + wrap + '`' : wraped
this.insert(wrap, true)
},
blockcode: function(elem) {
let that = this
layer.open({
type: 7,
title: '添加代码块',
$lang: [
{ id: 'asp' },
{ id: 'actionscript', name: 'ActionScript(3.0)/Flash/Flex' },
{ id: 'bash', name: 'Bash/Shell/Bat' },
{ id: 'css' },
{ id: 'c', name: 'C' },
{ id: 'cpp', name: 'C++' },
{ id: 'csharp', name: 'C#' },
{ id: 'coffeescript', name: 'CoffeeScript' },
{ id: 'd', name: 'D' },
{ id: 'dart' },
{ id: 'delphi', name: 'Delphi/Pascal' },
{ id: 'erlang' },
{ id: 'go', name: 'Golang' },
{ id: 'html' },
{ id: 'java' },
{ id: 'javascript' },
{ id: 'json' },
{ id: 'lua' },
{ id: 'less' },
{ id: 'markdown' },
{ id: 'nginx' },
{ id: 'objective-c' },
{ id: 'php' },
{ id: 'perl' },
{ id: 'python' },
{ id: 'r', name: 'R' },
{ id: 'ruby' },
{ id: 'sql' },
{ id: 'sass', name: 'SASS/SCSS' },
{ id: 'swift' },
{ id: 'typescript' },
{ id: 'xml' },
{ id: 'yaml' },
{ id: 'other', name: '其他语言' }
],
lang: 'javascript',
code: '',
maskClose: true,
insert: function() {
let val = `\n\`\`\`${this.lang}\n${this.code ||
'// 在此输入代码'}\n\`\`\`\n`
that.insert(val, false)
this.close()
},
content: `
<div class="do-meditor-codeblock">
<section class="do-fn-cl">
<span class="label">语言类型</span>
<select :duplex="lang">
<option :for="$lang" :attr-value="el.id">{{el.name || el.id}}</option>
</select>
</section>
<section>
<textarea :duplex="code" placeholder="在这里输入/粘贴代码"></textarea>
</section>
<section class="do-fn-cl">
<a
href="javascript:;"
class="do-meditor__button submit"
:click="insert">确定</a>
</section>
</div>
`
})
},
preview: function() {
this.preview = !this.preview
if (this.preview) {
this.htmlTxt = this.__tmp__
}
},
fullscreen: function() {
this.fullscreen = !this.fullscreen
if (this.fullscreen) {
document.body.style.overflow = 'hidden'
} else {
document.body.style.overflow = ''
}
if (typeof this.props.onFullscreen === 'function') {
this.props.onFullscreen(this.fullscreen)
}
},
about: function(elem) {
let offset = Anot(elem).offset()
layer.open({
type: 7,
title: '关于编辑器',
maskClose: true,
maskColor: 'rgba(255,255,255,0)',
offset: [offset.top + 35 - $doc.scrollTop()],
shift: { top: offset.top - $doc.scrollTop() },
content:
'<div class="do-meditor-about">' +
'<pre>' +
' __ __ _____ _ _ _\n' +
'| \\/ | ____|__| (_) |_ ___ _ __\n' +
"| |\\/| | _| / _` | | __/ _ \\| '__|\n" +
'| | | | |__| (_| | | || (_) | |\n' +
'|_| |_|_____\\__,_|_|\\__\\___/|_| ' +
'v' +
Anot.ui.meditor +
'</pre>' +
'<p>开源在线Markdown编辑器</p>' +
'<p><a target="_blank" href="https://doui.cc/product/meditor">https://doui.cc/product/meditor</a></p>' +
'<p>Copyright © 2017 Yutent, The MIT License.</p>' +
'</div>'
})
}
}
export default addon
wcui是一套基于`Web Components`的UI组件库, 宗旨是追求简单、实用、不花哨。
JavaScript 95.2%
CSS 4.8%