✨新增思维导图插件

This commit is contained in:
jmal 2022-08-18 18:04:45 +08:00
parent 1cb13b6ff1
commit 1146074305
18 changed files with 205 additions and 81 deletions

View File

@ -28,6 +28,7 @@
"jquery.fancytree": "^2.35.0",
"js-cookie": "2.2.0",
"jshint": "^2.11.1",
"jspdf": "^2.5.1",
"less-loader": "^6.1.0",
"lib-flexible": "^0.3.2",
"monaco-editor": "^0.23.0",
@ -81,6 +82,7 @@
"serve-static": "^1.13.2",
"svg-sprite-loader": "4.1.3",
"svgo": "1.2.2",
"vue-kityminder-ggg": "^1.3.10",
"vue-template-compiler": "^2.6.13"
},
"engines": {

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

View File

@ -279,9 +279,9 @@ export default {
})
},
// 根据id获取文件信息
getPublicFileInfoById: function(id) {
getPublicFileInfoById: function(fileId, shareId) {
return request({
url: `/public/file_info/${id}`,
url: `/public/file_info/${fileId}/${shareId}`,
method: 'get'
})
},

View File

@ -5,7 +5,7 @@
import { Icon } from 'ant-design-vue'
const IconFont = Icon.createFromIconfontCN({
scriptUrl: document.location.protocol + '/resource/font_2024484_9qbzcip6x9m.js'
scriptUrl: document.location.protocol + '/resource/font_2024484_b4h46y1d4ho.js'
})
// 把此段代码贴到iconfont项目页面的控制台中, 以获取图标列表

View File

@ -1839,6 +1839,7 @@ export default {
this.textPreviewVisible = true
break
case 'drawio':
case 'mind':
case 'docx':
case 'xlsx':
case 'pptx':
@ -2565,6 +2566,10 @@ export default {
this.newCreateFileDialogTitle = "新建流程图"
this.createNewFile('drawio')
break
case 'createMinderFile':
this.newCreateFileDialogTitle = "新建思维导图"
this.createNewFile('mind')
break
case 'createWordFile':
this.newCreateFileDialogTitle = "新建Word文档"
this.createNewFile('docx')
@ -3159,7 +3164,7 @@ export default {
this.openCompressionVisible = true
return
}
if (row.contentType.indexOf('office') > -1 || ['pdf','csv','drawio'].includes(row.suffix)) {
if (row.contentType.indexOf('office') > -1 || ['pdf','csv','drawio','mind'].includes(row.suffix)) {
// office文件
this.officePreviewVisible = true
this.officePreviewRow = row

View File

@ -1,63 +1,18 @@
<template>
<div class="drawio-content" :style="{'top': readOnly ? '0': '2.5rem'}">
<div class="drawio-title">
<span class="drawio-title-name" :style="{'color': saved ? '': '#ff8200'}">{{title}}</span>
<span class="drawio-save"><el-button v-if="!saved" @click="save" size="mini" :loading="saveBtnUpdating">保存</el-button></span>
<div class="drawio-title-name" :style="{'color': saved ? '': '#ff8200'}">{{title}}</div>
<div class="drawio-save"><el-button v-if="!saved" @click="save" size="mini" :loading="saveBtnUpdating">保存</el-button></div>
</div>
<iframe ref="myFlow" class="drawio-iframe" :src="url" :title="file.name"></iframe>
</div>
</template>
<style lang="scss" scoped>
.drawio-content {
z-index: 999;
position: absolute;
top: 2.5rem;
left: 0;
width: 100%;
height: 100%;
.drawio-title {
text-align: center;
background-color: #fbfbfb;
z-index: 2001;
position: absolute;
top: 0;
width: 100%;
height: 10px;
.drawio-title-name {
line-height: 40px;
}
.drawio-save {
float: right;
margin-right: 30px;
line-height: 40px;
}
}
.drawio-iframe {
z-index: 1999;
position: absolute;
top: 10px;
left: 0;
width: 100%;
height: 100%;
background: 0 0;
border: 0;
float: none;
margin: -1px 0 0;
max-width: none;
outline: 0;
padding: 0;
}
}
</style>
<script>
import api from '@/api/file-api'
import txtApi from "@/api/markdown-api"
import Bus from "@/assets/js/bus";
export default {
name: "Drawio",
@ -98,11 +53,15 @@ export default {
this.url = $J.apiUrl(`../drawio/webapp/${query}`)
},
mounted() {
Bus.$on('previewSaveAndClose', this.saveAndClose)
window.addEventListener('message', this.handleMessage)
},
beforeDestroy() {
window.removeEventListener('message', this.handleMessage)
},
destroyed() {
Bus.$off('previewSaveAndClose')
},
watch: {
'file.id': {
handler(id) {
@ -134,8 +93,14 @@ export default {
deep: true,
},
},
computed: {},
methods: {
/**
* 保存并关闭
*/
saveAndClose() {
this.save()
this.$emit('onClose')
},
updateContent() {
this.$refs.myFlow.contentWindow.postMessage(JSON.stringify({
action: "load",
@ -144,10 +109,9 @@ export default {
}), "*")
},
save() {
this.saved = true
this.title = this.file.name
this.update(this.xml)
this.$emit('onEdit', this.saved)
if (!this.saved) {
this.update(this.xml)
}
},
update(value) {
this.saveBtnUpdating = true
@ -158,11 +122,9 @@ export default {
contentText: value
}).then(() => {
this.saveBtnUpdating = false
this.$message({
message: "保存成功",
type: 'success',
duration : 1000
})
this.saved = true
this.title = this.file.name
this.$emit('onEdit', this.saved)
}).catch(() => {
this.saveBtnUpdating = false
})
@ -204,3 +166,51 @@ export default {
},
}
</script>
<style lang="scss" scoped>
.drawio-content {
z-index: 999;
position: absolute;
top: 2.5rem;
left: 0;
width: 100%;
height: 100%;
.drawio-title {
text-align: center;
background-color: #fbfbfb;
z-index: 2001;
position: absolute;
top: 0;
width: 100%;
height: 10px;
.drawio-title-name {
line-height: 40px;
}
.drawio-save {
float: right;
margin-top: -40px;
margin-right: 30px;
line-height: 40px;
}
}
.drawio-iframe {
z-index: 1999;
position: absolute;
top: 10px;
left: 0;
width: 100%;
height: 100%;
background: 0 0;
border: 0;
float: none;
margin: -1px 0 0;
max-width: none;
outline: 0;
padding: 0;
}
}
</style>

View File

@ -29,6 +29,10 @@ export default {
type: String,
default: ''
},
shareId: {
type: String,
default: ''
},
file: {
type: Object,
default: function () {
@ -77,7 +81,7 @@ export default {
this.loadFile()
})
} else {
api.getPublicFileInfoById(this.file.id).then(res => {
api.getPublicFileInfoById(this.file.id, this.shareId).then(res => {
this.file = res.data
this.loadFile()
})
@ -92,6 +96,9 @@ export default {
this.requestClose()
})
},
destroyed() {
Bus.$off('previewSaveAndClose')
},
methods: {
getType(type) {
switch (type) {

View File

@ -17,8 +17,9 @@
</div>
<div class="wrapper">
<pdf-preview v-if="fileType === 'pdf'" :file="file" :shareId="shareId" :file-url="fileUrl" @onReady="onReady"></pdf-preview>
<drawio v-else-if="fileType === 'drawio'" v-show="fileReday" :file="file" :shareId="shareId" :read-only="readOnly" @onEdit="onEdit" @onReady="onReady"></drawio>
<only-office-editor ref="officeEditor" v-else :file="file" :file-url="fileUrl" :read-only="readOnly" @onEdit="onEdit" @manualSave="manualSave" @onClose="close" @onReady="onReady"></only-office-editor>
<drawio v-else-if="fileType === 'drawio'" v-show="fileReday" :file="file" :shareId="shareId" :read-only="readOnly" @onEdit="onEdit" @onReady="onReady" @onClose="close"></drawio>
<my-mind-editor v-else-if="fileType === 'mind'" :file="file" :shareId="shareId" :read-only="readOnly" @onEdit="onEdit" @onReady="onReady" @onClose="close"></my-mind-editor>
<only-office-editor ref="officeEditor" v-else :file="file" :file-url="fileUrl" :shareId="shareId" :read-only="readOnly" @onEdit="onEdit" @manualSave="manualSave" @onClose="close" @onReady="onReady"></only-office-editor>
</div>
</div>
</div>
@ -33,10 +34,11 @@ import Bus from "@/assets/js/bus";
import fileConfig from "@/utils/file-config";
import PdfPreview from "@/components/office/PdfPreview";
import Drawio from "@/components/office/Drawio";
import MyMindEditor from "@/components/Minder/minder"
export default {
name: 'OfficePreview',
components: {Drawio, PdfPreview, MessageDialog, OnlyOfficeEditor},
components: {Drawio, PdfPreview, MessageDialog, OnlyOfficeEditor, MyMindEditor},
props: {
id: {
type: String,
@ -79,15 +81,10 @@ export default {
},
},
mounted() {
let that = this;
this.$nextTick(function () {
document.addEventListener('keyup', function (e) {
// 监听ESC键
if (e.code === 'Escape') {
that.beforeClose()
}
}, false)
})
document.addEventListener('keyup', this.escape)
},
destroyed() {
document.removeEventListener('keyup', this.escape)
},
watch: {
status: function(visible){
@ -96,7 +93,6 @@ export default {
this.$nextTick(() => {
this.previewDocument = document.querySelector('.preview-block')
})
this.checkReadOnly(this.file.userId)
// 6秒后还没加载出来视为加载失败
let that = this
@ -109,12 +105,23 @@ export default {
}
},
methods: {
/**
* 按esc键
*/
escape(event) {
// 监听ESC键
if (event.code === 'Escape') {
this.beforeClose()
}
},
getType(suffix) {
switch (suffix) {
case 'drawio':
return 'drawio'
case 'pdf':
return 'pdf'
case 'mind':
return 'mind'
default:
return 'office'
}

View File

@ -1 +1 @@
<svg t="1585726931619" class="icon" viewBox="0 0 1024 1024" version="1.1" xmlns="http://www.w3.org/2000/svg" p-id="70318" width="32" height="32"><path d="M0 0h1024v1024H0z" fill="#F2BF30" p-id="70319"></path><path d="M449.422222 591.644444H568.888889l-28.444445 62.577778H477.866667zM449.422222 859.022222l28.444445-204.8h62.577777l34.133334 204.8z" fill="#F2BF30" p-id="70320"></path><path d="M506.311111 284.444444L386.844444 210.488889 170.666667 324.266667l91.022222 96.711111zM506.311111 557.511111L261.688889 420.977778 170.666667 529.066667l233.244444 142.222222zM512 557.511111l108.088889 113.777778L853.333333 529.066667l-96.711111-108.088889z" fill="#FFFFFF" p-id="70321"></path><path d="M620.088889 711.111111l-113.777778-108.088889-96.711111 108.088889-142.222222-91.022222v85.333333L512 853.333333l250.311111-142.222222v-91.022222zM853.333333 324.266667l-221.866666-113.777778L512 284.444444l244.622222 136.533334z" fill="#FFFFFF" p-id="70322"></path></svg>
<?xml version="1.0" standalone="no"?><!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd"><svg t="1660809170207" class="icon" viewBox="0 0 1024 1024" version="1.1" xmlns="http://www.w3.org/2000/svg" p-id="21484" xmlns:xlink="http://www.w3.org/1999/xlink" width="32" height="32"><defs><style type="text/css"></style></defs><path d="M923.136 969.557333H193.024v-909.653333h521.386667l208.725333 207.701333z" fill="#7CCDFF" p-id="21485"></path><path d="M912.896 253.952l2.56 671.914667c0 15.530667-12.458667 27.989333-27.989333 27.989333H237.909333c-15.530667 0-27.989333-12.458667-27.989333-27.989333V96.938667c0-15.530667 12.458667-27.989333 27.989333-27.989334l493.397334-1.024-38.912-39.936H239.274667c-36.352 0-65.706667 29.354667-65.706667 65.706667v835.584c0 36.352 29.354667 65.706667 65.706667 65.706667h646.826666c36.352 0 65.706667-29.354667 65.706667-65.706667V293.888l-38.912-39.936z" fill="#4191FB" p-id="21486"></path><path d="M692.394667 222.72c0 39.424 31.914667 71.338667 71.338666 71.338667h188.245334L692.394667 27.989333v194.730667z" fill="#C7E2FF" p-id="21487"></path><path d="M557.568 482.304H158.72c-50.346667 0-91.136-40.789333-91.136-91.136v-60.245333c0-50.346667 40.789333-91.136 91.136-91.136h398.848c50.346667 0 91.136 40.789333 91.136 91.136v60.245333c0 50.346667-40.789333 91.136-91.136 91.136z" fill="#4191FB" p-id="21488"></path><path d="M126.464 287.573333h129.024V320.853333h-80.725333v24.746667h74.922666v31.744h-74.922666v30.72h83.114666v35.328h-131.413333v-155.818667zM273.066667 287.573333h53.077333l27.648 47.957334 26.794667-47.957334h52.565333l-48.469333 75.434667 53.077333 80.384h-54.101333l-30.72-50.005333-30.72 50.005333h-53.76l53.76-81.237333-49.152-74.581334zM452.949333 287.573333H581.973333V320.853333h-80.725333v24.746667h74.922667v31.744h-74.922667v30.72h83.114667v35.328h-131.242667v-155.818667h-0.170667z" fill="#FFFFFF" p-id="21489"></path><path d="M552.618667 709.461333h-167.424v-112.298666l167.424-20.309334zM732.672 709.461333h-167.424V576.853333l167.424-20.48zM552.618667 852.821333l-167.424-20.309333V720.213333h167.424zM732.672 873.301333l-167.424-20.48V720.213333h167.424z" fill="#4191FB" p-id="21490"></path></svg>

Before

Width:  |  Height:  |  Size: 971 B

After

Width:  |  Height:  |  Size: 2.2 KiB

File diff suppressed because one or more lines are too long

After

Width:  |  Height:  |  Size: 26 KiB

View File

@ -40,6 +40,9 @@ Vue.use(EVueContextmenu)
Vue.use(vant.ImagePreview)
import Minder from '@/components/Minder'
Vue.use(Minder)
import APlayer from '@moefe/vue-aplayer';
Vue.use(APlayer, {
defaultCover: 'https://images.unsplash.com/photo-1511671782779-c97d3d27a1d4?ixlib=rb-1.2.1&ixid=eyJhcHBfaWQiOjEyMDd9&auto=format&fit=crop&w=200&q=60',

View File

@ -11,8 +11,10 @@ body {
text-rendering: optimizeLegibility;
//font-family: Helvetica Neue, Helvetica, PingFang SC, Hiragino Sans GB, Microsoft YaHei, Arial, sans-serif;
font-family: Menlo,Monaco,Consolas,"Courier New",monospace;;
.el-tooltip__popper .popper__arrow {
border-width: 0;
}
}
>>>::-webkit-scrollbar {
/*滚动条整体样式*/
width: 12px;

View File

@ -61,6 +61,7 @@ iconClass.set('pptx','file-ppt')
iconClass.set('drawio','file-drawio')
iconClass.set('csv','file-csv')
iconClass.set('pdf','file-pdf')
iconClass.set('mind','file-mind')
iconClass.set('zip','zip')
iconClass.set('rar','zip')
iconClass.set('iml','file-idea')

View File

@ -35,6 +35,7 @@ export default {
{ divider: true, operation: 'divider' },
{ label: '新建', operation: 'create' ,child: [
{ label: '文本', operation: 'createTextFile', iconClass: 'file-txt'},
{ label: '思维导图', operation: 'createMinderFile', iconClass: 'file-mind'},
{ label: '流程图', operation: 'createDrawioFile', iconClass: 'file-drawio'},
{ label: 'Word', operation: 'createWordFile', iconClass: 'file-word'},
{ label: 'Excel', operation: 'createExcelFile', iconClass: 'file-excel'},

View File

@ -936,7 +936,7 @@
return
}
// office文件
if (row.contentType.indexOf('office') > -1 || ['pdf','csv','drawio'].includes(row.suffix)) {
if (row.contentType.indexOf('office') > -1 || ['pdf','csv','drawio','mind'].includes(row.suffix)) {
// office文件
this.officePreviewVisible = true
this.officePreviewRow = row

10
test/testes5.html Normal file
View File

@ -0,0 +1,10 @@
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
</head>
<body>
</body>
</html>