mirror of
https://github.com/501351981/vue-office.git
synced 2025-06-15 07:00:00 +08:00
✨ feat(OfficePdf):Lazy loading
VueOfficePdf has added lazy loading functionality, where it initially loads 5 pages by default and subsequently implements lazy loading as you scroll.
This commit is contained in:
parent
f03c6b1de9
commit
92e6a70f52
@ -1,9 +1,9 @@
|
||||
<script>
|
||||
import {defineComponent, ref, onMounted, watch} from 'vue-demi';
|
||||
import { defineComponent, ref, onMounted, watch } from 'vue-demi';
|
||||
import workerStr from './worker?raw';
|
||||
import pdfjsLib from './pdf?raw';
|
||||
import {download as downloadFile, getUrl, loadScript} from '../../../utils/url';
|
||||
import {base64_encode} from '../../../utils/base64';
|
||||
import { download as downloadFile, getUrl, loadScript } from '../../../utils/url';
|
||||
import { base64_encode } from '../../../utils/base64';
|
||||
import omit from 'lodash/omit';
|
||||
|
||||
const pdfJsLibSrc = `data:text/javascript;base64,${(base64_encode(pdfjsLib))}`;
|
||||
@ -27,18 +27,21 @@ export default defineComponent({
|
||||
}
|
||||
},
|
||||
emits: ['rendered', 'error'],
|
||||
setup(props, {emit}) {
|
||||
setup(props, { emit }) {
|
||||
let pdfDocument = null;
|
||||
let loadingTask = null;
|
||||
const rootRef = ref([]);
|
||||
const numPages = ref(0);
|
||||
|
||||
const lazySize = ref(5);
|
||||
const pageSize = ref(lazySize.value);
|
||||
|
||||
function installPdfScript() {
|
||||
return loadScript(pdfJsLibSrc).then(() => {
|
||||
if(window.pdfjsLib){
|
||||
if (window.pdfjsLib) {
|
||||
window.pdfjsLib.GlobalWorkerOptions.workerSrc = PdfJsWorkerSrc;
|
||||
}else{
|
||||
return Promise.reject('window.pdfjsLib未找到');
|
||||
} else {
|
||||
return Promise.reject('window.pdfjsLib未找到');
|
||||
}
|
||||
});
|
||||
}
|
||||
@ -64,16 +67,26 @@ export default defineComponent({
|
||||
});
|
||||
loadingTask.promise.then((pdf) => {
|
||||
pdfDocument = pdf;
|
||||
numPages.value = pdfDocument.numPages;
|
||||
numPages.value = Math.min(pdfDocument.numPages, lazySize.value);
|
||||
renderPage(1);
|
||||
}).catch((e) => {
|
||||
emit('error', e);
|
||||
});
|
||||
}
|
||||
|
||||
function onScrollPdf(e) {
|
||||
const { scrollTop, scrollHeight, clientHeight } = e.target;
|
||||
if (scrollTop + clientHeight >= scrollHeight) {
|
||||
if (numPages.value < pdfDocument.numPages) {
|
||||
numPages.value += Math.min(lazySize.value, pdfDocument.numPages)
|
||||
renderPage(1);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
function renderPage(num) {
|
||||
pdfDocument.getPage(num).then((pdfPage) => {
|
||||
const viewport = pdfPage.getViewport({scale: 2});
|
||||
const viewport = pdfPage.getViewport({ scale: 2 });
|
||||
const outputScale = window.devicePixelRatio || 1;
|
||||
|
||||
const canvas = rootRef.value[num - 1];
|
||||
@ -89,7 +102,7 @@ export default defineComponent({
|
||||
domWidth = Math.floor(props.options.width);
|
||||
domHeight = Math.floor(domHeight * scale);
|
||||
}
|
||||
if(domWidth > document.documentElement.clientWidth){
|
||||
if (domWidth > document.documentElement.clientWidth) {
|
||||
let scale = document.documentElement.clientWidth / domWidth;
|
||||
domWidth = Math.floor(document.documentElement.clientWidth);
|
||||
domHeight = Math.floor(domHeight * scale);
|
||||
@ -124,46 +137,38 @@ export default defineComponent({
|
||||
|
||||
onMounted(() => {
|
||||
if (props.src) {
|
||||
checkPdfLib().then(init).catch(e=>{
|
||||
checkPdfLib().then(init).catch(e => {
|
||||
console.warn(e);
|
||||
});
|
||||
}
|
||||
});
|
||||
|
||||
watch(() => props.src, () => {
|
||||
checkPdfLib().then(init).catch(e=>{
|
||||
checkPdfLib().then(init).catch(e => {
|
||||
console.warn(e);
|
||||
});
|
||||
});
|
||||
function save(fileName){
|
||||
pdfDocument && pdfDocument._transport && pdfDocument._transport.getData().then(fileData=>{
|
||||
downloadFile(fileName || `vue-office-pdf-${new Date().getTime()}.pdf`,fileData.buffer);
|
||||
function save(fileName) {
|
||||
pdfDocument && pdfDocument._transport && pdfDocument._transport.getData().then(fileData => {
|
||||
downloadFile(fileName || `vue-office-pdf-${new Date().getTime()}.pdf`, fileData.buffer);
|
||||
});
|
||||
}
|
||||
return {
|
||||
rootRef,
|
||||
numPages,
|
||||
save
|
||||
save,
|
||||
onScrollPdf
|
||||
};
|
||||
}
|
||||
});
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<div class="vue-office-pdf" ref="vue-office-pdf" style="text-align: center;overflow-y: auto;">
|
||||
<div
|
||||
v-if="numPages"
|
||||
class="vue-office-pdf-wrapper"
|
||||
style="background: gray; padding: 30px 0;position: relative;">
|
||||
<canvas
|
||||
v-for="page in numPages"
|
||||
ref="rootRef"
|
||||
:key="page"
|
||||
style="width:100%"
|
||||
/>
|
||||
<div class="vue-office-pdf" ref="vue-office-pdf" style="text-align: center;overflow-y: auto;" @scroll="onScrollPdf">
|
||||
<div v-if="numPages" class="vue-office-pdf-wrapper" style="background: gray; padding: 30px 0;position: relative;">
|
||||
<canvas v-for="page in numPages" ref="rootRef" :key="page" style="width:100%" />
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
<style lang="less">
|
||||
|
||||
</style>
|
||||
</style>
|
||||
|
Loading…
x
Reference in New Issue
Block a user