zydx-plus 1.32.261 → 1.32.263
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package.json
CHANGED
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
import { Extension } from '@tiptap/core'
|
|
2
|
+
|
|
3
|
+
export const Contenteditable = Extension.create({
|
|
4
|
+
name: 'Contenteditable',
|
|
5
|
+
|
|
6
|
+
addOptions() {
|
|
7
|
+
return {
|
|
8
|
+
types: ['heading', 'paragraph','textStyle'],
|
|
9
|
+
}
|
|
10
|
+
},
|
|
11
|
+
|
|
12
|
+
addGlobalAttributes() {
|
|
13
|
+
return [
|
|
14
|
+
{
|
|
15
|
+
types: this.options.types,
|
|
16
|
+
attributes: {
|
|
17
|
+
cont: {
|
|
18
|
+
default: null,
|
|
19
|
+
parseHTML: element => element.getAttribute('contenteditable'),
|
|
20
|
+
renderHTML: attributes => {
|
|
21
|
+
if (!attributes.cont) {
|
|
22
|
+
return {}
|
|
23
|
+
}
|
|
24
|
+
return {
|
|
25
|
+
'contenteditable': attributes.cont,
|
|
26
|
+
}
|
|
27
|
+
},
|
|
28
|
+
},
|
|
29
|
+
},
|
|
30
|
+
},
|
|
31
|
+
]
|
|
32
|
+
}
|
|
33
|
+
})
|
|
@@ -106,6 +106,7 @@ import textStyle from '@tiptap/extension-text-style'
|
|
|
106
106
|
import {sid} from "./sign-id";
|
|
107
107
|
import {FontSize} from "./font-size";
|
|
108
108
|
import {titleId} from "./title-id";
|
|
109
|
+
import {Contenteditable} from "./contenteditable";
|
|
109
110
|
import svgs from "./level";
|
|
110
111
|
|
|
111
112
|
export default {
|
|
@@ -288,6 +289,7 @@ export default {
|
|
|
288
289
|
textStyle,
|
|
289
290
|
FontSize,
|
|
290
291
|
titleId,
|
|
292
|
+
Contenteditable,
|
|
291
293
|
Color.configure({
|
|
292
294
|
types: ['textStyle'],
|
|
293
295
|
}),
|
|
@@ -707,6 +709,13 @@ export default {
|
|
|
707
709
|
</script>
|
|
708
710
|
|
|
709
711
|
<style scoped>
|
|
712
|
+
:deep(p[data-sid="prohibit"]) {
|
|
713
|
+
-webkit-user-select: none;
|
|
714
|
+
-moz-user-select: none;
|
|
715
|
+
-ms-user-select: none;
|
|
716
|
+
user-select: none;
|
|
717
|
+
pointer-events: none;
|
|
718
|
+
}
|
|
710
719
|
.speak{
|
|
711
720
|
position: fixed;
|
|
712
721
|
top: 0;
|
|
@@ -1,162 +1,212 @@
|
|
|
1
1
|
<template>
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
</div>
|
|
6
|
-
<!-- <div class="answer">-->
|
|
7
|
-
<!-- <div class="answer-max">-->
|
|
8
|
-
<!-- <div class="answer-title">一、单选题《共2题,合计20分)</div>-->
|
|
9
|
-
<!-- <div class="answer-list">-->
|
|
10
|
-
<!-- <div class="answer-list-title">1.我们从分享时机、分享形式、分享动机、分享场量4个来聊聊了社交分享]的那些事儿在常用的杜交分享姐件中,微信 (微信好友和朋友西) 、微、QQ?</div>-->
|
|
11
|
-
<!-- <div class="answer-const">-->
|
|
12
|
-
<!-- <div class="answer-const-title">参考答案:</div>-->
|
|
13
|
-
<!-- <div class="answer-const-text">A.景4个址度来聊聊 社交分享] 的那些事儿在常用的社交分享组件中,微信《微信好友和朋友圈) 、微博、QQ</div>-->
|
|
14
|
-
<!-- </div>-->
|
|
15
|
-
<!-- </div>-->
|
|
16
|
-
<!-- </div>-->
|
|
17
|
-
<!-- </div>-->
|
|
18
|
-
<div class="word-page" :ref="'wordPage'+id" v-if="page">
|
|
19
|
-
<div class="page-cont" v-for="(item,index) in htmlArr" :key="index" :style="{'z-index': zIndex}">
|
|
20
|
-
<div class="page-cont-html" v-html="item" :style="{padding: padding?'100px':'100px 0', 'padding-top': index === 0?'10px': '100px'}"></div>
|
|
21
|
-
<div class="page-cont-num">{{ index + 1 }}/{{ htmlArr.length }}</div>
|
|
22
|
-
</div>
|
|
23
|
-
</div>
|
|
24
|
-
<div v-if="loading" class="loading-back">
|
|
25
|
-
<div class="loading-cont">
|
|
26
|
-
<div class="loadings">Loading</div>
|
|
27
|
-
</div>
|
|
28
|
-
</div>
|
|
2
|
+
<div class="word-cont">
|
|
3
|
+
<div class="word-slot" :style="page?style:{}" :ref="'test'+id">
|
|
4
|
+
<slot></slot>
|
|
29
5
|
</div>
|
|
6
|
+
<!-- <div class="answer">-->
|
|
7
|
+
<!-- <div class="answer-max">-->
|
|
8
|
+
<!-- <div class="answer-title">一、单选题《共2题,合计20分)</div>-->
|
|
9
|
+
<!-- <div class="answer-list">-->
|
|
10
|
+
<!-- <div class="answer-list-title">1.我们从分享时机、分享形式、分享动机、分享场量4个来聊聊了社交分享]的那些事儿在常用的杜交分享姐件中,微信 (微信好友和朋友西) 、微、QQ?</div>-->
|
|
11
|
+
<!-- <div class="answer-const">-->
|
|
12
|
+
<!-- <div class="answer-const-title">参考答案:</div>-->
|
|
13
|
+
<!-- <div class="answer-const-text">A.景4个址度来聊聊 社交分享] 的那些事儿在常用的社交分享组件中,微信《微信好友和朋友圈) 、微博、QQ</div>-->
|
|
14
|
+
<!-- </div>-->
|
|
15
|
+
<!-- </div>-->
|
|
16
|
+
<!-- </div>-->
|
|
17
|
+
<!-- </div>-->
|
|
18
|
+
<div class="word-page" :ref="'wordPage'+id" v-if="page">
|
|
19
|
+
<div class="page-cont" v-for="(item,index) in htmlArr" :key="index" :style="{'z-index': zIndex}">
|
|
20
|
+
<div class="page-cont-html" v-html="item"
|
|
21
|
+
:style="{padding: padding?'100px':'100px 0', 'padding-top': index === 0?'10px': '100px'}"></div>
|
|
22
|
+
<div class="page-cont-num">{{ index + 1 }}/{{ htmlArr.length }}</div>
|
|
23
|
+
</div>
|
|
24
|
+
</div>
|
|
25
|
+
<div v-if="loading" class="loading-back">
|
|
26
|
+
<div class="loading-cont">
|
|
27
|
+
<div class="loadings">Loading</div>
|
|
28
|
+
</div>
|
|
29
|
+
</div>
|
|
30
|
+
<div style="position: fixed;top: -999px;left: -999px;width: 800px;" v-html="htmlArr2" :ref="`html${id}`"></div>
|
|
31
|
+
</div>
|
|
30
32
|
</template>
|
|
31
33
|
|
|
32
34
|
<script>
|
|
33
35
|
import exportWord from 'js-export-word'
|
|
36
|
+
import {html2json, json2html} from 'html2json'
|
|
34
37
|
|
|
35
38
|
|
|
36
39
|
export default {
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
40
|
+
name: "zydx-paper",
|
|
41
|
+
data() {
|
|
42
|
+
return {
|
|
43
|
+
htmlArr: [],
|
|
44
|
+
max: 0,
|
|
45
|
+
pHeight: 0,
|
|
46
|
+
html: '',
|
|
47
|
+
loading: false,
|
|
48
|
+
id: null,
|
|
49
|
+
imgArr: [],
|
|
50
|
+
arr: [],
|
|
51
|
+
imgIndex: 0,
|
|
52
|
+
htmlArr2: ''
|
|
53
|
+
}
|
|
54
|
+
},
|
|
55
|
+
props: {
|
|
56
|
+
page: {
|
|
57
|
+
type: Boolean,
|
|
58
|
+
default: false
|
|
47
59
|
},
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
default: false
|
|
52
|
-
},
|
|
53
|
-
fileName: {
|
|
54
|
-
type: String,
|
|
55
|
-
default: '试卷'
|
|
56
|
-
},
|
|
57
|
-
padding: {
|
|
58
|
-
type: Boolean,
|
|
59
|
-
default: true
|
|
60
|
-
},
|
|
61
|
-
zIndex: {
|
|
62
|
-
type: Number,
|
|
63
|
-
default: 1
|
|
64
|
-
}
|
|
60
|
+
fileName: {
|
|
61
|
+
type: String,
|
|
62
|
+
default: '试卷'
|
|
65
63
|
},
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
64
|
+
padding: {
|
|
65
|
+
type: Boolean,
|
|
66
|
+
default: true
|
|
67
|
+
},
|
|
68
|
+
zIndex: {
|
|
69
|
+
type: Number,
|
|
70
|
+
default: 1
|
|
71
|
+
}
|
|
72
|
+
},
|
|
73
|
+
computed: {
|
|
74
|
+
style() {
|
|
75
|
+
return {
|
|
76
|
+
position: 'fixed',
|
|
77
|
+
top: '-9999px',
|
|
78
|
+
left: 0,
|
|
79
|
+
zIndex: -1,
|
|
80
|
+
opacity: 0
|
|
81
|
+
}
|
|
82
|
+
}
|
|
83
|
+
},
|
|
84
|
+
mounted() {
|
|
85
|
+
this.id = this.randomId()
|
|
86
|
+
},
|
|
87
|
+
methods: {
|
|
88
|
+
randomId() { // 生成随机id
|
|
89
|
+
const id = Math.random().toString(36).substr(2)
|
|
90
|
+
return id.replace(/[0-9]/g, '')
|
|
91
|
+
},
|
|
92
|
+
init() {
|
|
93
|
+
if (!this.page) return
|
|
94
|
+
this.htmlArr = []
|
|
95
|
+
this.pHeight = 0
|
|
96
|
+
this.html = ''
|
|
97
|
+
setTimeout(() => {
|
|
98
|
+
const data = this.$refs[`test${this.id}`].children[0].childNodes
|
|
99
|
+
this.max = (this.$refs[`wordPage${this.id}`].offsetWidth * 1.4) - 300
|
|
100
|
+
this.children(data)
|
|
101
|
+
}, 100)
|
|
102
|
+
},
|
|
103
|
+
children(data) {
|
|
104
|
+
for (let i = 0; i < data.length; i++) {
|
|
105
|
+
let mar = this.marginCal(data[i])
|
|
106
|
+
let text = data[i].offsetHeight + mar
|
|
107
|
+
if ((this.pHeight + text) > (this.htmlArr.length === 0 ? this.max : this.max - 100)) {
|
|
108
|
+
this.propsClass(data[i].children)
|
|
109
|
+
} else {
|
|
110
|
+
this.pHeight += text
|
|
111
|
+
this.html += data[i].outerHTML
|
|
112
|
+
}
|
|
113
|
+
if (i === data.length - 1) {
|
|
114
|
+
this.htmlArr.push(this.html)
|
|
115
|
+
this.pHeight = 0
|
|
116
|
+
this.html = ''
|
|
117
|
+
break
|
|
75
118
|
}
|
|
119
|
+
}
|
|
76
120
|
},
|
|
77
|
-
|
|
78
|
-
|
|
121
|
+
marginCal(data) {
|
|
122
|
+
const mar = window.getComputedStyle(data, null).margin
|
|
123
|
+
const arr = mar.split(' ')
|
|
124
|
+
if (arr.length >= 3) {
|
|
125
|
+
return parseInt(arr[0]) + parseInt(arr[2])
|
|
126
|
+
} else {
|
|
127
|
+
return parseInt(arr[0]) * 2
|
|
128
|
+
}
|
|
79
129
|
},
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
this.htmlArr = []
|
|
130
|
+
propsClass(data) {
|
|
131
|
+
for (let i = 0; i < data.length; i++) {
|
|
132
|
+
let mar = this.marginCal(data[i])
|
|
133
|
+
let text = data[i].offsetHeight + mar
|
|
134
|
+
if ((this.pHeight + text) > (this.htmlArr.length === 0 ? this.max : this.max - 100)) {
|
|
135
|
+
if (data[i].children.length === 0 || data[i].className.indexOf('paper-choice') !== -1 || data[i].localName === 'table') {
|
|
136
|
+
this.htmlArr.push(this.html)
|
|
88
137
|
this.pHeight = 0
|
|
89
138
|
this.html = ''
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
}
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
let mar = this.marginCal(data[i])
|
|
126
|
-
let text = data[i].offsetHeight + mar
|
|
127
|
-
if((this.pHeight + text) > (this.htmlArr.length === 0? this.max: this.max - 100)) {
|
|
128
|
-
if(data[i].children.length === 0 || data[i].className.indexOf('paper-choice') !== -1 || data[i].localName === 'table') {
|
|
129
|
-
this.htmlArr.push(this.html)
|
|
130
|
-
this.pHeight = 0
|
|
131
|
-
this.html = ''
|
|
132
|
-
this.pHeight += text
|
|
133
|
-
this.html += data[i].outerHTML
|
|
134
|
-
}else {
|
|
135
|
-
this.propsClass(data[i].children)
|
|
136
|
-
}
|
|
137
|
-
}else {
|
|
138
|
-
this.pHeight += text
|
|
139
|
-
this.html += data[i].outerHTML
|
|
140
|
-
}
|
|
139
|
+
this.pHeight += text
|
|
140
|
+
this.html += data[i].outerHTML
|
|
141
|
+
} else {
|
|
142
|
+
this.propsClass(data[i].children)
|
|
143
|
+
}
|
|
144
|
+
} else {
|
|
145
|
+
this.pHeight += text
|
|
146
|
+
this.html += data[i].outerHTML
|
|
147
|
+
}
|
|
148
|
+
}
|
|
149
|
+
},
|
|
150
|
+
imgBase64(data) {
|
|
151
|
+
return new Promise((res, rej) => {
|
|
152
|
+
const img = new Image()
|
|
153
|
+
img.src = data
|
|
154
|
+
img.crossOrigin = 'anonymous' // 解决跨域
|
|
155
|
+
img.onload = function () {
|
|
156
|
+
const canvas = document.createElement('canvas')
|
|
157
|
+
canvas.width = img.width
|
|
158
|
+
canvas.height = img.height
|
|
159
|
+
const ctx = canvas.getContext('2d')
|
|
160
|
+
ctx.drawImage(img, 0, 0, img.width, img.height)
|
|
161
|
+
const dataURL = canvas.toDataURL('image/png')
|
|
162
|
+
res(dataURL)
|
|
163
|
+
}
|
|
164
|
+
})
|
|
165
|
+
},
|
|
166
|
+
htmlHandle(data) {
|
|
167
|
+
if (Array.isArray(data)) {
|
|
168
|
+
for(let i=0; i< data.length; i++) {
|
|
169
|
+
if (data[i].child?.length > 0) {
|
|
170
|
+
if(data[i].tag === 'img') {
|
|
171
|
+
this.imgBase64(data[i].attr.src).then(res => {
|
|
172
|
+
data[i].attr.src = res
|
|
173
|
+
})
|
|
141
174
|
}
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
const config = {
|
|
149
|
-
addStyle: true, // 是否导出样式,默认为true,此操作会将所有样式转换成行内样式导出
|
|
150
|
-
fileName: this.fileName, // 导出文件名
|
|
151
|
-
// toImg:['.need-to-img','.bg-danger'], // 页面哪些部分需要转化成图片,例如echart图表之类
|
|
152
|
-
success() {
|
|
153
|
-
console.log('导出成功')
|
|
154
|
-
that.loading = false
|
|
155
|
-
} // 完成之后回调,一般页面篇幅比较大,时间比较长
|
|
175
|
+
this.htmlHandle(data[i].child)
|
|
176
|
+
}else {
|
|
177
|
+
if(data[i].tag === 'img') {
|
|
178
|
+
this.imgBase64(data[i].attr.src).then(res => {
|
|
179
|
+
data[i].attr.src = res
|
|
180
|
+
})
|
|
156
181
|
}
|
|
157
|
-
|
|
182
|
+
}
|
|
158
183
|
}
|
|
184
|
+
}
|
|
185
|
+
},
|
|
186
|
+
exportToWord() {
|
|
187
|
+
let that = this
|
|
188
|
+
that.loading = true
|
|
189
|
+
const wrap = that.$refs[`test${that.id}`]
|
|
190
|
+
this.imgArr = html2json(wrap.children[0].innerHTML)
|
|
191
|
+
this.htmlHandle(this.imgArr.child)
|
|
192
|
+
setTimeout(() => {
|
|
193
|
+
this.htmlArr2 = json2html(this.imgArr)
|
|
194
|
+
setTimeout(() => {
|
|
195
|
+
const wrap2 = that.$refs[`html${that.id}`]
|
|
196
|
+
const config = {
|
|
197
|
+
addStyle: true, // 是否导出样式,默认为true,此操作会将所有样式转换成行内样式导出
|
|
198
|
+
fileName: this.fileName, // 导出文件名
|
|
199
|
+
toImg:['.mindMapContainer'],
|
|
200
|
+
success() {
|
|
201
|
+
that.loading = false
|
|
202
|
+
that.htmlArr2 = ''
|
|
203
|
+
} // 完成之后回调,一般页面篇幅比较大,时间比较长
|
|
204
|
+
}
|
|
205
|
+
exportWord(wrap2, config)
|
|
206
|
+
},1000)
|
|
207
|
+
}, 500)
|
|
159
208
|
}
|
|
209
|
+
}
|
|
160
210
|
}
|
|
161
211
|
</script>
|
|
162
212
|
|