askbot-dragon 1.5.72-beta → 1.5.73-beta

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.
Files changed (87) hide show
  1. package/README.md +27 -27
  2. package/babel.config.js +6 -6
  3. package/dragon.iml +7 -7
  4. package/package.json +58 -58
  5. package/public/index.html +74 -74
  6. package/src/App.vue +31 -31
  7. package/src/api/index.js +1 -1
  8. package/src/api/mock.http +2 -2
  9. package/src/api/requestUrl.js +185 -185
  10. package/src/assets/js/AliyunlssUtil.js +92 -92
  11. package/src/assets/js/Base64Util.js +22 -22
  12. package/src/assets/js/common.js +11 -11
  13. package/src/assets/js/hammer.js +100 -89
  14. package/src/assets/js/script.js +36 -36
  15. package/src/assets/less/common.css +6773 -6773
  16. package/src/assets/less/converSationContainer/common.less +199 -192
  17. package/src/assets/less/converSationContainer/converSatonContainer.less +493 -493
  18. package/src/assets/less/iconfont.css +37 -37
  19. package/src/assets/less/ticketMessage.less +294 -294
  20. package/src/components/ActionAlertIframe.vue +112 -112
  21. package/src/components/AiGuide.vue +467 -467
  22. package/src/components/AnswerDocknowledge.vue +532 -493
  23. package/src/components/AnswerVoice.vue +285 -285
  24. package/src/components/AskIFrame.vue +15 -15
  25. package/src/components/ConversationContainer.vue +4834 -4802
  26. package/src/components/FileType.vue +86 -86
  27. package/src/components/Message.vue +27 -27
  28. package/src/components/actionSatisfaction.vue +107 -107
  29. package/src/components/actionSendToBot.vue +62 -62
  30. package/src/components/answerDissatisfaction.vue +62 -62
  31. package/src/components/answerRadio.vue +132 -132
  32. package/src/components/ask-components/DissatisfactionOptions.vue +57 -57
  33. package/src/components/ask-components/Msgloading.vue +37 -37
  34. package/src/components/ask-components/SatisfactionV2.vue +15 -15
  35. package/src/components/askVideo.vue +162 -139
  36. package/src/components/assetDetails.vue +370 -370
  37. package/src/components/assetMessage.vue +228 -228
  38. package/src/components/associationIntention.vue +349 -349
  39. package/src/components/attachmentPreview.vue +90 -90
  40. package/src/components/botActionSatisfactor.vue +68 -68
  41. package/src/components/chatContent.vue +513 -513
  42. package/src/components/feedBack.vue +136 -136
  43. package/src/components/fielListView.vue +351 -351
  44. package/src/components/file/AliyunOssComponents.vue +108 -108
  45. package/src/components/formTemplate.vue +3604 -3607
  46. package/src/components/kkview.vue +1138 -1138
  47. package/src/components/loadingProcess.vue +164 -164
  48. package/src/components/message/ActionAlertIframe.vue +112 -112
  49. package/src/components/message/ShopMessage.vue +164 -164
  50. package/src/components/message/TextMessage.vue +924 -924
  51. package/src/components/message/TicketMessage.vue +201 -201
  52. package/src/components/message/swiper/index.js +4 -4
  53. package/src/components/message/swiper/ticketSwiper.vue +503 -503
  54. package/src/components/message/swiper/ticketSwiperItem.vue +61 -61
  55. package/src/components/msgLoading.vue +231 -231
  56. package/src/components/myPopup.vue +70 -70
  57. package/src/components/newPdfPosition.vue +878 -0
  58. package/src/components/pdfPosition.vue +1521 -1322
  59. package/src/components/popup.vue +227 -227
  60. package/src/components/previewDoc.vue +242 -242
  61. package/src/components/previewPdf.vue +315 -302
  62. package/src/components/receiverMessagePlatform.vue +65 -65
  63. package/src/components/recommend.vue +80 -80
  64. package/src/components/selector/hOption.vue +20 -20
  65. package/src/components/selector/hSelector.vue +199 -199
  66. package/src/components/selector/hWrapper.vue +216 -216
  67. package/src/components/senderMessagePlatform.vue +50 -50
  68. package/src/components/source/BotMessage.vue +24 -24
  69. package/src/components/source/CustomMessage.vue +24 -24
  70. package/src/components/test.vue +260 -260
  71. package/src/components/tree.vue +294 -294
  72. package/src/components/utils/AliyunIssUtil.js +81 -81
  73. package/src/components/utils/ckeditor.js +174 -174
  74. package/src/components/utils/ckeditorImageUpload/command.js +109 -109
  75. package/src/components/utils/ckeditorImageUpload/editing.js +11 -11
  76. package/src/components/utils/ckeditorImageUpload/plugin-image.js +11 -11
  77. package/src/components/utils/ckeditorImageUpload/toolbar-ui.js +40 -40
  78. package/src/components/utils/ckeditorfileUpload/common.js +180 -180
  79. package/src/components/utils/ckeditorfileUpload/editing.js +11 -11
  80. package/src/components/utils/ckeditorfileUpload/plugin_file.js +11 -11
  81. package/src/components/utils/ckeditorfileUpload/toolbar_ui.js +34 -34
  82. package/src/components/utils/format_date.js +25 -25
  83. package/src/components/utils/index.js +6 -6
  84. package/src/components/utils/math_utils.js +29 -29
  85. package/src/components/voiceComponent.vue +119 -119
  86. package/src/main.js +60 -60
  87. package/vue.config.js +55 -55
