前端页面导出PDF

随声附和 提交于 2019-12-17 10:12:16

【推荐】2019 Java 开发者跳槽指南.pdf(吐血整理) >>>

这是一个封装了的vue组件, 简单设置了导出的头, 内容, 底部. 内容可翻页. 实现导出列表所有页数.

实现是基于html2canvas把页面转换为图片, 然后使用jspdf把生成的图片直接添加到pdf里面.

html2canvas 配置参考 地址

JSPDFS Github地址

js操作blob的大小限制, 网上找的图.

使用

<export-pdf-view
                        ref="pdf"
                        :begin="begin"
                        :flush-content="loadList"
                        :end="end"
                        save-name="设备使用记录.pdf"
                        class="recharge">
</export-pdf-view>

注: 回调函数需要返回 Promise , 如果回调函数内部有修改数据, 注意dom刷新后再调用Promise的res. 所有回调函数均在生成前调用

  1. ref 使用ref来调用组件内部的方法 $refs.recharge.exportPDF() 导出pdf
  2. 回调函数 begin 开始导出时调用
  3. 回调函数 flush-content 开始导出内容时调用, 此方法会重复调用. 直到 Promise 的 res(false) 时结束, //可在这里重复加载列表数据
  4. 回调函数 end 生成pdf底部时调用

ExportPdfView.vue

<template>
    <div class="pdf-view">
        <div ref="header" class="header">
            <slot name="header"></slot>
        </div>
        <div ref="content" class="content">
            <slot name="content"></slot>
        </div>
        <div ref="footer" class="footer">
            <slot name="footer"></slot>
        </div>
    </div>
</template>

<script>
    import FileSaver from 'file-saver';//可能需要
    import html2canvas from 'html2canvas';
    import PDF from 'jspdf';

    let pdfWidth = 592.28;
    let pdfHeight = 841.89;

    export default {
        name: "ExportPdfView",
        props: ['begin', 'flushContent', 'end', 'saveName'],
        data() {
            return {

            }
        },
        methods: {
            exportPDF(){

                let pdf = new PDF('', 'pt', 'a4');
                let h2cOpt = {backgroundColor: '#fff', scale: 4};
                let nowHeight = 0;

                let appendToPDF = (canvas, dom) => {
                    let domHeight = pdfWidth / dom.offsetWidth * dom.offsetHeight;
                    if(domHeight <= 0){
                        return;
                    }
                    //console.log('pdfHeight:' + pdfHeight, 'domHeight:' + domHeight, 'nowHeight:' + nowHeight);
                    if(nowHeight + domHeight > pdfHeight){
                        pdf.addPage();
                        nowHeight = 0;
                    }

                    let data = canvas.toDataURL('image/jpeg', 1);
                    pdf.addImage(data, 'JPEG', 0, nowHeight, pdfWidth, domHeight);
                    nowHeight += domHeight;
                }

                let buildPDF = async () => {
                    console.log('开始导出pdf...');
                    if(this.begin){
                        await this.begin();
                    }
                    appendToPDF(await html2canvas(this.$refs.header, h2cOpt), this.$refs.header);
                    let res = false;
                    do{
                        res = await this.flushContent();
                        console.log('刷新pdf内容...', res);
                        appendToPDF(await html2canvas(this.$refs.content, h2cOpt), this.$refs.content);
                    } while (res);
                    if(this.end){
                        await this.end();
                    }
                    appendToPDF(await html2canvas(this.$refs.footer, h2cOpt), this.$refs.footer);
                    console.log('结束pdf导出, 保存到文件...');
                    pdf.save(this.saveName || 'export.pdf');
                }
                this.$nextTick( _ => {
                    buildPDF();
                });
            }
        }
    }
</script>

<style scoped lang="less">
.pdf-view{
    //width: 592.28px;
    display: table;
    margin: 0 auto;
    font-size: 12px;

    .header{

    }
    .content{

    }
    .footer{

    }
}
</style>

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!