@@ -1,1323 +1,1522 @@
1
- <template>
2
- <div class="pdf_view" ref="pdfView" @scroll="pdfScroll" :style="{
3
- marginTop: isPC ? '50px' : '',
4
- marginBottom: tagIds.length > 1 ? '60px' : '0px',
5
- height: setHeight
6
- }">
7
- <div class="change_scale" v-if="isPC">
8
- <section @click="changeScale('reduce')">
9
- <i class="el-icon-minus"></i>
10
- </section>
11
- <el-divider direction="vertical"></el-divider>
12
- <section @click="changeScale('zoom')">
13
- <i class="el-icon-plus"></i>
14
- </section>
15
- <el-select size="small" v-model="handScale" @change="changeScale" placeholder="请选择">
16
- <el-option v-for="item in scaleList" :key="item.value" :label="item.label" :value="item.value">
17
- </el-option>
18
- </el-select>
19
- </div>
20
- <div class="btn_footer" v-if="tagIds.length > 1 && !isPC">
21
- <div class="prev" @click="prev">上一段</div>
22
- <div class="next" @click="next">下一段</div>
23
- </div>
24
- <div id="pagination" v-if="tagIds.length > 1 && isPC">
25
- <el-pagination :current-page="currentPage + 1" @current-change="currentChange" @prev-click="prev"
26
- @next-click="next" layout="slot, prev, pager, next" :page-size="1" :total="tagIds.length">
27
- <span class="total-class">答案由{{ tagIds.length }}段内容生成</span>
28
- </el-pagination>
29
- </div>
30
- </div>
31
- </template>
32
-
33
- <script>
34
- import _ from 'lodash'
35
- // import * as pdfjsLib from 'pdfjs-dist'
36
- // pdfjsLib.GlobalWorkerOptions.workerSrc = 'pdfjs-dist/build/pdf.worker';
37
- // import { TextLayerBuilder } from "pdfjs-dist/web/pdf_viewer";
38
- // EventBus pdf_viewer 支持绑定自定义事件,一版不做
39
- // import 'pdfjs-dist/web/pdf_viewer.css'
40
- /* eslint-disable */
41
- const pdfjsLib = window['pdfjsLib']
42
- if (pdfjsLib) {
43
- pdfjsLib.GlobalWorkerOptions.workerSrc = window['pdfjs-dist/build/pdf.worker']
44
- // 'pdfjs-dist/build/pdf.worker';
45
- }
46
- const { TextLayerBuilder } = window['pdfjs-dist/web/pdf_viewer']
47
- // import { zoomElement } from '../assets/js/hammer'
48
- export default {
49
- name: 'pdfView',
50
- props: ['tagIds', 'isMessageRecord'],
51
- data () {
52
- return {
53
- url: '',
54
- pages: [],
55
- pageLoadStatus: {
56
- WAIT: 0,
57
- LOADED: 1,
58
- },
59
- scale: 1,
60
- rotation: 0,
61
- pageSize: {},
62
- PAGE_INTVERVAL: 15,
63
- SLICE_COUNT: 5,
64
- contentView: null,
65
- fisrtLoad: true,
66
- TextLayerBuilder: null,
67
- totalPageCount: 0,
68
- identifyTextPostion: {
69
- top: 0,
70
- left: 0,
71
- width: 100,
72
- height: 0,
73
- page: 1,
74
- pageHeight: 0,
75
- pageWidth: 0,
76
- extractInfo: {},
77
- currentPageAllLine: []
78
- },
79
- currentPageAllLine: [],
80
- pdfUrl: '',
81
- cachePdf: [],
82
- newViewer: null,
83
- currentPage: 0,
84
- changetoolbar: false,
85
- allTr: [],
86
- preViewType: 'pdf',
87
- displacement: {
88
- pageX: 0,
89
- pageY: 0,
90
- moveable: false,
91
- pageX2: 0,
92
- pageY2: 0,
93
- originScale: 1,
94
- },
95
- isTouchMoved: false,
96
- transformSalce: null,
97
- isPC: false,
98
- handScale: 'auto',
99
- scaleList: [
100
- {
101
- label: '自动缩放',
102
- value: 'auto'
103
- },
104
- {
105
- label: '实际比例',
106
- value: 'reality'
107
- },
108
- {
109
- label: '100%',
110
- value: 1
111
- },
112
- {
113
- label: '120%',
114
- value: 1.2
115
- },
116
- {
117
- label: '150%',
118
- value: 1.5
119
- },
120
- {
121
- label: '170%',
122
- value: 1.7
123
- }
124
- ,
125
- {
126
- label: '200%',
127
- value: 2
128
- }
129
- ],
130
- scrollTop: 0,
131
- scrollLeft: 0
132
- }
133
- },
134
- methods: {
135
- getpdfResloutePage (pdfResloute) {
136
- // 根据当前页面宽度设置缩放比例
137
- // this.scale = Math.round(this.$refs.pdfView.clientWidth / pdfResloute.pageWidth * 100) / 100
138
- if (this.isMessageRecord) {
139
- this.scale = Math.round(this.$refs.pdfView.clientWidth / pdfResloute.pageWidth * 100) / 100
140
- } else {
141
- this.scale = 2
142
- }
143
- // 从后端获取到当前分片后所有的pdf页码,初始化数组,数组下{} 对应每页pdf文件
144
- this.pdfUrl = pdfResloute.publicPageFileUrl.substring(0, pdfResloute.publicPageFileUrl.lastIndexOf('/') + 1)
145
- this.initPages(pdfResloute.total)
146
- // 定位功能,加载对应页码位置
147
- this.loadPdfData(pdfResloute.page)
148
- },
149
- async loadPdfData (loadPage) {
150
- if (this.pages[loadPage - 1] && ((this.pages[loadPage - 1].dom && this.pages[loadPage - 1].dom.children.length > 0) || this.pages[loadPage - 1].loadStatus)) {
151
- return
152
- } else {
153
- if (this.changetoolbar) {
154
- this.$nextTick(() => {
155
- this.renderHighlights()
156
- })
157
- this.changetoolbar = false
158
- }
159
- }
160
- // 记录开始缓存的状态
161
- // pdfjsLib.GlobalWorkerOptions.workerSrc = require("pdfjs-dist/legacy/build/pdf.worker.entry.js");
162
- // 拿到第一个分片
163
- const { startPage, url } = await this.fetchPdfFragment(loadPage);
164
- let loadingTask = pdfjsLib.getDocument(url)
165
- loadingTask.promise.then(async (pdfDoc) => {
166
- // 将已经下载的分片保存到 pages 数组中
167
- // for (let i = 0; i < pdfDoc.numPages; i += 1) {
168
- // const pageIndex = startPage + i;
169
- // const page = this.pages[pageIndex - 1];
170
- // // // 不在缓存列表内,重新获取本页pdf
171
- // // if (page.loadStatus !== this.pageLoadStatus.LOADED) {
172
-
173
- // // } else {
174
- // // if (this.changetoolbar) {
175
- // // this.$nextTick(() => {
176
- // // this.renderHighlights()
177
- // // })
178
- // // this.changetoolbar = false
179
- // // }
180
- // // }
181
- // }
182
- const page = this.pages[loadPage - 1]
183
- await pdfDoc.getPage(1).then(async (pdfPage) => {
184
- this.pages[loadPage - 1].loadStatus = true
185
- this.pages[loadPage - 1].pdfPage = pdfPage;
186
- // 通知可以进行渲染了
187
- await this.startRenderPages(pdfPage, page, loadPage)
188
- });
189
- });
190
- },
191
- initPages (totalPage) {
192
- // const pages = [];
193
- this.totalPageCount = totalPage
194
- for (let i = 0; i < totalPage; i += 1) {
195
- this.pages.push({
196
- pageNo: i + 1,
197
- loadStatus: false,
198
- pdfPage: null,
199
- dom: null
200
- });
201
- }
202
- },
203
- async fetchPdfFragment (pageIndex) {
204
- // 置换加签后的文件地址。
205
- let obj = {}
206
- await this.$http.post(
207
- '/knowledge-api/temporary-certificate/or-origin?expired=30',
208
- this.pdfUrl + pageIndex + '.pdf',
209
- {
210
- headers: {
211
- "Content-Type": "application/json",
212
- },
213
- }).then(async res => {
214
- if (res.bodyText) {
215
- // 最后返回一个 包含这4个参数的对象
216
- obj = await {
217
- "startPage": pageIndex, // 分片的开始页码
218
- "endPage": pageIndex + 5, // 分片结束页码
219
- "totalPage": this.totalPageCount, // pdf 总页数
220
- "url": res.bodyText // 分片内容下载地址
221
- }
222
- }
223
- if (res.data) {
224
- // 最后返回一个 包含这4个参数的对象
225
- obj = await {
226
- "startPage": pageIndex, // 分片的开始页码
227
- "endPage": pageIndex + 5, // 分片结束页码
228
- "totalPage": this.totalPageCount, // pdf 总页数
229
- "url": res.data // 分片内容下载地址
230
- }
231
- }
232
- })
233
- return obj
234
- },
235
- startRenderPages (pdfPage, page, pageIndex) {
236
- if (Object.keys(this.pageSize).length == 0) {
237
- const viewport = pdfPage.getViewport({
238
- scale: this.scale, // 缩放的比例
239
- rotation: this.rotation, // 旋转的角度
240
- });
241
- // 记录pdf页面高度
242
- const pageSize = {
243
- width: viewport.width,
244
- height: viewport.height,
245
- }
246
- this.pageSize = pageSize
247
- // 创建内容绘制区,并设置大小
248
- if (this.$refs.pdfView.clientWidth / this.pageSize.width >= 1 || this.isMessageRecord) {
249
- this.contentView.style.width = `${pageSize.width - 10}px`;
250
- this.contentView.style.height = `${(this.totalPageCount * (pageSize.height + this.PAGE_INTVERVAL)) + this.PAGE_INTVERVAL}px`;
251
- } else {
252
- this.transformSalce = this.$refs.pdfView.clientWidth / this.pageSize.width
253
- this.contentView.style.width = `${pageSize.width * this.transformSalce - 10}px`;
254
- this.contentView.style.height = `${(this.totalPageCount * (pageSize.height * (this.transformSalce) + this.PAGE_INTVERVAL)) + this.PAGE_INTVERVAL}px`;
255
- }
256
- this.contentView.style.margin = '0 auto 0'
257
- this.contentView.style.position = 'relative'
258
- this.contentView.style.paddingBottom = '60px'
259
- // contentView.style.overflowY = 'auto'
260
- this.$refs.pdfView.appendChild(this.contentView);
261
- }
262
- this.renderPages(pageIndex)
263
- },
264
- // 渲染需要展示的页面,不需展示的页码将其清除
265
- renderPages (pageIndex) {
266
- const pagesToRender = this.getRenderScope(pageIndex);
267
- for (const i of this.pages) {
268
- if (pagesToRender.some(p => { return p.pageNo == i.pageNo })) {
269
- if (i.loadStatus === true) {
270
- this.renderPageContent(i, i.pageNo)
271
- } else {
272
- this.renderPageLoading(i, i.pageNo)
273
- }
274
- } else {
275
- this.clearPage(i);
276
- }
277
- }
278
-
279
- },
280
- async renderPageContent (page, pageIndex) {
281
- const { pdfPage, pageNo, dom } = page;
282
- // dom 元素已存在,无须重新渲染,直接返回
283
- if ((dom && dom.children.length != 0) || page.loading) {
284
- return;
285
- }
286
- page.loading = true
287
- const viewport = pdfPage.getViewport({
288
- scale: this.scale,
289
- rotation: this.rotation,
290
- });
291
- // 创建新的canvas
292
- const canvas = document.createElement('canvas');
293
- const context = canvas.getContext('2d');
294
- // canvas.getContext('2d');
295
- canvas.height = this.pageSize.height;
296
- canvas.width = this.pageSize.width;
297
- canvas.style.position = 'relative'
298
- canvas.style.top = -3 + 'px'
299
- // 创建渲染的dom
300
- const pageDom = document.createElement('div');
301
- pageDom.style.position = 'absolute';
302
- pageDom.style.top = `${((pageNo - 1) * (this.pageSize.height + this.PAGE_INTVERVAL)) + this.PAGE_INTVERVAL}px`;
303
- pageDom.style.width = `${this.pageSize.width}px`;
304
- pageDom.style.height = `${this.pageSize.height}px`;
305
- pageDom.setAttribute('data-id', 'page' + pageNo)
306
- pageDom.appendChild(canvas);
307
- // 渲染内容
308
- let renderContext = {
309
- canvasContext: context,
310
- viewport: viewport,
311
- }
312
- await pdfPage.render(renderContext).promise.then(() => {
313
- return pdfPage.getTextContent()
314
- }).then(async (textContent) => {
315
- const textLayerDiv = document.createElement('div');
316
- textLayerDiv.setAttribute('class', 'textLayer');
317
- // 将文本图层div添加至每页pdf的div中
318
- // 创建新的TextLayerBuilder实例
319
- let textLayer = new TextLayerBuilder({
320
- textLayerDiv: textLayerDiv,
321
- pageIndex: pdfPage._pageIndex,
322
- viewport: viewport,
323
- });
324
- let findPage = this.currentPageAllLine.find(l => { return l.page == pageIndex })
325
- let rectdomTop = 0
326
- if (findPage) {
327
- let AllLines = findPage.allLines
328
- // setTimeout(() => {
329
- if (AllLines.length > 0) {
330
- for (let j = 0; j < AllLines.length; j++) {
331
- let lines = AllLines[j].lines
332
- let rectdom = document.createElement('div')
333
- rectdom.setAttribute('react-count', AllLines[j].pageCount);
334
- rectdom.style.position = 'absolute';
335
- rectdom.style.top = 0
336
- rectdom.style.left = 0
337
- rectdom.classList.add('rectdom')
338
- for (let index = 0; index < lines.length; index++) {
339
- if (!/^\s+$/g.test(lines[index].content)) {
340
- let postionArr = lines[index].location
341
- let div = document.createElement('div')
342
- div.style.position = 'absolute';
343
- div.style.left = postionArr[0] * this.scale + 'px',
344
- // 后端返回的坐标有基线对齐的问题,top 值是后端算好(基线top - 文字高度),在此加上文字高度的 1/9 (大致比例)为实际展示出文字的top值
345
- div.style.top = postionArr[1] * this.scale + 'px'
346
- div.style.height = postionArr[3] * this.scale + 'px';
347
- div.style.width = postionArr[2] * this.scale + 'px'
348
- div.style.backgroundColor = 'rgba(54, 106, 255, 0.3)'
349
- div.classList.add('lineHeight')
350
- rectdom.appendChild(div)
351
- if (index == 0 && j == 0) {
352
- if (this.transformSalce !== null) {
353
- rectdomTop = postionArr[1] * this.scale * this.transformSalce
354
- } else {
355
- rectdomTop = postionArr[1] * this.scale
356
- }
357
- // if(this.isPC) {
358
- // rectdomTop = rectdomTop - 50 < 0 ? 0 : rectdomTop - 50
359
- // }
360
- }
361
- }
362
- }
363
- if (rectdom.children.length > 0) {
364
- pageDom.appendChild(rectdom)
365
- }
366
- }
367
- }
368
- }
369
- textLayer.setTextContent(textContent);
370
- textLayer.render()
371
- pageDom.appendChild(textLayerDiv);
372
-
373
- let backgroundDom = document.getElementById('backgroundLoad' + pageNo)
374
- if (backgroundDom) {
375
- this.contentView.removeChild(backgroundDom);
376
- }
377
- page.dom = await pageDom;
378
- page.loading = false
379
- this.contentView.appendChild(pageDom);
380
- if (this.transformSalce !== null) {
381
- this.contentView.style.transform = `scale(${this.transformSalce}, ${this.transformSalce})`
382
- }
383
- if (this.changetoolbar) {
384
- setTimeout(() => {
385
- this.renderHighlights()
386
- this.changetoolbar = false
387
- }, 500)
388
- }
389
- if (this.fisrtLoad) {
390
- setTimeout(() => {
391
- let pageoffsetHeight = 0
392
- if (this.transformSalce !== null) {
393
- pageoffsetHeight = (this.pageSize.height + this.PAGE_INTVERVAL) * this.transformSalce
394
- } else {
395
- pageoffsetHeight = (this.pageSize.height + this.PAGE_INTVERVAL)
396
- }
397
- if (this.$refs.pdfView.clientHeight - pageoffsetHeight > 0 && pageIndex == 1) {
398
- const height = this.$refs.pdfView.clientHeight;
399
- let startNum = 0
400
- let endNum = 0
401
- if (this.transformSalce !== null) {
402
- startNum = Math.ceil(this.$refs.pdfView.scrollTop / ((this.pageSize.height + this.PAGE_INTVERVAL) * this.transformSalce))
403
- endNum = startNum + Math.ceil(height / ((this.pageSize.height + this.PAGE_INTVERVAL) * this.transformSalce))
404
- } else {
405
- startNum = Math.ceil(this.$refs.pdfView.scrollTop / (this.pageSize.height + this.PAGE_INTVERVAL))
406
- endNum = startNum + Math.ceil(height / (this.pageSize.height + this.PAGE_INTVERVAL))
407
-
408
- }
409
- for (let pageIndex = startNum; pageIndex <= endNum; pageIndex++) {
410
- if (pageIndex > 0 && pageIndex <= this.pages.length) {
411
- this.loadPdfData(pageIndex)
412
- }
413
- }
414
- }
415
- if (this.$refs.pdfView.scrollTop == Math.floor((pageNo - 1) * pageoffsetHeight)) {
416
- this.$refs.pdfView.scrollTop = rectdomTop
417
- this.fisrtLoad = false
418
- } else {
419
- this.$refs.pdfView.scrollTop = `${((pageNo - 1) * pageoffsetHeight) + rectdomTop - this.PAGE_INTVERVAL}`
420
- this.fisrtLoad = false
421
- }
422
- this.renderHighlights()
423
- // zoomElement(this.contentView)
424
- }, 100)
425
- }
426
- })
427
- },
428
- // 监听容器的滚动事件,触发 scrollPdf 方法
429
- // 这里加了防抖保证不会一次产生过多请求
430
- debounceScrollPdf: _.debounce(function (e, that) {
431
- if (this.fisrtLoad) {
432
- this.fisrtLoad = false
433
- return
434
- }
435
- const scrollTop = e.target.scrollTop;
436
- const height = e.target.clientHeight;
437
- let startNum = 0
438
- let endNum = 0
439
- if (this.transformSalce !== null) {
440
- startNum = Math.ceil(scrollTop / ((that.pageSize.height + that.PAGE_INTVERVAL) * this.transformSalce))
441
- endNum = startNum + Math.ceil(height / ((that.pageSize.height + that.PAGE_INTVERVAL) * this.transformSalce))
442
- } else {
443
- startNum = Math.ceil(scrollTop / (that.pageSize.height + that.PAGE_INTVERVAL))
444
- endNum = startNum + Math.ceil(height / (that.pageSize.height + that.PAGE_INTVERVAL))
445
- }
446
- for (let pageIndex = startNum; pageIndex < endNum; pageIndex++) {
447
- if (pageIndex > 0 && pageIndex < that.pages.length) {
448
- that.loadPdfData(pageIndex)
449
- }
450
- }
451
- }, 200),
452
- directScrolling (e, that) {
453
- if (this.fisrtLoad) {
454
- this.fisrtLoad = false
455
- return
456
- }
457
- const scrollTop = e.target.scrollTop;
458
- const height = e.target.clientHeight;
459
- // 根据内容可视区域中心点计算页码, 没有滚动时,指向第一页
460
- const pageIndex = scrollTop > 0 ?
461
- Math.ceil((scrollTop + (height / 2)) / (that.pageSize.height + that.PAGE_INTVERVAL)) :
462
- 1;
463
- this.loadPdfData(pageIndex)
464
- },
465
- pdfScroll (e) {
466
- if (this.preViewType !== 'pdf' || this.isTouchMoved) {
467
- return
468
- }
469
- if (this.scrollLeft != e.target.scrollLeft) {
470
- this.scrollLeft = e.target.scrollLeft
471
- }
472
- if (this.scrollTop != e.target.scrollTop) {
473
- this.scrollTop = e.target.scrollTop
474
- this.debounceScrollPdf(e, this)
475
- }
476
- },
477
- // 分片每次只做一次处理,所以不考虑多片情况
478
- loadBefore (pageIndex) {
479
- this.loadPdfData(pageIndex)
480
- },
481
- loadAfter (pageIndex) {
482
- this.loadPdfData(pageIndex)
483
- },
484
- // 首先我们获取到需要渲染的范围
485
- // 根据当前的可视范围内的页码,我们前后只保留 8
486
- getRenderScope (pageIndex) {
487
- const pagesToRender = [];
488
- let i = pageIndex - 1;
489
- let j = pageIndex + 1;
490
- // pageIndex - 1 表示当前页码数 对应的下标位置
491
- pagesToRender.push(this.pages[pageIndex - 1]);
492
- while (pagesToRender.length < 8 && pagesToRender.length < this.pages.length) {
493
- if (i > 0) {
494
- pagesToRender.push(this.pages[i - 1]);
495
- i -= 1;
496
- }
497
- if (pagesToRender.length >= 8) {
498
- break;
499
- }
500
- if (j <= this.pages.length) {
501
- pagesToRender.push(this.pages[j - 1]);
502
- j += 1;
503
- }
504
- }
505
- // for (let index = 0; index < array.length; index++) {
506
- // const element = array[index];
507
-
508
- // }
509
- return pagesToRender;
510
- },
511
-
512
- // 清除页面 dom
513
- clearPage (page) {
514
- if (this.contentView.contains(page.dom) && page.dom) {
515
- this.contentView.removeChild(page.dom);
516
- page.loadStatus = false
517
- page.loading = false
518
- page.dom = undefined;
519
- }
520
- },
521
- // 页面正在下载时渲染loading视图
522
- renderPageLoading (page) {
523
- const { pageNo, dom } = page;
524
- if (dom && dom.children.length != 0) {
525
- return;
526
- }
527
- let backgroundDom = document.getElementById('backgroundLoad' + pageNo)
528
- if (this.contentView.contains(backgroundDom)) {
529
- return
530
- }
531
- const pageDom = document.createElement('div');
532
- pageDom.style.width = `${this.pageSize.width}px`;
533
- pageDom.style.height = `${this.pageSize.height}px`;
534
- pageDom.style.position = 'absolute';
535
- pageDom.style.top = `${((pageNo - 1) * (this.pageSize.height + this.PAGE_INTVERVAL)) + this.PAGE_INTVERVAL
536
- }px`;
537
- pageDom.style.backgroundImage = `url('https://guoranopen-zjk.oss-cn-zhangjiakou.aliyuncs.com/cdn-common/images/loading.gif')`
538
- pageDom.style.backgroundPosition = 'center'
539
- pageDom.style.backgroundRepeat = 'no-repeat'
540
- pageDom.style.backgroundColor = '#FFF'
541
- pageDom.setAttribute('id', 'backgroundLoad' + pageNo)
542
- page.dom = pageDom;
543
- this.contentView.appendChild(pageDom);
544
- },
545
- prev () {
546
- this.currentPage--
547
- if (this.currentPage < 0) {
548
- this.currentPage = 0
549
- if (!this.isPC) {
550
- this.$toast({
551
- message: '当前已经是第一段了',
552
- duration: 2000,
553
- })
554
- return
555
- }
556
- }
557
- if (this.preViewType == 'pdf') {
558
- this.scrollToUplaodePage(this.currentPage)
559
- } else {
560
- this.scrollToExcalTop(this.currentPage)
561
- }
562
- // this.getpdfResloutePage(this.cachePdf[this.currentPage - 1])
563
- },
564
- next () {
565
- this.currentPage++
566
- if (this.currentPage >= this.tagIds.length) {
567
- this.currentPage = this.tagIds.length - 1
568
- if (!this.isPC) {
569
- this.$toast({
570
- message: '当前已经是最后一段了',
571
- duration: 2000,
572
- })
573
- return
574
- }
575
- }
576
- if (this.preViewType == 'pdf') {
577
- this.scrollToUplaodePage(this.currentPage)
578
- } else {
579
- this.scrollToExcalTop(this.currentPage)
580
- }
581
- },
582
- currentChange (value) {
583
- this.currentPage = value - 1
584
- if (this.preViewType == 'pdf') {
585
- this.scrollToUplaodePage(this.currentPage)
586
- } else {
587
- this.scrollToExcalTop(this.currentPage)
588
- }
589
- },
590
- scrollToUplaodePage (currentPage) {
591
- this.changetoolbar = true
592
- if (this.preViewType !== 'pdf') {
593
- return
594
- }
595
-
596
- let pdfResloute = this.cachePdf[currentPage]
597
- this.identifyTextPostion.extractInfo = pdfResloute.extractInfo
598
- this.identifyTextPostion.left = pdfResloute.extractInfo.location[0]
599
- this.identifyTextPostion.top = pdfResloute.extractInfo.location[1]
600
- this.identifyTextPostion.width = pdfResloute.extractInfo.location[2]
601
- this.identifyTextPostion.height = pdfResloute.extractInfo.location[3]
602
- this.identifyTextPostion.page = pdfResloute.page
603
- this.identifyTextPostion.pageHeight = pdfResloute.pageHeight
604
- this.identifyTextPostion.pageWidth = pdfResloute.pageWidth
605
- // 在当前段落在最后一页pdf时,根据计算的高度并不能触发滚动,在此执行重新渲染方法,非次情况会执行两次,待优化
606
- this.$nextTick(() => {
607
- this.renderHighlights()
608
- })
609
- if (this.transformSalce !== null) {
610
- this.$refs.pdfView.scrollTop = `${((pdfResloute.page - 1) * (this.pageSize.height + this.PAGE_INTVERVAL) * this.transformSalce) + (this.identifyTextPostion.top * this.scale * this.transformSalce)}`
611
- } else {
612
- this.$refs.pdfView.scrollTop = `${((pdfResloute.page - 1) * (this.pageSize.height + this.PAGE_INTVERVAL)) + (this.identifyTextPostion.top * this.scale * this.transformSalce)}`
613
- }
614
- },
615
- scrollToExcalTop (currentPage) {
616
- for (let index = 0; index < this.allTr.length; index++) {
617
- if (index == currentPage) {
618
- Array.from(this.allTr[index].children).forEach(item => {
619
- item.style.background = 'rgba(255, 136, 0, 0.6)'
620
- item.classList.add('animation')
621
- setTimeout(() => {
622
- item.classList.remove('animation')
623
- }, 4000)
624
- })
625
- // getBoundingClientRect().top 当前元素距离屏幕顶部的高度 + 弹窗header 高度
626
- if (!this.isPC) {
627
- let top = this.allTr[index].getBoundingClientRect().top - this.$refs.pdfView.getBoundingClientRect().top
628
- this.$refs.pdfView.scrollTop = top
629
- } else {
630
- let top = this.allTr[index].getBoundingClientRect().top
631
- this.$refs.pdfView.scrollTop = top - 50
632
- }
633
- } else {
634
- Array.from(this.allTr[index].children).forEach(item => {
635
- item.style.background = 'rgba(54, 106, 255, 0.6)'
636
- item.classList.remove('animation')
637
- })
638
- }
639
- }
640
- },
641
- // pdf是否需要重新渲染高亮位置
642
- renderHighlights () {
643
- let lineHeightDom = Array.from(document.getElementsByClassName('rectdom'))
644
- if (lineHeightDom) {
645
- lineHeightDom.forEach((d) => {
646
- for (let i = 0; i < d.children.length; i++) {
647
- if (d.getAttribute('react-count') == this.currentPage) {
648
- d.children[i].style.backgroundColor = 'rgba(255, 136, 0, 0.3)'
649
- d.children[i].classList.add('animation')
650
- setTimeout(() => {
651
- d.children[i].classList.remove('animation')
652
- }, 4000)
653
- } else {
654
- d.children[i].style.backgroundColor = 'rgba(54, 106, 255, 0.3)'
655
- d.children[i].classList.remove('animation')
656
- }
657
- }
658
- })
659
- }
660
- },
661
- displayHiglight (pageIndex) {
662
- let lineHeightDom = Array.from(document.getElementsByClassName('rectdom'))
663
- if (lineHeightDom) {
664
- lineHeightDom.forEach((d) => {
665
- if (d.getAttribute('page-index') == pageIndex) {
666
- d.style.display = 'none'
667
- }
668
- })
669
- }
670
- },
671
- // 前端暂时缓存多页
672
- autoLoadMore (pageIndex) {
673
- let pdfResloute = this.cachePdf.find(cache => {
674
- return cache.page == pageIndex
675
- })
676
- if (pdfResloute) {
677
- this.getpdfResloutePage(pdfResloute)
678
- } else {
679
- this.loadPdfData(pageIndex)
680
- }
681
- },
682
- setPageAllLine (arr) {
683
- this.currentPageAllLine = []
684
- arr.forEach((item, index) => {
685
- let i = this.currentPageAllLine.findIndex(l => { return l.page && l.page == item.page })
686
- if (i != -1) {
687
- // this.currentPageAllLine[i].allLines.lines.push(item.extractInfo.lines)
688
- this.currentPageAllLine[i].allLines.push({
689
- pageCount: index,
690
- lines: item.extractInfo.lines
691
- })
692
- } else {
693
- this.currentPageAllLine.push({
694
- page: item.page,
695
- allLines: [{
696
- pageCount: index,
697
- lines: item.extractInfo.lines
698
- }],
699
- })
700
- }
701
- })
702
- },
703
- openTouch () {
704
- // this.$nextTick()将回调延迟到下次 DOM 更新循环之后执行
705
- let that = this;
706
- this.$nextTick(() => {
707
- // setInterval(() => {
708
- // this.scale = this.scale + 0.1
709
- // that.pages.forEach((item, index) =>{
710
- // if(item.dom) {
711
- // item.dom.children.forEach( childDom =>{
712
- // if(childDom.getAttribute('react-count')) {
713
- // childDom.style.transform = "scale(" + this.scale + ")";
714
- // childDom.style.transformOrigin = "0px 0px 0px";
715
- // } else {
716
- // item.dom = null
717
- // this.startRenderPages(item.pdfPage, null, index)
718
- // }
719
- // } )
720
- // }
721
- // })
722
- // }, 100);
723
- // 获取放大或缩小的区域DOM
724
- let matrix_box = this.contentView
725
- matrix_box.addEventListener("touchstart", function (event) {
726
- this.isTouchMoved = true
727
- let touches = event.touches;
728
- let events = touches[0];
729
- let events2 = touches[1];
730
-
731
- // event.preventDefault();
732
-
733
- // 第一个触摸点的坐标
734
- that.displacement.pageX = events.pageX;
735
- that.displacement.pageY = events.pageY;
736
-
737
- that.displacement.moveable = true;
738
-
739
- if (events2) {
740
- that.displacement.pageX2 = events2.pageX;
741
- that.displacement.pageY2 = events2.pageY;
742
- }
743
-
744
- that.displacement.originScale = this.scale || 1;
745
- });
746
- document.addEventListener("touchmove", function (event) {
747
- if (!that.displacement.moveable) {
748
- return;
749
- }
750
- // event.preventDefault();
751
- let touches = event.touches;
752
- let events = touches[0];
753
- let events2 = touches[1];
754
- // 双指移动
755
- if (events2) {
756
- // 第2个指头坐标在touchmove时候获取
757
- if (!that.displacement.pageX2) {
758
- that.displacement.pageX2 = events2.pageX;
759
- }
760
- if (!that.displacement.pageY2) {
761
- that.displacement.pageY2 = events2.pageY;
762
- }
763
- // 双指缩放比例计算
764
- let zoom = that.getDistance({
765
- x: events.pageX,
766
- y: events.pageY
767
- },
768
- {
769
- x: events2.pageX,
770
- y: events2.pageY
771
- }
772
- ) / that.getDistance(
773
- {
774
- x: that.displacement.pageX,
775
- y: that.displacement.pageY
776
- },
777
- {
778
- x: that.displacement.pageX2,
779
- y: that.displacement.pageY2
780
- }
781
- );
782
- // 应用在元素上的缩放比例
783
- let newScale = that.displacement.originScale * zoom;
784
- // 最大缩放比例限制
785
- if (newScale > 2) {
786
- newScale = 2;
787
- }
788
- // 最大缩放比例限制
789
- if (newScale < 1) {
790
- newScale = 1;
791
- }
792
- // 记住使用的缩放值
793
- that.displacement.scale = newScale;
794
- // console.log(newScale);
795
- matrix_box.style.transform = "scale(" + newScale + ")";
796
- // 设置旋转元素的基点位置
797
- matrix_box.style.transformOrigin = "0px 0px 0px";
798
- }
799
- }, { passive: false });
800
- document.addEventListener('touchend', function () {
801
- that.isTouchMoved = false
802
- }, { passive: false })
803
- });
804
- },
805
- getDistance (start, stop) {
806
- // Math.hypot()计算参数的平方根
807
- return Math.hypot(stop.x - start.x, stop.y - start.y);
808
- },
809
- setupCanvas (canvas, width, height) {
810
- const dpr = 1;
811
- // const rect = canvas.getBoundingClientRect();
812
- canvas.width = width
813
- canvas.height = height
814
- const ctx = canvas.getContext('2d');
815
- ctx?.scale(dpr, dpr);
816
- return ctx;
817
- },
818
- changeScale (value) {
819
- if (value == 'zoom') {
820
- this.handScale = 'auto'
821
- this.transformSalce = (this.transformSalce + 0.2).toFixed(1)
822
- } else if (value == 'reduce') {
823
- if ((this.transformSalce - 0.2).toFixed(1) <= 0) {
824
- return
825
- }
826
- this.handScale = 'auto'
827
- this.transformSalce = (this.transformSalce - 0.2).toFixed(1)
828
- } else if (value == 'auto') {
829
- this.transformSalce = this.$refs.pdfView.clientWidth / this.pageSize.width
830
- } else if (value == 'reality') {
831
- this.transformSalce = 0.5
832
- } else {
833
- this.transformSalce = (value / 2).toFixed(1)
834
- }
835
- this.transformSalce = Number(this.transformSalce)
836
- this.contentView.style.transform = 'scale(' + this.transformSalce + ')';
837
- // this.getpdfResloutePage(this.cachePdf[0])
838
- },
839
- },
840
- computed: {
841
- perviewUrl () {
842
- return '/web/viewer.html?file=' + '/pdflist/pdf4split-1.pdf'
843
- },
844
- setHeight () {
845
- if (this.tagIds.length > 1) {
846
- if (this.isPC) {
847
- return 'calc(100% - 110px)'
848
- } else {
849
- return 'calc(100% - 60px)'
850
- }
851
- } else {
852
- if (this.isPC) {
853
- return 'calc(100% - 50px)'
854
- } else {
855
- return '100%'
856
- }
857
- }
858
- }
859
- },
860
- watch: {
861
- tagIds: {
862
- handler (value) {
863
- if (value && value.length) {
864
- // 在 pdf_view 下创建 所有canvs的容器
865
- this.contentView = document.createElement('div')
866
- this.contentView.style.transformOrigin = '0px 0px 0px'
867
- this.$http.get('/knowledge-api/knowledge/knowledge-part-location-info/list?ids=' + value.join(',')).then(res => {
868
- // res.data = {"data":[{"id":"64591b7d8bb8ab1b91c65f24","knowledgeId":"64591a9c8da27649473f3b4b","mainId":"fb348d095c0b4fd7bbd37826563dac7d","page":3,"total":18,"pageHeight":540.0,"pageWidth":960.00946,"publicPageFileUrl":"https://askbot-pdf-all.oss-cn-zhangjiakou.aliyuncs.com/fb348d095c0b4fd7bbd37826563dac7d/2023/05/08/11/55/18/64591b638bb8ab1b91c65eed/3.pdf","extractInfo":{"location":[280.488,161.32,398.71573,61.99298],"content":"黄花城水长城旅游区位于北京市怀柔区九渡河镇境内,距北京市区65公里,是以奇而著称,融山川、碧水、古长城为一体的旅游休闲胜地。而这里的“三绝景”更是引人入","lines":[{"content":"黄花城水长城旅游区位于北京市怀柔区九渡河镇境内,距","location":[280.488,161.32,398.71573,15.9869995]},{"content":"北京市区65公里,是以奇而著称,融山川、碧水、古长","location":[283.691,184.30899,392.3055,15.9869995]},{"content":"城为一体的旅游休闲胜地。而这里的“三绝景”更是引人入","location":[282.699,207.32599,394.3033,15.9869995]}],"tagId":null}}],"code":"0","msg":null,"traceId":null}
869
- // res.data = {"data":[{"id":"64590ce1eb1320043401cc90","knowledgeId":"64590cd5017b461d67e282e1","mainId":"fb348d095c0b4fd7bbd37826563dac7d","page":2,"total":5,"pageHeight":841.8898,"pageWidth":595.30396,"publicPageFileUrl":"https://askbot-pdf-all.oss-cn-zhangjiakou.aliyuncs.com/fb348d095c0b4fd7bbd37826563dac7d/2023/05/08/10/53/20/64590ce0eb1320043401cc7b/2.pdf","extractInfo":{"location":[89.32981,638.1907,415.15512,98.63251],"content":":北京地铁 13\r号线 :藤黄\r色 :西直门站—\r东直门站 :17 :41.\r5 :6\r准\rB :2002年\r09月\r28日 ","lines":[{"content":":北京地铁 13\r号线 ","location":[89.32981,638.1907,99.44599,98.63251]},{"content":":藤黄\r色 ","location":[188.7758,638.1907,46.79959,98.63251]},{"content":":西直门站—\r东直门站 ","location":[235.5754,638.1907,86.09996,98.63251]},{"content":":17 ","location":[321.67535,638.1907,36.200012,98.63251]},{"content":":41.\r5 ","location":[357.87537,638.1907,39.400696,98.63251]},{"content":":6\r准\rB ","location":[397.27606,638.1907,41.099,98.63251]},{"content":":2002年\r09月\r28日 ","location":[438.37506,638.1907,66.10986,98.63251]}],"tagId":null}}],"code":"0","msg":null,"traceId":null}
870
- // res.data = {"data":[{"id":"64591b7d8bb8ab1b91c65f24","knowledgeId":"64591a9c8da27649473f3b4b","mainId":"fb348d095c0b4fd7bbd37826563dac7d","page":3,"total":18,"pageHeight":540.0,"pageWidth":960.00946,"publicPageFileUrl":"https://askbot-pdf-all.oss-cn-zhangjiakou.aliyuncs.com/fb348d095c0b4fd7bbd37826563dac7d/2023/05/08/11/55/18/64591b638bb8ab1b91c65eed/3.pdf","extractInfo":{"location":[280.488,161.32,398.71573,61.99298],"content":"黄花城水长城旅游区位于北京市怀柔区九渡河镇境内,距北京市区65公里,是以奇而著称,融山川、碧水、古长城为一体的旅游休闲胜地。而这里的“三绝景”更是引人入","lines":[{"content":"黄花城水长城旅游区位于北京市怀柔区九渡河镇境内,距","location":[280.488,161.32,398.71573,15.9869995]},{"content":"北京市区65公里,是以奇而著称,融山川、碧水、古长","location":[283.691,184.30899,392.3055,15.9869995]},{"content":"城为一体的旅游休闲胜地。而这里的“三绝景”更是引人入","location":[282.699,207.32599,394.3033,15.9869995]}],"tagId":null}}],"code":"0","msg":null,"traceId":null}
871
- // res.data = {"data":[{"id":"6475eab868110215ab821a80","knowledgeId":"6475e7eac724c54c46cbfa2d","mainId":"5ecf2fcd704541149201ab9c1c31162d","page":0,"total":1,"pageHeight":0.0,"pageWidth":0.0,"publicPageFileUrl":"https://askbot-pdf-all.oss-cn-zhangjiakou.aliyuncs.com/5ecf2fcd704541149201ab9c1c31162d/2023/05/30/08/23/20/6475eab63339db423f26b196/0.html","extractInfo":{"location":null,"content":"产品:系统配置,产品型号:存储,VX30:4G+16G,VX50:16G+256G","lines":null,"tagId":"6475eab868110215ab821a80"}}],"code":"0","msg":null,"traceId":null}
872
- // res.data = {"data":[{"id":"6475e9393339db423f26af01","knowledgeId":"6475e44fc724c54c46cbfa21","mainId":"5ecf2fcd704541149201ab9c1c31162d","page":2,"total":2,"pageHeight":510.25,"pageWidth":1559.05,"publicPageFileUrl":"https://askbot-pdf-all.oss-cn-zhangjiakou.aliyuncs.com/5ecf2fcd704541149201ab9c1c31162d/2023/05/30/08/00/29/6475e55d3339db423f26a9b8/2.pdf","extractInfo":{"location":[327.70532,288.0498,414.9734,12.241608],"content":"三、指示灯状态说明1.白色常亮:开机/开机中2.红色常亮:待机3.白色呼吸:息屏4.红色闪烁:升级1.LAN:通过网线连接到主机的Camera端口2.电源开关:电源切换开关","lines":[{"content":"三、指示灯状态说明","location":[634.3203,288.0498,108.3584,12.0]},{"content":"1.白色常亮:开机/开机中","location":[634.3203,320.08978,108.23407,9.0]},{"content":"2.红色常亮:待机","location":[634.3204,341.3298,78.597046,9.0]},{"content":"3.白色呼吸:息屏","location":[634.32043,362.45282,78.597046,9.0]},{"content":"4.红色闪烁:升级","location":[634.3205,383.6928,78.597046,9.0]},{"content":"1.LAN:通过网线连接到主机的","location":[327.70535,291.2914,144.35995,9.0]},{"content":"Camera端口","location":[327.70532,306.88843,55.322998,9.0]},{"content":"2.电源开关:电源切换开关","location":[482.74832,291.2914,105.36301,9.0]}],"tagId":null}}],"code":"0","msg":null,"traceId":null}
873
- // if(value.length === 1) {
874
- // this.$refs.pdfView.style.height = 'calc(100% - 50px)'
875
- // }
876
- // res.data = {
877
- // "data": [
878
- // {
879
- // "id": "64e746120372d778849d2e8e",
880
- // "knowledgeId": "64e30035edffac0ec96a2d39",
881
- // "mainId": "e0f6898c6b0d47fa98e8f71ceab1bde8",
882
- // "page": 14,
883
- // "total": 60,
884
- // "pageHeight": 728.504,
885
- // "pageWidth": 515.906,
886
- // "publicPageFileUrl": "https://askbot-pdf-all.oss-cn-zhangjiakou.aliyuncs.com/e0f6898c6b0d47fa98e8f71ceab1bde8/2023/08/21/02/12/07/64e300378c3dfb3bc434f51a/15.pdf",
887
- // "extractInfo": {
888
- // "location": [
889
- // 52.665375,
890
- // 312.01306,
891
- // 404.98618,
892
- // 142.5199
893
- // ],
894
- // "content": null,
895
- // "lines": [
896
- // {
897
- // "content": null,
898
- // "location": [
899
- // 52.665375,
900
- // 312.01306,
901
- // 404.98618,
902
- // 142.5199
903
- // ]
904
- // }
905
- // ],
906
- // "tagId": null
907
- // },
908
- // "block": {
909
- // "type": "TEXT",
910
- // "location": [
911
- // 52.665375,
912
- // 312.01306,
913
- // 404.98618,
914
- // 142.5199
915
- // ],
916
- // "color": "#366AFF",
917
- // "flowChart": {
918
- // "content": ""
919
- // },
920
- // "image": {
921
- // "url": null,
922
- // "desc": ""
923
- // },
924
- // "table": {
925
- // "title": null,
926
- // "table": null
927
- // },
928
- // "text": {
929
- // "originText": "① 头部防护:安全帽\n佩戴要求:\n①存在坠物或对头部产生碰撞风险的作业场所需要佩戴安全帽 ;\n②安全帽必须戴正、戴牢、不能晃动,要系紧下颏带,调节好后箍以\n防安全帽脱落 ;\n③受强力撞击及超过有效期的安全帽必须更换。",
930
- // "indexText": "① 头部防护:安全帽\n佩戴要求:\n①存在坠物或对头部产生碰撞风险的作业场所需要佩戴安全帽 ;\n②安全帽必须戴正、戴牢、不能晃动,要系紧下颏带,调节好后箍以\n防安全帽脱落 ;\n③受强力撞击及超过有效期的安全帽必须更换。",
931
- // "lines": [
932
- // {
933
- // "location": [
934
- // 69.08148,
935
- // 368.92072,
936
- // 65.90851,
937
- // 10.5
938
- // ]
939
- // },
940
- // {
941
- // "location": [
942
- // 86.290985,
943
- // 384.67072,
944
- // 31.5,
945
- // 10.5
946
- // ]
947
- // },
948
- // {
949
- // "location": [
950
- // 286.2992,
951
- // 315.73584,
952
- // 37.656006,
953
- // 12.0
954
- // ]
955
- // },
956
- // {
957
- // "location": [
958
- // 324.6939,
959
- // 316.79932,
960
- // 122.74487,
961
- // 10.5
962
- // ]
963
- // },
964
- // {
965
- // "location": [
966
- // 286.2954,
967
- // 336.0458,
968
- // 149.625,
969
- // 10.5
970
- // ]
971
- // },
972
- // {
973
- // "location": [
974
- // 286.2954,
975
- // 356.0483,
976
- // 161.15405,
977
- // 10.5
978
- // ]
979
- // },
980
- // {
981
- // "location": [
982
- // 286.2954,
983
- // 376.0508,
984
- // 161.15405,
985
- // 10.5
986
- // ]
987
- // },
988
- // {
989
- // "location": [
990
- // 286.2954,
991
- // 396.0533,
992
- // 76.125,
993
- // 10.5
994
- // ]
995
- // },
996
- // {
997
- // "location": [
998
- // 286.2954,
999
- // 416.05582,
1000
- // 161.17517,
1001
- // 10.5
1002
- // ]
1003
- // },
1004
- // {
1005
- // "location": [
1006
- // 286.2954,
1007
- // 436.8038,
1008
- // 52.5,
1009
- // 10.5
1010
- // ]
1011
- // },
1012
- // {
1013
- // "location": [
1014
- // 338.7992,
1015
- // 435.73584,
1016
- // 12.0,
1017
- // 12.0
1018
- // ]
1019
- // }
1020
- // ]
1021
- // }
1022
- // }
1023
- // }
1024
- // ],
1025
- // "code": "0",
1026
- // "msg": null,
1027
- // "traceId": null
1028
- // }
1029
- if (res.data.code == 0) {
1030
- // tagIds 会按照gpt识别的生成有序的数组,前端直接按照下标的顺序取就可以了
1031
- // 缓存拿到的所有数据
1032
- this.cachePdf = res.data.data
1033
- let publicPageFileUrl = res.data.data[0].publicPageFileUrl
1034
- this.currentPage = 0
1035
- if (publicPageFileUrl.substring(publicPageFileUrl.lastIndexOf('.')) === '.pdf') {
1036
- this.preViewType = 'pdf'
1037
- this.setPageAllLine(this.cachePdf)
1038
- this.getpdfResloutePage(res.data.data[0])
1039
- } else {
1040
- this.preViewType = 'excal'
1041
- this.$http.post(
1042
- '/knowledge-api/temporary-certificate/or-origin?expired=30',
1043
- publicPageFileUrl,
1044
- {
1045
- headers: {
1046
- "Content-Type": "application/json",
1047
- },
1048
- }).then(res => {
1049
- // 使用原声请求方式 axios会带有不需要的请求头
1050
- let xhr = new XMLHttpRequest();
1051
- xhr.open('GET', res.data || res.bodyText, true);
1052
- // 定义请求完成的处理函数,请求前也可以增加加载框/禁用下载按钮逻辑
1053
- xhr.onload = ({ currentTarget }) => {
1054
- // 请求完成
1055
- if (currentTarget.status === 200) { // 返回200
1056
- this.contentView.innerHTML = currentTarget.response
1057
- this.contentView.style.padding = '10px'
1058
- // this.contentView.style.position = 'relative'
1059
- this.$refs.pdfView.style.backgroundColor = '#FFFFFF'
1060
- this.$refs.pdfView.appendChild(this.contentView)
1061
- let allTr = Array.from(this.$refs.pdfView.getElementsByTagName('tr'))
1062
- this.allTr = []
1063
- for (let index = 0; index < allTr.length; index++) {
1064
- if (value.includes(allTr[index].getAttribute('tag-id'))) {
1065
- this.allTr.push(allTr[index])
1066
- }
1067
- }
1068
- this.currentChange(1)
1069
-
1070
- }
1071
- }
1072
- xhr.send();
1073
- })
1074
- }
1075
- } else {
1076
- let div = document.createElement('div')
1077
- div.innerText = '文件加载异常'
1078
- this.contentView.appendChild(div)
1079
- this.$refs.pdfView.appendChild(this.contentView)
1080
- }
1081
- })
1082
- }
1083
- },
1084
- deep: true,
1085
- immediate: true
1086
- }
1087
- },
1088
- mounted () {
1089
- if (/(iPhone|iPad|iPod|iOS|Android)/i.test(navigator.userAgent)) {
1090
- this.isPC = false
1091
- } else {
1092
- this.isPC = true
1093
- }
1094
- }
1095
- }
1096
- </script>
1097
-
1098
- <style lang="less" scoped>
1099
- .pdf_view {
1100
- width: 100%;
1101
- height: calc(100% - 110px);
1102
- overflow: auto;
1103
- background-color: #f5f7fb;
1104
- // margin-bottom: 60px;
1105
- box-sizing: border-box;
1106
-
1107
- // position: relative;
1108
- // > div {
1109
- // width: 100%;
1110
- // height: 100%;
1111
- // overflow: hidden;
1112
- // overflow-y: auto;
1113
- // position: relative;
1114
- // }
1115
- >iframe {
1116
- width: 100%;
1117
- height: 100%;
1118
- }
1119
-
1120
- a:link {
1121
- color: none;
1122
- }
1123
-
1124
- a:visited {
1125
- color: none;
1126
- }
1127
-
1128
- a:hover {
1129
- color: none;
1130
- }
1131
-
1132
- a:active {
1133
- color: none;
1134
- }
1135
- .btn_footer {
1136
- width: 100%;
1137
- height: 60px;
1138
- display: flex;
1139
- align-items: center;
1140
- justify-content: space-around;
1141
- position: absolute;
1142
- bottom: 0px;
1143
- left: 0;
1144
- z-index: 999;
1145
- background: #ffffff;
1146
-
1147
- .prev,
1148
- .next {
1149
- width: 35%;
1150
- height: 40px;
1151
- display: flex;
1152
- align-items: center;
1153
- justify-content: center;
1154
- border-radius: 50px;
1155
- cursor: pointer;
1156
- }
1157
-
1158
- .prev {
1159
- background: #F2F5FA;
1160
- color: #000;
1161
- }
1162
-
1163
- .next {
1164
- background: #366aff;
1165
- color: #ffffff;
1166
- }
1167
- }
1168
-
1169
- #pagination {
1170
- .total-class {
1171
- margin-right: 13px;
1172
- font-weight: 400;
1173
- }
1174
-
1175
- position: absolute;
1176
- bottom: 0px;
1177
- right: 0;
1178
- width: 100%;
1179
- display: flex;
1180
- align-items: center;
1181
- justify-content: center;
1182
- height: 50px;
1183
- background-color: white;
1184
- box-shadow: 0px 0px 18px 0px rgba(29, 55, 129, 0.07);
1185
- border-radius: 5px;
1186
- z-index: 1000;
1187
-
1188
-
1189
-
1190
- /deep/.el-pagination {
1191
- margin-right: 110px;
1192
- }
1193
-
1194
- /deep/.el-pager {
1195
- background: #EDF0F6;
1196
- border-radius: 15px;
1197
- }
1198
-
1199
- /deep/.el-pagination.is-background .btn-next {
1200
- width: 30px;
1201
- height: 30px;
1202
- background: #EDF0F6;
1203
- border-radius: 50%;
1204
- }
1205
-
1206
- /deep/.el-pagination .btn-next {
1207
- width: 30px;
1208
- height: 30px;
1209
- background: #EDF0F6;
1210
- border-radius: 50%;
1211
- padding-left: 0;
1212
- margin-left: 5px;
1213
- }
1214
-
1215
- /deep/.el-pagination .btn-prev {
1216
- width: 30px;
1217
- height: 30px;
1218
- background: #EDF0F6;
1219
- border-radius: 50%;
1220
- padding-right: 0;
1221
- margin-right: 5px;
1222
- }
1223
-
1224
- /deep/.el-pagination button {
1225
- padding: 0;
1226
- min-width: 30px;
1227
- }
1228
-
1229
- /deep/.el-pager li {
1230
- background: #EDF0F6;
1231
- height: 30px;
1232
- min-width: 30px;
1233
- line-height: 30px;
1234
- font-size: 12px;
1235
- color: #717b90;
1236
- }
1237
-
1238
- /deep/.el-pager li:first-child {
1239
- border-bottom-left-radius: 15px !important;
1240
- border-top-left-radius: 15px !important;
1241
- }
1242
-
1243
- /deep/.el-pager li:last-child {
1244
- border-top-right-radius: 15px !important;
1245
- border-bottom-right-radius: 15px !important;
1246
- }
1247
-
1248
- /deep/.el-pager li.active {
1249
- width: 30px;
1250
- height: 30px;
1251
- min-width: 30px;
1252
- background: #366AFF;
1253
- border: 3px solid #A1B9FF;
1254
- border-radius: 50%;
1255
- line-height: 24px;
1256
- color: white;
1257
- }
1258
-
1259
- /deep/.el-pagination.is-background .el-pager li:not(.disabled).active {
1260
- background: #366AFF;
1261
- }
1262
- }
1263
-
1264
- .change_scale {
1265
- width: 100%;
1266
- height: 50px;
1267
- position: absolute;
1268
- top: 50px;
1269
- left: 0;
1270
- background: #ffffff;
1271
- display: flex;
1272
- align-items: center;
1273
- padding: 0 10px;
1274
- box-sizing: border-box;
1275
-
1276
- section {
1277
- cursor: pointer;
1278
- width: 30px;
1279
- height: 30px;
1280
- margin-right: 5px;
1281
- border-radius: 5px;
1282
- display: flex;
1283
- align-items: center;
1284
- justify-content: center;
1285
-
1286
- i {
1287
- font-weight: 900;
1288
- }
1289
- }
1290
-
1291
- section:hover {
1292
- background: rgba(221, 222, 223, 1);
1293
- }
1294
- }
1295
- }
1296
- </style>
1297
- <style lang="less">
1298
- .animation {
1299
- animation-name: highlight;
1300
- animation-duration: 4s;
1301
- }
1302
-
1303
- @keyframes highlight {
1304
- 0% {
1305
- background: rgba(255, 136, 0, 0.3);
1306
- }
1307
-
1308
- 25% {
1309
- background: rgba(255, 136, 0, 0.6);
1310
- }
1311
-
1312
- 50% {
1313
- background: rgba(255, 136, 0, 0.3);
1314
- }
1315
-
1316
- 75% {
1317
- background: rgba(255, 136, 0, 0.6);
1318
- }
1319
-
1320
- 100% {
1321
- background: rgba(255, 136, 0, 0.3);
1322
- }
1
+ <template>
2
+ <div class="pdf_view" id="pdf_view" :style="{
3
+ marginTop: isPC ? '50px' : '',
4
+ marginBottom: tagIds.length > 1 ? '60px' : '0px',
5
+ height: setHeight
6
+ }">
7
+ <div class="change_scale" v-if="isPC">
8
+ <section @click="changeScale('reduce')">
9
+ <i class="el-icon-minus"></i>
10
+ </section>
11
+ <el-divider direction="vertical"></el-divider>
12
+ <section @click="changeScale('zoom')">
13
+ <i class="el-icon-plus"></i>
14
+ </section>
15
+ <el-select size="small" v-model="handScale" @change="changeScale" placeholder="请选择">
16
+ <el-option v-for="item in scaleList" :key="item.value" :label="item.label" :value="item.value">
17
+ </el-option>
18
+ </el-select>
19
+ </div>
20
+ <div class="pdf_container_view" id="pdf_container_view" @scroll="pdfScroll" ref="pdfView"></div>
21
+ <div class="btn_footer" v-if="tagIds.length > 1 && !isPC">
22
+ <div class="prev" @click="prev">上一段</div>
23
+ <div class="next" @click="next">下一段</div>
24
+ </div>
25
+ <div id="pagination" v-if="tagIds.length > 1 && isPC">
26
+ <el-pagination :current-page="currentPage + 1" @current-change="currentChange" @prev-click="prev"
27
+ @next-click="next" layout="slot, prev, pager, next" :page-size="1" :total="tagIds.length">
28
+ <span class="total-class">答案由{{ tagIds.length }}段内容生成</span>
29
+ </el-pagination>
30
+ </div>
31
+ </div>
32
+ </template>
33
+
34
+ <script>
35
+ import _ from 'lodash'
36
+ // import * as pdfjsLib from 'pdfjs-dist'
37
+ // pdfjsLib.GlobalWorkerOptions.workerSrc = 'pdfjs-dist/build/pdf.worker';
38
+ // import { TextLayerBuilder } from "pdfjs-dist/web/pdf_viewer";
39
+ // EventBus pdf_viewer 支持绑定自定义事件,一版不做
40
+ // import 'pdfjs-dist/web/pdf_viewer.css'
41
+ /* eslint-disable */
42
+ const pdfjsLib = window['pdfjsLib']
43
+ if (pdfjsLib) {
44
+ pdfjsLib.GlobalWorkerOptions.workerSrc = window['pdfjs-dist/build/pdf.worker']
45
+ // 'pdfjs-dist/build/pdf.worker';
46
+ }
47
+ const { TextLayerBuilder } = window['pdfjs-dist/web/pdf_viewer']
48
+ const CSS_UNITS = 96.0 / 72.0
49
+ // import { zoomElement } from '../assets/js/hammer'
50
+ export default {
51
+ name: 'pdfView',
52
+ props: ['tagIds', 'isMessageRecord','fileName', "knowledgeItem"],
53
+ data () {
54
+ return {
55
+ url: '',
56
+ pages: [],
57
+ pageLoadStatus: {
58
+ WAIT: 0,
59
+ LOADED: 1,
60
+ },
61
+ scale: 1,
62
+ rotation: 0,
63
+ pageSize: {},
64
+ PAGE_INTVERVAL: 15,
65
+ SLICE_COUNT: 5,
66
+ contentView: null,
67
+ fisrtLoad: true,
68
+ TextLayerBuilder: null,
69
+ totalPageCount: 0,
70
+ identifyTextPostion: {
71
+ top: 0,
72
+ left: 0,
73
+ width: 100,
74
+ height: 0,
75
+ page: 1,
76
+ pageHeight: 0,
77
+ pageWidth: 0,
78
+ extractInfo: {},
79
+ currentPageAllLine: []
80
+ },
81
+ currentPageAllLine: [],
82
+ pdfUrl: '',
83
+ cachePdf: [],
84
+ newViewer: null,
85
+ currentPage: 0,
86
+ changetoolbar: false,
87
+ allTr: [],
88
+ preViewType: 'pdf',
89
+ displacement: {
90
+ pageX: 0,
91
+ pageY: 0,
92
+ moveable: false,
93
+ pageX2: 0,
94
+ pageY2: 0,
95
+ originScale: 1,
96
+ },
97
+ isTouchMoved: false,
98
+ transformSalce: null,
99
+ defaultTransform:0.8,
100
+ isPC: false,
101
+ handScale: 'auto',
102
+ scaleList: [
103
+ {
104
+ label: '自动缩放',
105
+ value: 'auto'
106
+ },
107
+ {
108
+ label: '实际比例',
109
+ value: 'reality'
110
+ },
111
+ {
112
+ label: '100%',
113
+ value: 1
114
+ },
115
+ {
116
+ label: '120%',
117
+ value: 1.2
118
+ },
119
+ {
120
+ label: '150%',
121
+ value: 1.5
122
+ },
123
+ {
124
+ label: '170%',
125
+ value: 1.7
126
+ }
127
+ ,
128
+ {
129
+ label: '200%',
130
+ value: 2
131
+ }
132
+ ],
133
+ scrollTop: 0,
134
+ scrollLeft: 0
135
+ }
136
+ },
137
+ methods: {
138
+ getpdfResloutePage (pdfResloute) {
139
+ // 根据当前页面宽度设置缩放比例
140
+ // this.scale = Math.round(this.$refs.pdfView.clientWidth / pdfResloute.pageWidth * 100) / 100
141
+ if (this.isMessageRecord) {
142
+ this.scale = Math.round(this.$refs.pdfView.clientWidth / pdfResloute.pageWidth * 100) / 100
143
+ } else {
144
+ this.scale = 2
145
+ }
146
+ // 从后端获取到当前分片后所有的pdf页码,初始化数组,数组下{} 对应每页pdf文件
147
+ this.pdfUrl = pdfResloute.publicPageFileUrl.substring(0, pdfResloute.publicPageFileUrl.lastIndexOf('/') + 1)
148
+ this.initPages(pdfResloute.total)
149
+ // 定位功能,加载对应页码位置
150
+ this.loadPdfData(pdfResloute.page)
151
+ },
152
+ async loadPdfData (loadPage) {
153
+ if (this.pages[loadPage - 1] && ((this.pages[loadPage - 1].dom && this.pages[loadPage - 1].dom.children.length > 0) || this.pages[loadPage - 1].loadStatus)) {
154
+ return
155
+ } else {
156
+ if (this.changetoolbar) {
157
+ this.$nextTick(() => {
158
+ this.renderHighlights()
159
+ })
160
+ this.changetoolbar = false
161
+ }
162
+ }
163
+ // 记录开始缓存的状态
164
+ // pdfjsLib.GlobalWorkerOptions.workerSrc = require("pdfjs-dist/legacy/build/pdf.worker.entry.js");
165
+ // 拿到第一个分片
166
+ const { startPage, url } = await this.fetchPdfFragment(loadPage);
167
+ let loadingTask = pdfjsLib.getDocument(url)
168
+ loadingTask.promise.then(async (pdfDoc) => {
169
+ // 将已经下载的分片保存到 pages 数组中
170
+ // for (let i = 0; i < pdfDoc.numPages; i += 1) {
171
+ // const pageIndex = startPage + i;
172
+ // const page = this.pages[pageIndex - 1];
173
+ // // // 不在缓存列表内,重新获取本页pdf
174
+ // // if (page.loadStatus !== this.pageLoadStatus.LOADED) {
175
+
176
+ // // } else {
177
+ // // if (this.changetoolbar) {
178
+ // // this.$nextTick(() => {
179
+ // // this.renderHighlights()
180
+ // // })
181
+ // // this.changetoolbar = false
182
+ // // }
183
+ // // }
184
+ // }
185
+ const page = this.pages[loadPage - 1]
186
+ await pdfDoc.getPage(1).then(async (pdfPage) => {
187
+ this.pages[loadPage - 1].loadStatus = true
188
+ this.pages[loadPage - 1].pdfPage = pdfPage;
189
+ // 通知可以进行渲染了
190
+ await this.startRenderPages(pdfPage, page, loadPage)
191
+ });
192
+ });
193
+ },
194
+ initPages (totalPage) {
195
+ // const pages = [];
196
+ this.totalPageCount = totalPage
197
+ for (let i = 0; i < totalPage; i += 1) {
198
+ this.pages.push({
199
+ pageNo: i + 1,
200
+ loadStatus: false,
201
+ pdfPage: null,
202
+ dom: null
203
+ });
204
+ }
205
+ },
206
+ async fetchPdfFragment (pageIndex) {
207
+ // 置换加签后的文件地址。
208
+ let obj = {}
209
+ await this.$http.post(
210
+ '/knowledge-api/temporary-certificate/or-origin?expired=30',
211
+ this.pdfUrl + pageIndex + '.pdf',
212
+ {
213
+ headers: {
214
+ "Content-Type": "application/json",
215
+ },
216
+ }).then(async res => {
217
+ if (res.bodyText) {
218
+ // 最后返回一个 包含这4个参数的对象
219
+ obj = await {
220
+ "startPage": pageIndex, // 分片的开始页码
221
+ "endPage": pageIndex + 5, // 分片结束页码
222
+ "totalPage": this.totalPageCount, // pdf 总页数
223
+ "url": res.bodyText // 分片内容下载地址
224
+ }
225
+ }
226
+ if (res.data) {
227
+ // 最后返回一个 包含这4个参数的对象
228
+ obj = await {
229
+ "startPage": pageIndex, // 分片的开始页码
230
+ "endPage": pageIndex + 5, // 分片结束页码
231
+ "totalPage": this.totalPageCount, // pdf 总页数
232
+ "url": res.data // 分片内容下载地址
233
+ }
234
+ }
235
+ })
236
+ return obj
237
+ },
238
+ startRenderPages (pdfPage, page, pageIndex) {
239
+ if (Object.keys(this.pageSize).length == 0) {
240
+ const viewport = pdfPage.getViewport({
241
+ scale: this.scale, // 缩放的比例
242
+ rotation: this.rotation, // 旋转的角度
243
+ });
244
+ // 记录pdf页面高度
245
+ const pageSize = {
246
+ width: viewport.width,
247
+ height: viewport.height,
248
+ }
249
+ this.pageSize = pageSize
250
+ // 创建内容绘制区,并设置大小
251
+ if (this.$refs.pdfView.clientWidth / this.pageSize.width >= 1 || this.isMessageRecord) {
252
+ this.contentView.style.width = `${pageSize.width - 10}px`;
253
+ this.contentView.style.height = `${(this.totalPageCount * (pageSize.height + this.PAGE_INTVERVAL)) + this.PAGE_INTVERVAL}px`;
254
+ this.contentView.style.margin = '0 auto 0'
255
+ } else {
256
+ this.transformSalce = this.$refs.pdfView.clientWidth / this.pageSize.width / CSS_UNITS
257
+ this.contentView.style.width = `${pageSize.width * this.transformSalce - 10}px`;
258
+ this.contentView.style.height = `${(this.totalPageCount * (pageSize.height * (this.transformSalce) + this.PAGE_INTVERVAL)) + this.PAGE_INTVERVAL}px`;
259
+ }
260
+ // this.contentView.style.margin = '0 auto 0'
261
+ this.contentView.style.position = 'relative'
262
+ this.contentView.style.paddingBottom = '60px'
263
+ // contentView.style.overflowY = 'auto'
264
+ this.$refs.pdfView.appendChild(this.contentView);
265
+ if (this.knowledgeItem && (this.knowledgeItem.source === 'CORP_LOCAL_FILE' || this.knowledgeItem.source === 'YUQUE' || this.knowledgeItem.source === 'FEISHU') && (this.knowledgeItem.visitorWatermarkValue || this.knowledgeItem.textWatermarkValue)){
266
+ this.watermark()
267
+ }
268
+ }
269
+ this.renderPages(pageIndex)
270
+ },
271
+ // 渲染需要展示的页面,不需展示的页码将其清除
272
+ renderPages (pageIndex) {
273
+ const pagesToRender = this.getRenderScope(pageIndex);
274
+ for (const i of this.pages) {
275
+ if (pagesToRender.some(p => { return p.pageNo == i.pageNo })) {
276
+ if (i.loadStatus === true) {
277
+ this.renderPageContent(i, i.pageNo)
278
+ } else {
279
+ this.renderPageLoading(i, i.pageNo)
280
+ }
281
+ } else {
282
+ this.clearPage(i);
283
+ }
284
+ }
285
+
286
+ },
287
+ async renderPageContent (page, pageIndex) {
288
+ const { pdfPage, pageNo, dom } = page;
289
+ // dom 元素已存在,无须重新渲染,直接返回
290
+ if ((dom && dom.children.length != 0) || page.loading) {
291
+ return;
292
+ }
293
+ page.loading = true
294
+ const viewport = pdfPage.getViewport({
295
+ scale: this.scale,
296
+ rotation: this.rotation,
297
+ });
298
+ // 创建新的canvas
299
+ const canvas = document.createElement('canvas');
300
+ const context = canvas.getContext('2d');
301
+ // canvas.getContext('2d');
302
+ canvas.height = this.pageSize.height * (this.fileName ? CSS_UNITS : 1);
303
+ canvas.width = this.pageSize.width * (this.fileName ? CSS_UNITS : 1);
304
+ canvas.style.position = 'relative'
305
+ canvas.style.top = -3 + 'px'
306
+ // 创建渲染的dom
307
+ const pageDom = document.createElement('div');
308
+ pageDom.style.position = 'absolute';
309
+ pageDom.style.top = `${((pageNo - 1) * (this.pageSize.height + this.PAGE_INTVERVAL) * (this.fileName ? CSS_UNITS : 1)) + this.PAGE_INTVERVAL}px`;
310
+ pageDom.style.width = `${this.pageSize.width * (this.fileName ? CSS_UNITS : 1)}px`;
311
+ pageDom.style.height = `${this.pageSize.height * (this.fileName ? CSS_UNITS : 1)}px`;
312
+ pageDom.setAttribute('data-id', 'page' + pageNo)
313
+ // pageDom.appendChild(canvas);
314
+ // 渲染内容
315
+ let renderContext = {
316
+ canvasContext: context,
317
+ viewport: viewport,
318
+ transform: this.fileName ? [CSS_UNITS, 0, 0, CSS_UNITS, 0, 0] : '',
319
+ }
320
+ await pdfPage.render(renderContext).promise.then(() => {
321
+ const html = canvas.toDataURL();
322
+ let image = document.createElement('img');
323
+ image.setAttribute('src',html)
324
+ pageDom.appendChild(image);
325
+ return pdfPage.getTextContent()
326
+ }).then(async (textContent) => {
327
+ const textLayerDiv = document.createElement('div');
328
+ textLayerDiv.setAttribute('class', 'textLayer');
329
+ // 将文本图层div添加至每页pdf的div中
330
+ // 创建新的TextLayerBuilder实例
331
+ let textLayer = new TextLayerBuilder({
332
+ textLayerDiv: textLayerDiv,
333
+ pageIndex: pdfPage._pageIndex,
334
+ viewport: viewport,
335
+ });
336
+ let findPage = this.currentPageAllLine.find(l => { return l.page == pageIndex })
337
+ let rectdomTop = 0
338
+ if (findPage) {
339
+ let AllLines = findPage.allLines
340
+ // setTimeout(() => {
341
+ if (AllLines.length > 0) {
342
+ for (let j = 0; j < AllLines.length; j++) {
343
+ let lines = AllLines[j].lines
344
+ let rectdom = document.createElement('div')
345
+ rectdom.setAttribute('react-count', AllLines[j].pageCount);
346
+ rectdom.style.position = 'absolute';
347
+ rectdom.style.top = 0
348
+ rectdom.style.left = 0
349
+ rectdom.classList.add('rectdom')
350
+ for (let index = 0; index < lines.length; index++) {
351
+ if (!/^\s+$/g.test(lines[index].content)) {
352
+ let postionArr = lines[index].location
353
+ let div = document.createElement('div')
354
+ div.style.position = 'absolute';
355
+ div.style.left = postionArr[0] * this.scale * (this.fileName ? CSS_UNITS : 1) + 'px',
356
+ // 后端返回的坐标有基线对齐的问题,top 值是后端算好(基线top - 文字高度),在此加上文字高度的 1/9 (大致比例)为实际展示出文字的top值
357
+ div.style.top = postionArr[1] * this.scale * (this.fileName ? CSS_UNITS : 1) + 'px'
358
+ div.style.height = postionArr[3] * this.scale * (this.fileName ? CSS_UNITS : 1) + 'px';
359
+ div.style.width = postionArr[2] * this.scale * (this.fileName ? CSS_UNITS : 1) + 'px'
360
+ div.style.backgroundColor = 'rgba(54, 106, 255, 0.3)'
361
+ div.classList.add('lineHeight')
362
+ rectdom.appendChild(div)
363
+ if (index == 0 && j == 0) {
364
+ if (this.transformSalce !== null) {
365
+ rectdomTop = postionArr[1]* this.scale * (this.fileName ? CSS_UNITS : 1) * this.transformSalce
366
+ } else {
367
+ rectdomTop = postionArr[1] * this.scale * (this.fileName ? CSS_UNITS : 1) * this.defaultTransform
368
+ }
369
+ // if(this.isPC) {
370
+ // rectdomTop = rectdomTop - 50 < 0 ? 0 : rectdomTop - 50
371
+ // }
372
+ }
373
+ }
374
+ }
375
+ if (rectdom.children.length > 0) {
376
+ pageDom.appendChild(rectdom)
377
+ }
378
+ }
379
+ }
380
+ }
381
+ textLayer.setTextContent(textContent);
382
+ textLayer.render()
383
+ pageDom.appendChild(textLayerDiv);
384
+ let backgroundDom = document.getElementById('backgroundLoad' + pageNo)
385
+ if (backgroundDom) {
386
+ this.contentView.removeChild(backgroundDom);
387
+ }
388
+ page.dom = await pageDom;
389
+ page.loading = false
390
+ this.contentView.appendChild(pageDom);
391
+ let pdf_view = document.getElementsByClassName('pdf_view');
392
+ if (pdf_view && pdf_view[0]){
393
+ pdf_view[0].style.backgroundImage = 'none'
394
+ }
395
+ let postionArr = []
396
+ if (findPage){
397
+ let AllLines = findPage.allLines
398
+ if (AllLines.length){
399
+ postionArr = AllLines[0].lines[0].location
400
+ }
401
+ }
402
+ if(this.transformSalce !== null && this.fileName) {
403
+ this.contentView.style.transform = `scale(${this.transformSalce}, ${this.transformSalce})`
404
+ } else {
405
+ this.contentView.style.transform = `scale(${this.defaultTransform})`;
406
+
407
+ }
408
+ if (this.changetoolbar) {
409
+ setTimeout(() => {
410
+ this.renderHighlights()
411
+ this.changetoolbar = false
412
+ }, 500)
413
+ }
414
+ if (this.fisrtLoad) {
415
+ setTimeout(() => {
416
+ let pageoffsetHeight = 0
417
+ if (this.transformSalce !== null) {
418
+ pageoffsetHeight = (this.pageSize.height + this.PAGE_INTVERVAL) * this.transformSalce * (this.fileName ? CSS_UNITS : 1)
419
+ } else {
420
+ pageoffsetHeight = (this.pageSize.height + this.PAGE_INTVERVAL) * this.defaultTransform *(this.fileName ? CSS_UNITS : 1)
421
+ }
422
+ if (this.$refs.pdfView.clientHeight - pageoffsetHeight > 0 && pageIndex == 1) {
423
+ const height = this.$refs.pdfView.clientHeight;
424
+ let startNum = 0
425
+ let endNum = 0
426
+ if (this.transformSalce !== null) {
427
+ startNum = Math.ceil(this.$refs.pdfView.scrollTop / ((this.pageSize.height + this.PAGE_INTVERVAL) * this.transformSalce* (this.fileName ? CSS_UNITS : 1)))
428
+ endNum = startNum + Math.ceil(height / ((this.pageSize.height + this.PAGE_INTVERVAL) * this.transformSalce* (this.fileName ? CSS_UNITS : 1)))
429
+ } else {
430
+ startNum = Math.ceil(this.$refs.pdfView.scrollTop / ((this.pageSize.height + this.PAGE_INTVERVAL) * (this.fileName ? CSS_UNITS : 1) * this.defaultTransform))
431
+ endNum = startNum + Math.ceil(height / ((this.pageSize.height + this.PAGE_INTVERVAL) * (this.fileName ? CSS_UNITS : 1) * this.defaultTransform))}
432
+ console.log(this.$refs.pdfView.scrollTop, startNum, endNum, 'endNumendNum');
433
+ for (let pageIndex = startNum; pageIndex <= endNum; pageIndex++) {
434
+ if (pageIndex > 0 && pageIndex <= this.pages.length) {
435
+ this.loadPdfData(pageIndex)
436
+ }
437
+ }
438
+ }
439
+ if (this.$refs.pdfView.scrollTop == Math.floor((pageNo - 1) * pageoffsetHeight)) {
440
+ this.$refs.pdfView.scrollTop = rectdomTop
441
+ this.fisrtLoad = false
442
+ } else {
443
+ this.$refs.pdfView.scrollTop = `${((pageNo - 1) * pageoffsetHeight) + rectdomTop - this.PAGE_INTVERVAL}`
444
+ this.fisrtLoad = false
445
+ }
446
+ this.renderHighlights()
447
+ // zoomElement(this.contentView)
448
+ }, 100)
449
+ }
450
+ })
451
+ },
452
+ // 监听容器的滚动事件,触发 scrollPdf 方法
453
+ // 这里加了防抖保证不会一次产生过多请求
454
+ debounceScrollPdf: _.debounce(function (e, that) {
455
+ if (this.fisrtLoad) {
456
+ this.fisrtLoad = false
457
+ return
458
+ }
459
+ const scrollTop = e.target.scrollTop;
460
+ const height = e.target.clientHeight;
461
+ let startNum = 0
462
+ let endNum = 0
463
+ if (this.transformSalce !== null) {
464
+ startNum = Math.ceil(scrollTop / ((that.pageSize.height + that.PAGE_INTVERVAL) * this.transformSalce * (this.fileName ? CSS_UNITS : 1)))
465
+ endNum = startNum + Math.ceil(height / ((that.pageSize.height + that.PAGE_INTVERVAL) * this.transformSalce * (this.fileName ? CSS_UNITS : 1)))
466
+ } else {
467
+ startNum = Math.ceil(scrollTop / ((that.pageSize.height + that.PAGE_INTVERVAL) * (this.fileName ? CSS_UNITS : 1) * this.defaultTransform))
468
+ endNum = startNum + Math.ceil(height / ((that.pageSize.height + that.PAGE_INTVERVAL) * (this.fileName ? CSS_UNITS : 1) * this.defaultTransform))
469
+ }
470
+ for (let pageIndex = startNum; pageIndex <= endNum; pageIndex++) {
471
+ if (pageIndex > 0 && pageIndex <= that.pages.length) {
472
+ that.loadPdfData(pageIndex)
473
+ }
474
+ }
475
+ }, 200),
476
+ directScrolling (e, that) {
477
+ if (this.fisrtLoad) {
478
+ this.fisrtLoad = false
479
+ return
480
+ }
481
+ const scrollTop = e.target.scrollTop;
482
+ const height = e.target.clientHeight;
483
+ // 根据内容可视区域中心点计算页码, 没有滚动时,指向第一页
484
+ const pageIndex = scrollTop > 0 ?
485
+ Math.ceil((scrollTop + (height / 2)) / (that.pageSize.height + that.PAGE_INTVERVAL)) :
486
+ 1;
487
+ this.loadPdfData(pageIndex)
488
+ },
489
+ pdfScroll (e) {
490
+ if (this.preViewType !== 'pdf' || this.isTouchMoved) {
491
+ return
492
+ }
493
+ if (this.scrollLeft != e.target.scrollLeft) {
494
+ this.scrollLeft = e.target.scrollLeft
495
+ }
496
+ if (this.scrollTop != e.target.scrollTop) {
497
+ this.scrollTop = e.target.scrollTop
498
+ this.debounceScrollPdf(e, this)
499
+ }
500
+ },
501
+ // 分片每次只做一次处理,所以不考虑多片情况
502
+ loadBefore (pageIndex) {
503
+ this.loadPdfData(pageIndex)
504
+ },
505
+ loadAfter (pageIndex) {
506
+ this.loadPdfData(pageIndex)
507
+ },
508
+ // 首先我们获取到需要渲染的范围
509
+ // 根据当前的可视范围内的页码,我们前后只保留 8 页
510
+ getRenderScope (pageIndex) {
511
+ const pagesToRender = [];
512
+ let i = pageIndex - 1;
513
+ let j = pageIndex + 1;
514
+ // pageIndex - 1 表示当前页码数 对应的下标位置
515
+ pagesToRender.push(this.pages[pageIndex - 1]);
516
+ while (pagesToRender.length < 8 && pagesToRender.length < this.pages.length) {
517
+ if (i > 0) {
518
+ pagesToRender.push(this.pages[i - 1]);
519
+ i -= 1;
520
+ }
521
+ if (pagesToRender.length >= 8) {
522
+ break;
523
+ }
524
+ if (j <= this.pages.length) {
525
+ pagesToRender.push(this.pages[j - 1]);
526
+ j += 1;
527
+ }
528
+ }
529
+ // for (let index = 0; index < array.length; index++) {
530
+ // const element = array[index];
531
+
532
+ // }
533
+ return pagesToRender;
534
+ },
535
+
536
+ // 清除页面 dom
537
+ clearPage (page) {
538
+ if (this.contentView.contains(page.dom) && page.dom) {
539
+ this.contentView.removeChild(page.dom);
540
+ page.loadStatus = false
541
+ page.loading = false
542
+ page.dom = undefined;
543
+ }
544
+ },
545
+ // 页面正在下载时渲染loading视图
546
+ renderPageLoading (page) {
547
+ const { pageNo, dom } = page;
548
+ if (dom && dom.children.length != 0) {
549
+ return;
550
+ }
551
+ let backgroundDom = document.getElementById('backgroundLoad' + pageNo)
552
+ if (this.contentView.contains(backgroundDom)) {
553
+ return
554
+ }
555
+ const pageDom = document.createElement('div');
556
+ pageDom.style.width = `${this.pageSize.width * (this.fileName ? CSS_UNITS : 1)}px`;
557
+ pageDom.style.height = `${this.pageSize.height * (this.fileName ? CSS_UNITS : 1)}px`;
558
+ pageDom.style.position = 'absolute';
559
+ pageDom.style.top = `${((pageNo - 1) * (this.pageSize.height + this.PAGE_INTVERVAL) * (this.fileName ? CSS_UNITS : 1)) + this.PAGE_INTVERVAL
560
+ }px`;
561
+ pageDom.style.backgroundImage = `url('https://guoranopen-zjk.oss-cn-zhangjiakou.aliyuncs.com/cdn-common/images/loading.gif')`
562
+ pageDom.style.backgroundPosition = 'center'
563
+ pageDom.style.backgroundRepeat = 'no-repeat'
564
+ pageDom.style.backgroundColor = '#FFF'
565
+ pageDom.setAttribute('id', 'backgroundLoad' + pageNo)
566
+ page.dom = pageDom;
567
+ this.contentView.appendChild(pageDom);
568
+ },
569
+ prev () {
570
+ this.currentPage--
571
+ if (this.currentPage < 0) {
572
+ this.currentPage = 0
573
+ if (!this.isPC) {
574
+ this.$toast({
575
+ message: '当前已经是第一段了',
576
+ duration: 2000,
577
+ })
578
+ return
579
+ }
580
+ }
581
+ if (this.preViewType == 'pdf') {
582
+ this.scrollToUplaodePage(this.currentPage)
583
+ } else {
584
+ this.scrollToExcalTop(this.currentPage)
585
+ }
586
+ // this.getpdfResloutePage(this.cachePdf[this.currentPage - 1])
587
+ },
588
+ next () {
589
+ this.currentPage++
590
+ if (this.currentPage >= this.tagIds.length) {
591
+ this.currentPage = this.tagIds.length - 1
592
+ if (!this.isPC) {
593
+ this.$toast({
594
+ message: '当前已经是最后一段了',
595
+ duration: 2000,
596
+ })
597
+ return
598
+ }
599
+ }
600
+ if (this.preViewType == 'pdf') {
601
+ this.scrollToUplaodePage(this.currentPage)
602
+ } else {
603
+ this.scrollToExcalTop(this.currentPage)
604
+ }
605
+ },
606
+ currentChange (value) {
607
+ this.currentPage = value - 1
608
+ if (this.preViewType == 'pdf') {
609
+ this.scrollToUplaodePage(this.currentPage)
610
+ } else {
611
+ this.scrollToExcalTop(this.currentPage)
612
+ }
613
+ },
614
+ scrollToUplaodePage (currentPage) {
615
+ this.changetoolbar = true
616
+ if (this.preViewType !== 'pdf') {
617
+ return
618
+ }
619
+
620
+ let pdfResloute = this.cachePdf[currentPage]
621
+ this.identifyTextPostion.extractInfo = pdfResloute.extractInfo
622
+ this.identifyTextPostion.left = pdfResloute.extractInfo.location[0]
623
+ this.identifyTextPostion.top = pdfResloute.extractInfo.location[1]
624
+ this.identifyTextPostion.width = pdfResloute.extractInfo.location[2]
625
+ this.identifyTextPostion.height = pdfResloute.extractInfo.location[3]
626
+ this.identifyTextPostion.page = pdfResloute.page
627
+ this.identifyTextPostion.pageHeight = pdfResloute.pageHeight
628
+ this.identifyTextPostion.pageWidth = pdfResloute.pageWidth
629
+ // 在当前段落在最后一页pdf时,根据计算的高度并不能触发滚动,在此执行重新渲染方法,非次情况会执行两次,待优化
630
+ this.$nextTick(() => {
631
+ this.renderHighlights()
632
+ })
633
+ if (this.transformSalce !== null) {
634
+ this.$refs.pdfView.scrollTop = `${((pdfResloute.page - 1) * (this.pageSize.height + this.PAGE_INTVERVAL) * this.transformSalce * (this.fileName ? CSS_UNITS : 1)) + (this.identifyTextPostion.top * this.scale * this.transformSalce * (this.fileName ? CSS_UNITS : 1))}`
635
+ } else {
636
+ this.$refs.pdfView.scrollTop = `${((pdfResloute.page - 1) * (this.pageSize.height + this.PAGE_INTVERVAL) * this.defaultTransform * (this.fileName ? CSS_UNITS : 1)) + (this.identifyTextPostion.top * this.scale * this.defaultTransform * (this.fileName ? CSS_UNITS : 1))}`
637
+ }
638
+ },
639
+ scrollToExcalTop (currentPage) {
640
+ for (let index = 0; index < this.allTr.length; index++) {
641
+ if (index == currentPage) {
642
+ Array.from(this.allTr[index].children).forEach(item => {
643
+ item.style.background = 'rgba(255, 136, 0, 0.6)'
644
+ item.classList.add('animation')
645
+ setTimeout(() => {
646
+ item.classList.remove('animation')
647
+ }, 4000)
648
+ })
649
+ // getBoundingClientRect().top 当前元素距离屏幕顶部的高度 + 弹窗header 高度
650
+ if (!this.isPC) {
651
+ let top = this.allTr[index].getBoundingClientRect().top - this.$refs.pdfView.getBoundingClientRect().top
652
+ this.$refs.pdfView.scrollTop = top
653
+ } else {
654
+ let top = this.allTr[index].getBoundingClientRect().top
655
+ this.$refs.pdfView.scrollTop = top - 50
656
+ }
657
+ } else {
658
+ Array.from(this.allTr[index].children).forEach(item => {
659
+ item.style.background = 'rgba(54, 106, 255, 0.6)'
660
+ item.classList.remove('animation')
661
+ })
662
+ }
663
+ }
664
+ },
665
+ // pdf是否需要重新渲染高亮位置
666
+ renderHighlights () {
667
+ let lineHeightDom = Array.from(document.getElementsByClassName('rectdom'))
668
+ if (lineHeightDom) {
669
+ lineHeightDom.forEach((d) => {
670
+ for (let i = 0; i < d.children.length; i++) {
671
+ if (d.getAttribute('react-count') == this.currentPage) {
672
+ d.children[i].style.backgroundColor = 'rgba(255, 136, 0, 0.3)'
673
+ d.children[i].classList.add('animation')
674
+ setTimeout(() => {
675
+ d.children[i].classList.remove('animation')
676
+ }, 4000)
677
+ } else {
678
+ d.children[i].style.backgroundColor = 'rgba(54, 106, 255, 0.3)'
679
+ d.children[i].classList.remove('animation')
680
+ }
681
+ }
682
+ })
683
+ }
684
+ },
685
+ displayHiglight (pageIndex) {
686
+ let lineHeightDom = Array.from(document.getElementsByClassName('rectdom'))
687
+ if (lineHeightDom) {
688
+ lineHeightDom.forEach((d) => {
689
+ if (d.getAttribute('page-index') == pageIndex) {
690
+ d.style.display = 'none'
691
+ }
692
+ })
693
+ }
694
+ },
695
+ // 前端暂时缓存多页
696
+ autoLoadMore (pageIndex) {
697
+ let pdfResloute = this.cachePdf.find(cache => {
698
+ return cache.page == pageIndex
699
+ })
700
+ if (pdfResloute) {
701
+ this.getpdfResloutePage(pdfResloute)
702
+ } else {
703
+ this.loadPdfData(pageIndex)
704
+ }
705
+ },
706
+ setPageAllLine (arr) {
707
+ this.currentPageAllLine = []
708
+ arr.forEach((item, index) => {
709
+ let i = this.currentPageAllLine.findIndex(l => { return l.page && l.page == item.page })
710
+ if (i != -1) {
711
+ // this.currentPageAllLine[i].allLines.lines.push(item.extractInfo.lines)
712
+ this.currentPageAllLine[i].allLines.push({
713
+ pageCount: index,
714
+ lines: item.extractInfo.lines
715
+ })
716
+ } else {
717
+ this.currentPageAllLine.push({
718
+ page: item.page,
719
+ allLines: [{
720
+ pageCount: index,
721
+ lines: item.extractInfo.lines
722
+ }],
723
+ })
724
+ }
725
+ })
726
+ },
727
+ openTouch () {
728
+ // this.$nextTick()将回调延迟到下次 DOM 更新循环之后执行
729
+ let that = this;
730
+ this.$nextTick(() => {
731
+ // setInterval(() => {
732
+ // this.scale = this.scale + 0.1
733
+ // that.pages.forEach((item, index) =>{
734
+ // if(item.dom) {
735
+ // item.dom.children.forEach( childDom =>{
736
+ // if(childDom.getAttribute('react-count')) {
737
+ // childDom.style.transform = "scale(" + this.scale + ")";
738
+ // childDom.style.transformOrigin = "0px 0px 0px";
739
+ // } else {
740
+ // item.dom = null
741
+ // this.startRenderPages(item.pdfPage, null, index)
742
+ // }
743
+ // } )
744
+ // }
745
+ // })
746
+ // }, 100);
747
+ // 获取放大或缩小的区域DOM
748
+ let matrix_box = this.contentView
749
+ matrix_box.addEventListener("touchstart", function (event) {
750
+ this.isTouchMoved = true
751
+ let touches = event.touches;
752
+ let events = touches[0];
753
+ let events2 = touches[1];
754
+
755
+ // event.preventDefault();
756
+
757
+ // 第一个触摸点的坐标
758
+ that.displacement.pageX = events.pageX;
759
+ that.displacement.pageY = events.pageY;
760
+
761
+ that.displacement.moveable = true;
762
+
763
+ if (events2) {
764
+ that.displacement.pageX2 = events2.pageX;
765
+ that.displacement.pageY2 = events2.pageY;
766
+ }
767
+
768
+ that.displacement.originScale = this.scale || 1;
769
+ });
770
+ document.addEventListener("touchmove", function (event) {
771
+ if (!that.displacement.moveable) {
772
+ return;
773
+ }
774
+ // event.preventDefault();
775
+ let touches = event.touches;
776
+ let events = touches[0];
777
+ let events2 = touches[1];
778
+ // 双指移动
779
+ if (events2) {
780
+ // 第2个指头坐标在touchmove时候获取
781
+ if (!that.displacement.pageX2) {
782
+ that.displacement.pageX2 = events2.pageX;
783
+ }
784
+ if (!that.displacement.pageY2) {
785
+ that.displacement.pageY2 = events2.pageY;
786
+ }
787
+ // 双指缩放比例计算
788
+ let zoom = that.getDistance({
789
+ x: events.pageX,
790
+ y: events.pageY
791
+ },
792
+ {
793
+ x: events2.pageX,
794
+ y: events2.pageY
795
+ }
796
+ ) / that.getDistance(
797
+ {
798
+ x: that.displacement.pageX,
799
+ y: that.displacement.pageY
800
+ },
801
+ {
802
+ x: that.displacement.pageX2,
803
+ y: that.displacement.pageY2
804
+ }
805
+ );
806
+ // 应用在元素上的缩放比例
807
+ let newScale = that.displacement.originScale * zoom;
808
+ // 最大缩放比例限制
809
+ if (newScale > 2) {
810
+ newScale = 2;
811
+ }
812
+ // 最大缩放比例限制
813
+ if (newScale < 1) {
814
+ newScale = 1;
815
+ }
816
+ // 记住使用的缩放值
817
+ that.displacement.scale = newScale;
818
+ // console.log(newScale);
819
+ matrix_box.style.transform = "scale(" + newScale + ")";
820
+ // 设置旋转元素的基点位置
821
+ matrix_box.style.transformOrigin = "0px 0px 0px";
822
+ }
823
+ }, { passive: false });
824
+ document.addEventListener('touchend', function () {
825
+ that.isTouchMoved = false
826
+ }, { passive: false })
827
+ });
828
+ },
829
+ getDistance (start, stop) {
830
+ // Math.hypot()计算参数的平方根
831
+ return Math.hypot(stop.x - start.x, stop.y - start.y);
832
+ },
833
+ setupCanvas (canvas, width, height) {
834
+ const dpr = 1;
835
+ // const rect = canvas.getBoundingClientRect();
836
+ canvas.width = width
837
+ canvas.height = height
838
+ const ctx = canvas.getContext('2d');
839
+ ctx?.scale(dpr, dpr);
840
+ return ctx;
841
+ },
842
+ changeScale (value) {
843
+ if (value == 'zoom') {
844
+ this.handScale = 'auto'
845
+ this.transformSalce = (this.transformSalce + 0.2).toFixed(1)
846
+ } else if (value == 'reduce') {
847
+ if ((this.transformSalce - 0.2).toFixed(1) <= 0) {
848
+ return
849
+ }
850
+ this.handScale = 'auto'
851
+ this.transformSalce = (this.transformSalce - 0.2).toFixed(1)
852
+ } else if (value == 'auto') {
853
+ this.transformSalce = this.$refs.pdfView.clientWidth / this.pageSize.width
854
+ } else if (value == 'reality') {
855
+ this.transformSalce = 0.5
856
+ } else {
857
+ this.transformSalce = (value / 2).toFixed(1)
858
+ }
859
+ this.transformSalce = Number(this.transformSalce)
860
+ this.contentView.style.transform = 'scale(' + this.transformSalce + ')';
861
+ // this.getpdfResloutePage(this.cachePdf[0])
862
+ },
863
+ //添加水印
864
+ watermark() {
865
+ //默认设置
866
+ var defaultSettings = {
867
+ watermark_txt:"",
868
+ watermark_x: 0,//水印起始位置x轴坐标
869
+ watermark_y: 0,//水印起始位置Y轴坐标
870
+ watermark_rows: 0,//水印行数
871
+ watermark_cols: 0,//水印列数
872
+ watermark_x_space: 40,//水印x轴间隔
873
+ watermark_y_space: 60,//水印y轴间隔
874
+ watermark_color: 'black',//水印字体颜色
875
+ watermark_alpha: .3,//水印透明度
876
+ watermark_fontsize: 12,//水印字体大小
877
+ watermark_font: '微软雅黑',//水印字体
878
+ watermark_width: 100,//水印宽度
879
+ watermark_height: 80,//水印长度
880
+ watermark_angle: 20,//水印倾斜度数***
881
+ visitorWatermark_txt:""
882
+ };
883
+ if(this.knowledgeItem.textWatermarkValue){
884
+ defaultSettings.watermark_txt = this.knowledgeItem.textWatermarkValue;
885
+ }
886
+ if (this.knowledgeItem.visitorWatermarkValue){
887
+ defaultSettings.visitorWatermark_txt = this.knowledgeItem.visitorWatermarkValue
888
+ }
889
+ //采用配置项替换默认值,作用类似jquery.extend
890
+ if (arguments.length === 1 && typeof arguments[0] === "object") {
891
+ console.log("arguments = " + JSON.stringify(arguments[0]));
892
+ // 获取参数配置
893
+ var src = arguments[0];
894
+ for (let key in src) {
895
+ if (src[key] && defaultSettings[key] && src[key] === defaultSettings[key])
896
+ continue;
897
+ else if (src[key])
898
+ defaultSettings[key] = src[key];
899
+ }
900
+ }
901
+ var oTemp = document.createDocumentFragment();
902
+ //获取页面最大宽度
903
+ console.debug('pdf_view',document.getElementById('pdf_view'))
904
+ let scrollWidth = document.getElementById('pdf_view').scrollWidth;
905
+ let clientWidth = document.getElementById('pdf_view').clientWidth;
906
+ var page_width = Math.max(scrollWidth, clientWidth);
907
+
908
+ var cutWidth = page_width * 0.0150;
909
+
910
+ page_width = page_width - cutWidth;
911
+
912
+ //获取页面最大高度
913
+ let height = parseInt(this.totalPageCount * this.pageSize.height)
914
+ var page_height = Math.max(document.getElementById('pdf_container_view').scrollHeight,height);
915
+
916
+ console.debug('page_height',page_height,this.totalPageCount * this.pageSize.height);
917
+
918
+ // var page_height = document.body.scrollHeight+document.body.scrollTop;
919
+
920
+ //如果将水印列数设置为0,或水印列数设置过大,超过页面最大宽度,则重新计算水印列数和水印x轴间隔
921
+
922
+ if (defaultSettings.watermark_cols == 0 || (parseInt(defaultSettings.watermark_x + defaultSettings
923
+ .watermark_width * defaultSettings.watermark_cols + defaultSettings.watermark_x_space *
924
+ (defaultSettings.watermark_cols - 1)) > page_width)) {
925
+ defaultSettings.watermark_cols = parseInt((page_width - defaultSettings.watermark_x + defaultSettings
926
+ .watermark_x_space) / (defaultSettings.watermark_width + defaultSettings
927
+ .watermark_x_space));
928
+ defaultSettings.watermark_x_space = parseInt((page_width - defaultSettings.watermark_x -
929
+ defaultSettings
930
+ .watermark_width * defaultSettings.watermark_cols) / (defaultSettings.watermark_cols - 1));
931
+ }
932
+
933
+ //如果将水印行数设置为0,或水印行数设置过大,超过页面最大长度,则重新计算水印行数和水印y轴间隔
934
+
935
+ if (defaultSettings.watermark_rows == 0 || (parseInt(defaultSettings.watermark_y + defaultSettings
936
+
937
+ .watermark_height * defaultSettings.watermark_rows + defaultSettings.watermark_y_space * (
938
+
939
+ defaultSettings.watermark_rows - 1)) > page_height)) {
940
+
941
+ defaultSettings.watermark_rows = parseInt((defaultSettings.watermark_y_space + page_height -
942
+
943
+ defaultSettings
944
+
945
+ .watermark_y) / (defaultSettings.watermark_height + defaultSettings.watermark_y_space));
946
+
947
+ defaultSettings.watermark_y_space = parseInt(((page_height - defaultSettings.watermark_y) -
948
+
949
+ defaultSettings
950
+
951
+ .watermark_height * defaultSettings.watermark_rows) / (defaultSettings.watermark_rows - 1));
952
+
953
+ }
954
+
955
+ var x;
956
+
957
+ var y;
958
+
959
+ for (var i = 0; i < defaultSettings.watermark_rows; i++) {
960
+ y = defaultSettings.watermark_y + (defaultSettings.watermark_y_space + defaultSettings.watermark_height) * i;
961
+ for (var j = 0; j < defaultSettings.watermark_cols; j++) {
962
+ x = defaultSettings.watermark_x + (defaultSettings.watermark_width + defaultSettings.watermark_x_space) * j;
963
+
964
+ var mask_div = document.createElement('div');
965
+ mask_div.id = 'mask_div' + i + j;
966
+ mask_div.className = 'mask_div';
967
+
968
+ //注意看这里加了图片水印
969
+ mask_div.style.webkitTransform = "rotate(-" + defaultSettings.watermark_angle + "deg)";
970
+ mask_div.style.MozTransform = "rotate(-" + defaultSettings.watermark_angle + "deg)";
971
+ mask_div.style.msTransform = "rotate(-" + defaultSettings.watermark_angle + "deg)";
972
+ mask_div.style.OTransform = "rotate(-" + defaultSettings.watermark_angle + "deg)";
973
+ mask_div.style.transform = "rotate(-" + defaultSettings.watermark_angle + "deg)";
974
+ mask_div.style.visibility = "";
975
+ mask_div.style.position = "absolute";
976
+ //奇偶行错开,这样水印就不对齐,显的不呆板
977
+ console.debug('x',x)
978
+ if (i % 2 != 0) {
979
+ mask_div.style.left = x + 'px';
980
+ if (j % 2 != 0 && this.knowledgeItem.visitorWatermarkValue){
981
+ mask_div.appendChild(document.createTextNode(defaultSettings.visitorWatermark_txt));
982
+ } else {
983
+ if (!this.knowledgeItem.textWatermarkValue){
984
+ mask_div.appendChild(document.createTextNode(defaultSettings.visitorWatermark_txt));
985
+ } else {
986
+ mask_div.appendChild(document.createTextNode(defaultSettings.watermark_txt));
987
+ }
988
+ }
989
+ } else {
990
+ mask_div.style.left = x + 'px';
991
+ if (j % 2 != 0 && this.knowledgeItem.textWatermarkValue){
992
+ mask_div.appendChild(document.createTextNode(defaultSettings.watermark_txt));
993
+ } else {
994
+ if (!this.knowledgeItem.visitorWatermarkValue){
995
+ mask_div.appendChild(document.createTextNode(defaultSettings.watermark_txt));
996
+ } else {
997
+ mask_div.appendChild(document.createTextNode(defaultSettings.visitorWatermark_txt));
998
+ }
999
+ }
1000
+ }
1001
+
1002
+ mask_div.style.top = y + 'px';
1003
+ mask_div.style.overflow = "hidden";
1004
+ mask_div.style.zIndex = "9999";
1005
+ mask_div.style.pointerEvents = 'none'; //让水印不遮挡页面的点击事件
1006
+ mask_div.style.opacity = defaultSettings.watermark_alpha;
1007
+ mask_div.style.fontSize = defaultSettings.watermark_fontsize;
1008
+ mask_div.style.fontFamily = defaultSettings.watermark_font;
1009
+ mask_div.style.color = defaultSettings.watermark_color;
1010
+ mask_div.style.textAlign = "center";
1011
+ mask_div.style.width = defaultSettings.watermark_width + 'px';
1012
+ mask_div.style.height = defaultSettings.watermark_height + 'px';
1013
+ mask_div.style.display = "block";
1014
+ oTemp.appendChild(mask_div);
1015
+ }
1016
+ }
1017
+ let pageDom = document.getElementById('pdf_container_view')
1018
+ pageDom.appendChild(oTemp);
1019
+
1020
+ },
1021
+ },
1022
+ computed: {
1023
+ perviewUrl () {
1024
+ return '/web/viewer.html?file=' + '/pdflist/pdf4split-1.pdf'
1025
+ },
1026
+ setHeight () {
1027
+ if (this.tagIds.length > 1) {
1028
+ if (this.isPC) {
1029
+ return 'calc(100% - 110px)'
1030
+ } else {
1031
+ return 'calc(100% - 60px)'
1032
+ }
1033
+ } else {
1034
+ if (this.isPC) {
1035
+ return 'calc(100% - 50px)'
1036
+ } else {
1037
+ return '100%'
1038
+ }
1039
+ }
1040
+ }
1041
+ },
1042
+ watch: {
1043
+ tagIds: {
1044
+ handler (value) {
1045
+ if (value && value.length) {
1046
+ // 在 pdf_view 下创建 所有canvs的容器
1047
+ this.contentView = document.createElement('div')
1048
+ this.contentView.setAttribute('id','contentView')
1049
+ this.contentView.style.transformOrigin = '0px 0px 0px'
1050
+ this.contentView.setAttribute('id','contentView');
1051
+
1052
+ this.$http.get('/knowledge-api/knowledge/knowledge-part-location-info/list?ids=' + value.join(',')).then(res => {
1053
+ // res.data = {"data":[{"id":"64591b7d8bb8ab1b91c65f24","knowledgeId":"64591a9c8da27649473f3b4b","mainId":"fb348d095c0b4fd7bbd37826563dac7d","page":3,"total":18,"pageHeight":540.0,"pageWidth":960.00946,"publicPageFileUrl":"https://askbot-pdf-all.oss-cn-zhangjiakou.aliyuncs.com/fb348d095c0b4fd7bbd37826563dac7d/2023/05/08/11/55/18/64591b638bb8ab1b91c65eed/3.pdf","extractInfo":{"location":[280.488,161.32,398.71573,61.99298],"content":"黄花城水长城旅游区位于北京市怀柔区九渡河镇境内,距北京市区65公里,是以奇而著称,融山川、碧水、古长城为一体的旅游休闲胜地。而这里的“三绝景”更是引人入","lines":[{"content":"黄花城水长城旅游区位于北京市怀柔区九渡河镇境内,距","location":[280.488,161.32,398.71573,15.9869995]},{"content":"北京市区65公里,是以奇而著称,融山川、碧水、古长","location":[283.691,184.30899,392.3055,15.9869995]},{"content":"城为一体的旅游休闲胜地。而这里的“三绝景”更是引人入","location":[282.699,207.32599,394.3033,15.9869995]}],"tagId":null}}],"code":"0","msg":null,"traceId":null}
1054
+ // res.data = {"data":[{"id":"64590ce1eb1320043401cc90","knowledgeId":"64590cd5017b461d67e282e1","mainId":"fb348d095c0b4fd7bbd37826563dac7d","page":2,"total":5,"pageHeight":841.8898,"pageWidth":595.30396,"publicPageFileUrl":"https://askbot-pdf-all.oss-cn-zhangjiakou.aliyuncs.com/fb348d095c0b4fd7bbd37826563dac7d/2023/05/08/10/53/20/64590ce0eb1320043401cc7b/2.pdf","extractInfo":{"location":[89.32981,638.1907,415.15512,98.63251],"content":":北京地铁 13\r号线 :藤黄\r色 :西直门站—\r东直门站 :17 :41.\r5 :6\r准\rB :2002年\r09月\r28日 ","lines":[{"content":":北京地铁 13\r号线 ","location":[89.32981,638.1907,99.44599,98.63251]},{"content":":藤黄\r色 ","location":[188.7758,638.1907,46.79959,98.63251]},{"content":":西直门站—\r东直门站 ","location":[235.5754,638.1907,86.09996,98.63251]},{"content":":17 ","location":[321.67535,638.1907,36.200012,98.63251]},{"content":":41.\r5 ","location":[357.87537,638.1907,39.400696,98.63251]},{"content":":6\r准\rB ","location":[397.27606,638.1907,41.099,98.63251]},{"content":":2002年\r09月\r28日 ","location":[438.37506,638.1907,66.10986,98.63251]}],"tagId":null}}],"code":"0","msg":null,"traceId":null}
1055
+ // res.data = {"data":[{"id":"64591b7d8bb8ab1b91c65f24","knowledgeId":"64591a9c8da27649473f3b4b","mainId":"fb348d095c0b4fd7bbd37826563dac7d","page":3,"total":18,"pageHeight":540.0,"pageWidth":960.00946,"publicPageFileUrl":"https://askbot-pdf-all.oss-cn-zhangjiakou.aliyuncs.com/fb348d095c0b4fd7bbd37826563dac7d/2023/05/08/11/55/18/64591b638bb8ab1b91c65eed/3.pdf","extractInfo":{"location":[280.488,161.32,398.71573,61.99298],"content":"黄花城水长城旅游区位于北京市怀柔区九渡河镇境内,距北京市区65公里,是以奇而著称,融山川、碧水、古长城为一体的旅游休闲胜地。而这里的“三绝景”更是引人入","lines":[{"content":"黄花城水长城旅游区位于北京市怀柔区九渡河镇境内,距","location":[280.488,161.32,398.71573,15.9869995]},{"content":"北京市区65公里,是以奇而著称,融山川、碧水、古长","location":[283.691,184.30899,392.3055,15.9869995]},{"content":"城为一体的旅游休闲胜地。而这里的“三绝景”更是引人入","location":[282.699,207.32599,394.3033,15.9869995]}],"tagId":null}}],"code":"0","msg":null,"traceId":null}
1056
+ // res.data = {"data":[{"id":"6475eab868110215ab821a80","knowledgeId":"6475e7eac724c54c46cbfa2d","mainId":"5ecf2fcd704541149201ab9c1c31162d","page":0,"total":1,"pageHeight":0.0,"pageWidth":0.0,"publicPageFileUrl":"https://askbot-pdf-all.oss-cn-zhangjiakou.aliyuncs.com/5ecf2fcd704541149201ab9c1c31162d/2023/05/30/08/23/20/6475eab63339db423f26b196/0.html","extractInfo":{"location":null,"content":"产品:系统配置,产品型号:存储,VX30:4G+16G,VX50:16G+256G","lines":null,"tagId":"6475eab868110215ab821a80"}}],"code":"0","msg":null,"traceId":null}
1057
+ // res.data = {"data":[{"id":"6475e9393339db423f26af01","knowledgeId":"6475e44fc724c54c46cbfa21","mainId":"5ecf2fcd704541149201ab9c1c31162d","page":2,"total":2,"pageHeight":510.25,"pageWidth":1559.05,"publicPageFileUrl":"https://askbot-pdf-all.oss-cn-zhangjiakou.aliyuncs.com/5ecf2fcd704541149201ab9c1c31162d/2023/05/30/08/00/29/6475e55d3339db423f26a9b8/2.pdf","extractInfo":{"location":[327.70532,288.0498,414.9734,12.241608],"content":"三、指示灯状态说明1.白色常亮:开机/开机中2.红色常亮:待机3.白色呼吸:息屏4.红色闪烁:升级1.LAN:通过网线连接到主机的Camera端口2.电源开关:电源切换开关","lines":[{"content":"三、指示灯状态说明","location":[634.3203,288.0498,108.3584,12.0]},{"content":"1.白色常亮:开机/开机中","location":[634.3203,320.08978,108.23407,9.0]},{"content":"2.红色常亮:待机","location":[634.3204,341.3298,78.597046,9.0]},{"content":"3.白色呼吸:息屏","location":[634.32043,362.45282,78.597046,9.0]},{"content":"4.红色闪烁:升级","location":[634.3205,383.6928,78.597046,9.0]},{"content":"1.LAN:通过网线连接到主机的","location":[327.70535,291.2914,144.35995,9.0]},{"content":"Camera端口","location":[327.70532,306.88843,55.322998,9.0]},{"content":"2.电源开关:电源切换开关","location":[482.74832,291.2914,105.36301,9.0]}],"tagId":null}}],"code":"0","msg":null,"traceId":null}
1058
+ // if(value.length === 1) {
1059
+ // this.$refs.pdfView.style.height = 'calc(100% - 50px)'
1060
+ // }
1061
+ // res.data = {
1062
+ // "data": [
1063
+ // {
1064
+ // "id": "64e746120372d778849d2e8e",
1065
+ // "knowledgeId": "64e30035edffac0ec96a2d39",
1066
+ // "mainId": "e0f6898c6b0d47fa98e8f71ceab1bde8",
1067
+ // "page": 14,
1068
+ // "total": 60,
1069
+ // "pageHeight": 728.504,
1070
+ // "pageWidth": 515.906,
1071
+ // "publicPageFileUrl": "https://askbot-pdf-all.oss-cn-zhangjiakou.aliyuncs.com/e0f6898c6b0d47fa98e8f71ceab1bde8/2023/08/21/02/12/07/64e300378c3dfb3bc434f51a/15.pdf",
1072
+ // "extractInfo": {
1073
+ // "location": [
1074
+ // 52.665375,
1075
+ // 312.01306,
1076
+ // 404.98618,
1077
+ // 142.5199
1078
+ // ],
1079
+ // "content": null,
1080
+ // "lines": [
1081
+ // {
1082
+ // "content": null,
1083
+ // "location": [
1084
+ // 52.665375,
1085
+ // 312.01306,
1086
+ // 404.98618,
1087
+ // 142.5199
1088
+ // ]
1089
+ // }
1090
+ // ],
1091
+ // "tagId": null
1092
+ // },
1093
+ // "block": {
1094
+ // "type": "TEXT",
1095
+ // "location": [
1096
+ // 52.665375,
1097
+ // 312.01306,
1098
+ // 404.98618,
1099
+ // 142.5199
1100
+ // ],
1101
+ // "color": "#366AFF",
1102
+ // "flowChart": {
1103
+ // "content": ""
1104
+ // },
1105
+ // "image": {
1106
+ // "url": null,
1107
+ // "desc": ""
1108
+ // },
1109
+ // "table": {
1110
+ // "title": null,
1111
+ // "table": null
1112
+ // },
1113
+ // "text": {
1114
+ // "originText": "① 头部防护:安全帽\n佩戴要求:\n①存在坠物或对头部产生碰撞风险的作业场所需要佩戴安全帽 ;\n②安全帽必须戴正、戴牢、不能晃动,要系紧下颏带,调节好后箍以\n防安全帽脱落 ;\n③受强力撞击及超过有效期的安全帽必须更换。",
1115
+ // "indexText": "① 头部防护:安全帽\n佩戴要求:\n①存在坠物或对头部产生碰撞风险的作业场所需要佩戴安全帽 ;\n②安全帽必须戴正、戴牢、不能晃动,要系紧下颏带,调节好后箍以\n防安全帽脱落 ;\n③受强力撞击及超过有效期的安全帽必须更换。",
1116
+ // "lines": [
1117
+ // {
1118
+ // "location": [
1119
+ // 69.08148,
1120
+ // 368.92072,
1121
+ // 65.90851,
1122
+ // 10.5
1123
+ // ]
1124
+ // },
1125
+ // {
1126
+ // "location": [
1127
+ // 86.290985,
1128
+ // 384.67072,
1129
+ // 31.5,
1130
+ // 10.5
1131
+ // ]
1132
+ // },
1133
+ // {
1134
+ // "location": [
1135
+ // 286.2992,
1136
+ // 315.73584,
1137
+ // 37.656006,
1138
+ // 12.0
1139
+ // ]
1140
+ // },
1141
+ // {
1142
+ // "location": [
1143
+ // 324.6939,
1144
+ // 316.79932,
1145
+ // 122.74487,
1146
+ // 10.5
1147
+ // ]
1148
+ // },
1149
+ // {
1150
+ // "location": [
1151
+ // 286.2954,
1152
+ // 336.0458,
1153
+ // 149.625,
1154
+ // 10.5
1155
+ // ]
1156
+ // },
1157
+ // {
1158
+ // "location": [
1159
+ // 286.2954,
1160
+ // 356.0483,
1161
+ // 161.15405,
1162
+ // 10.5
1163
+ // ]
1164
+ // },
1165
+ // {
1166
+ // "location": [
1167
+ // 286.2954,
1168
+ // 376.0508,
1169
+ // 161.15405,
1170
+ // 10.5
1171
+ // ]
1172
+ // },
1173
+ // {
1174
+ // "location": [
1175
+ // 286.2954,
1176
+ // 396.0533,
1177
+ // 76.125,
1178
+ // 10.5
1179
+ // ]
1180
+ // },
1181
+ // {
1182
+ // "location": [
1183
+ // 286.2954,
1184
+ // 416.05582,
1185
+ // 161.17517,
1186
+ // 10.5
1187
+ // ]
1188
+ // },
1189
+ // {
1190
+ // "location": [
1191
+ // 286.2954,
1192
+ // 436.8038,
1193
+ // 52.5,
1194
+ // 10.5
1195
+ // ]
1196
+ // },
1197
+ // {
1198
+ // "location": [
1199
+ // 338.7992,
1200
+ // 435.73584,
1201
+ // 12.0,
1202
+ // 12.0
1203
+ // ]
1204
+ // }
1205
+ // ]
1206
+ // }
1207
+ // }
1208
+ // }
1209
+ // ],
1210
+ // "code": "0",
1211
+ // "msg": null,
1212
+ // "traceId": null
1213
+ // }
1214
+ if (res.data.code == 0) {
1215
+ // tagIds 会按照gpt识别的生成有序的数组,前端直接按照下标的顺序取就可以了
1216
+ // 缓存拿到的所有数据
1217
+ this.cachePdf = res.data.data
1218
+ let publicPageFileUrl = res.data.data && res.data.data[0] ? res.data.data[0].publicPageFileUrl : ''
1219
+ this.currentPage = 0
1220
+ if (publicPageFileUrl && publicPageFileUrl.substring(publicPageFileUrl.lastIndexOf('.')) === '.pdf') {
1221
+ this.preViewType = 'pdf'
1222
+ this.setPageAllLine(this.cachePdf)
1223
+ this.getpdfResloutePage(res.data.data[0])
1224
+ } else {
1225
+ this.preViewType = 'excal'
1226
+ this.$http.post(
1227
+ '/knowledge-api/temporary-certificate/or-origin?expired=30',
1228
+ publicPageFileUrl,
1229
+ {
1230
+ headers: {
1231
+ "Content-Type": "application/json",
1232
+ },
1233
+ }).then(res => {
1234
+ // 使用原声请求方式 axios会带有不需要的请求头
1235
+ let xhr = new XMLHttpRequest();
1236
+ xhr.open('GET', res.data || res.bodyText, true);
1237
+ // 定义请求完成的处理函数,请求前也可以增加加载框/禁用下载按钮逻辑
1238
+ xhr.onload = ({ currentTarget }) => {
1239
+ // 请求完成
1240
+ if (currentTarget.status === 200) { // 返回200
1241
+ let pdf_view = document.getElementsByClassName('pdf_view');
1242
+ if (pdf_view && pdf_view[0]){
1243
+ pdf_view[0].style.backgroundImage = 'none'
1244
+ }
1245
+ this.contentView.innerHTML = currentTarget.response
1246
+ this.contentView.style.padding = '10px'
1247
+ // this.contentView.style.position = 'relative'
1248
+ this.$refs.pdfView.style.backgroundColor = '#FFFFFF'
1249
+ this.$refs.pdfView.appendChild(this.contentView)
1250
+
1251
+ let allTr = Array.from(this.$refs.pdfView.getElementsByTagName('tr'))
1252
+ this.allTr = []
1253
+ for (let index = 0; index < allTr.length; index++) {
1254
+ if (value.includes(allTr[index].getAttribute('tag-id'))) {
1255
+ this.allTr.push(allTr[index])
1256
+ }
1257
+ }
1258
+ this.currentChange(1)
1259
+
1260
+ }
1261
+ }
1262
+ xhr.send();
1263
+ })
1264
+ }
1265
+ } else {
1266
+ let div = document.createElement('div')
1267
+ div.innerText = '文件加载异常'
1268
+ this.contentView.appendChild(div)
1269
+ this.$refs.pdfView.appendChild(this.contentView)
1270
+ }
1271
+ })
1272
+ }
1273
+ },
1274
+ deep: true,
1275
+ immediate: true
1276
+ }
1277
+ },
1278
+ mounted () {
1279
+ if (/(iPhone|iPad|iPod|iOS|Android)/i.test(navigator.userAgent)) {
1280
+ this.isPC = false
1281
+ } else {
1282
+ this.isPC = true
1283
+ }
1284
+ }
1285
+ }
1286
+ </script>
1287
+
1288
+ <style lang="less" scoped>
1289
+ .pdf_view {
1290
+ width: 100%;
1291
+ height: calc(100% - 110px);
1292
+ overflow: auto;
1293
+ //overflow-y: scroll;
1294
+ background-color: #f5f7fb;
1295
+ // margin-bottom: 60px;
1296
+ box-sizing: border-box;
1297
+ background-image: url('https://guoranopen-zjk.oss-cn-zhangjiakou.aliyuncs.com/cdn-common/images/loading.gif');
1298
+ background-position: center;
1299
+ background-size: 50px;
1300
+ background-repeat: no-repeat;
1301
+ // position: relative;
1302
+ // > div {
1303
+ // width: 100%;
1304
+ // height: 100%;
1305
+ // overflow: hidden;
1306
+ // overflow-y: auto;
1307
+ // position: relative;
1308
+ // }
1309
+ >iframe {
1310
+ width: 100%;
1311
+ height: 100%;
1312
+ }
1313
+
1314
+ a:link {
1315
+ color: none;
1316
+ }
1317
+
1318
+ a:visited {
1319
+ color: none;
1320
+ }
1321
+
1322
+ a:hover {
1323
+ color: none;
1324
+ }
1325
+
1326
+ a:active {
1327
+ color: none;
1328
+ }
1329
+ .btn_footer {
1330
+ width: 100%;
1331
+ height: 60px;
1332
+ display: flex;
1333
+ align-items: center;
1334
+ justify-content: space-around;
1335
+ position: absolute;
1336
+ bottom: 0px;
1337
+ left: 0;
1338
+ z-index: 999;
1339
+ background: #ffffff;
1340
+
1341
+ .prev,
1342
+ .next {
1343
+ width: 35%;
1344
+ height: 40px;
1345
+ display: flex;
1346
+ align-items: center;
1347
+ justify-content: center;
1348
+ border-radius: 50px;
1349
+ cursor: pointer;
1350
+ }
1351
+
1352
+ .prev {
1353
+ background: #F2F5FA;
1354
+ color: #000;
1355
+ }
1356
+
1357
+ .next {
1358
+ background: #366aff;
1359
+ color: #ffffff;
1360
+ }
1361
+ }
1362
+
1363
+ #pagination {
1364
+ .total-class {
1365
+ margin-right: 13px;
1366
+ font-weight: 400;
1367
+ }
1368
+
1369
+ position: absolute;
1370
+ bottom: 0px;
1371
+ right: 0;
1372
+ width: 100%;
1373
+ display: flex;
1374
+ align-items: center;
1375
+ justify-content: center;
1376
+ height: 50px;
1377
+ background-color: white;
1378
+ box-shadow: 0px 0px 18px 0px rgba(29, 55, 129, 0.07);
1379
+ border-radius: 5px;
1380
+ z-index: 1000;
1381
+
1382
+
1383
+
1384
+ /deep/.el-pagination {
1385
+ margin-right: 110px;
1386
+ }
1387
+
1388
+ /deep/.el-pager {
1389
+ background: #EDF0F6;
1390
+ border-radius: 15px;
1391
+ }
1392
+
1393
+ /deep/.el-pagination.is-background .btn-next {
1394
+ width: 30px;
1395
+ height: 30px;
1396
+ background: #EDF0F6;
1397
+ border-radius: 50%;
1398
+ }
1399
+
1400
+ /deep/.el-pagination .btn-next {
1401
+ width: 30px;
1402
+ height: 30px;
1403
+ background: #EDF0F6;
1404
+ border-radius: 50%;
1405
+ padding-left: 0;
1406
+ margin-left: 5px;
1407
+ }
1408
+
1409
+ /deep/.el-pagination .btn-prev {
1410
+ width: 30px;
1411
+ height: 30px;
1412
+ background: #EDF0F6;
1413
+ border-radius: 50%;
1414
+ padding-right: 0;
1415
+ margin-right: 5px;
1416
+ }
1417
+
1418
+ /deep/.el-pagination button {
1419
+ padding: 0;
1420
+ min-width: 30px;
1421
+ }
1422
+
1423
+ /deep/.el-pager li {
1424
+ background: #EDF0F6;
1425
+ height: 30px;
1426
+ min-width: 30px;
1427
+ line-height: 30px;
1428
+ font-size: 12px;
1429
+ color: #717b90;
1430
+ }
1431
+
1432
+ /deep/.el-pager li:first-child {
1433
+ border-bottom-left-radius: 15px !important;
1434
+ border-top-left-radius: 15px !important;
1435
+ }
1436
+
1437
+ /deep/.el-pager li:last-child {
1438
+ border-top-right-radius: 15px !important;
1439
+ border-bottom-right-radius: 15px !important;
1440
+ }
1441
+
1442
+ /deep/.el-pager li.active {
1443
+ width: 30px;
1444
+ height: 30px;
1445
+ min-width: 30px;
1446
+ background: #366AFF;
1447
+ border: 3px solid #A1B9FF;
1448
+ border-radius: 50%;
1449
+ line-height: 24px;
1450
+ color: white;
1451
+ }
1452
+
1453
+ /deep/.el-pagination.is-background .el-pager li:not(.disabled).active {
1454
+ background: #366AFF;
1455
+ }
1456
+ }
1457
+
1458
+ .change_scale {
1459
+ width: 100%;
1460
+ height: 50px;
1461
+ position: absolute;
1462
+ top: 50px;
1463
+ left: 0;
1464
+ background: #ffffff;
1465
+ display: flex;
1466
+ align-items: center;
1467
+ padding: 0 10px;
1468
+ box-sizing: border-box;
1469
+
1470
+ section {
1471
+ cursor: pointer;
1472
+ width: 30px;
1473
+ height: 30px;
1474
+ margin-right: 5px;
1475
+ border-radius: 5px;
1476
+ display: flex;
1477
+ align-items: center;
1478
+ justify-content: center;
1479
+
1480
+ i {
1481
+ font-weight: 900;
1482
+ }
1483
+ }
1484
+
1485
+ section:hover {
1486
+ background: rgba(221, 222, 223, 1);
1487
+ }
1488
+ }
1489
+ .pdf_container_view{
1490
+ height: 100%;
1491
+ width: 100%;
1492
+ position: relative;
1493
+ overflow: auto;
1494
+ }
1495
+ }
1496
+ </style>
1497
+ <style lang="less">
1498
+ .animation {
1499
+ animation-name: highlight;
1500
+ animation-duration: 4s;
1501
+ }
1502
+
1503
+ @keyframes highlight {
1504
+ 0% {
1505
+ background: rgba(255, 136, 0, 0.3);
1506
+ }
1507
+ 25% {
1508
+ background: rgba(255, 136, 0, 0.6);
1509
+ }
1510
+
1511
+ 50% {
1512
+ background: rgba(255, 136, 0, 0.3);
1513
+ }
1514
+
1515
+ 75% {
1516
+ background: rgba(255, 136, 0, 0.6);
1517
+ }
1518
+
1519
+ 100% {
1520
+ background: rgba(255, 136, 0, 0.3);
1521
+ }
1323
1522
  }</style>