如何实现vue导出网页为pdf

1、准备一个vue 的项目安装依赖,两个命令,第一个命令把网页转成图片,第二个是图片转成pdf.

因此,vue导出网页为pdf 的原理就是先把网页生成成图片,在把图片写到pdf中,正因为这个原理,造成这种方式的一些缺点,比如,可能引发黑色阴影,分页分割问题等瑕疵。

npm install html2canvas --save
npm install jspdf --save

2、引入依赖

import html2canvas from 'html2canvas';
import JsPDF from 'jspdf';

3、加入导出方法

<div @click="downloadPdf('main')">导出PDF</div>
<div id="main">
    此区域的所有代码渲染的效果都会导出
</div>
methods: {
            printOutpdf(name) {
                let shareContent = document.body,
                width = shareContent.clientWidth, //宽度
                height = shareContent.clientHeight, //高度
                canvas = document.createElement("canvas"),
                scale = 2; //定义任意放大倍数 支持小数
                canvas.width = width * scale; //定义canvas 宽度 * 缩放
                canvas.height = height * scale; //定义canvas高度 *缩放
                canvas.style.width = shareContent.clientWidth * scale + "px";
                canvas.style.height = shareContent.clientHeight * scale + "px";
                canvas.getContext("2d").scale(scale, scale); //获取context,设置scale
                let opts = {
                    scale: scale, // 添加的scale 参数
                    canvas: canvas, //自定义 canvas
                    logging: false, //日志开关,便于查看html2canvas的内部执行流程
                    width: width, //dom 原始宽度
                    height: height,
                    useCORS: true, // 【重要】开启跨域配置
                };
                //开始转换
                html2canvas(shareContent).then(canvas => {
                    var contentWidth = canvas.width;
                    var contentHeight = canvas.height;
                    //一页pdf显示html页面生成的canvas高度;
                    var pageHeight = (contentWidth / 592.28) * 841.89;
                    //未生成pdf的html页面高度
                    var leftHeight = contentHeight;
                    //页面偏移
                    var position = 0;
                    //a4纸的尺寸[595.28,841.89],html页面生成的canvas在pdf中图片的宽高
                    var imgWidth = 595.28;
                    var imgHeight = (592.28 / contentWidth) * contentHeight;
                    var pageData = canvas.toDataURL("image/jpeg", 1.0);
                    var PDF = new JsPDF("", "pt", "a4");
                    if (leftHeight < pageHeight) {
                        PDF.addImage(pageData, "JPEG", 0, 0, imgWidth, imgHeight);
                    } else {
                        while (leftHeight > 0) {
                            PDF.addImage(pageData, "JPEG", 0, position, imgWidth, imgHeight);
                            leftHeight -= pageHeight;
                            position -= 841.89;
                            if (leftHeight > 0) {
                                PDF.addPage();
                            }
                        }
                    }
                    PDF.save(name + ".pdf"); // 这里是导出的文件名
                });
            },
}

提示:页面如果太长,可能会报错,诸如之前博主遇到的,调取一个手机号的通讯记录生成报表并导出,由于页面内容过长,导出不友好,那就只能用后端导出。

4、wkhtmltopdf 后端导出html为pdf

下载地址

https://wkhtmltopdf.org/downloads.html

https://github.com/wkhtmltopdf/wkhtmltopdf/releases

import java.io.File;
import java.util.Date;


public class Wkhtmltopdf {
    //wkhtmltopdf 在系统中的路径
    private static final String toPdfTool = "C:\\Users\\DELL\\Downloads\\wkhtmltox-0.12.5-1.msvc2015-win64\\bin\\wkhtmltopdf.exe";
    public static void main(String[] args) {
        Date date = new Date();
        String fileName = String.valueOf(date.getTime()) + ".pdf";
        convert("https://www.csdn.net/", "F:\\" + fileName);
    }
    /**
     *  * html转pdf
     *  *
     *  * @param srcPath  html路径,可以是硬盘上的路径,也可以是网络路径
     *  * @param destPath pdf保存路径
     *  * @return 转换成功返回true
     *  
     */
    public static boolean convert(String srcPath, String destPath) {
        File file = new File(destPath);
        File parent = file.getParentFile();
        //如果pdf保存路径不存在,则创建路径
        if (!parent.exists()) {
            parent.mkdirs();
        }
        StringBuilder cmd = getFormal();
        //html路径 即目标网页路径
        cmd.append(" ");
        cmd.append(srcPath);
        cmd.append(" ");
        //pdf保存路径
        cmd.append(destPath);
        boolean result = true;
        try {
            Process proc = Runtime.getRuntime().exec(cmd.toString());
            HtmlToPdfInterceptor error = new HtmlToPdfInterceptor(proc.getErrorStream());
            HtmlToPdfInterceptor output = new HtmlToPdfInterceptor(proc.getInputStream());
            error.start();
            output.start();
            proc.waitFor();
        } catch (Exception e) {
            result = false;
            e.printStackTrace();
        }
        return result;
    }
    /**
     *  * 标准格式
     *  *
     *  * @return
     *  
     */
    public static StringBuilder getFormal() {
        StringBuilder cmd = new StringBuilder();
        //wkhtmltopdf 在系统中的路径
        cmd.append(toPdfTool);
        cmd.append(" ");
//        cmd.append(" --header-line");//页眉下面的线
//   cmd.append("  --footer-line");//页脚上面的线
//        cmd.append("  --footer-center [page]/[topage]"); //在页脚中心放置页码
//   cmd.append("  --header-right 这里是我们系统的页眉"); //页眉中间放置文字
//        cmd.append("  --header-html http://localhost:8090/myheader.html"); //页眉中间放置图片
//        cmd.append("  --header-spacing 5 ");// (设置页眉和内容的距离,默认0 )
//        cmd.append("  --margin-top 20mm  "); //设置页面上边距 (default 10mm)
//        cmd.append(" cover http://localhost:8090/firstPage.html ");
        return cmd;
    }
    public static StringBuilder test1() {
        StringBuilder cmd = new StringBuilder();
        //wkhtmltopdf 在系统中的路径
        cmd.append(toPdfTool);
//   cmd.append(" --cover http://localhost:8090/firstPage.html");
        cmd.append(" -T 15mm");
        cmd.append(" --header-spacing 5");
        cmd.append(" --outline");
        cmd.append(" cover http://image.baidu.com");
        cmd.append(" ");
        return cmd;
    }

}

package top.cfl.cflwork.util;


import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;


/**
  * 当java调用wkhtmltopdf时,用于获取wkhtmltopdf返回的内容
  */
public class HtmlToPdfInterceptor extends Thread {
    private InputStream is;


    public HtmlToPdfInterceptor(InputStream is) {
        this.is = is;
    }


    public void run() {
        try {
            InputStreamReader isr = new InputStreamReader(is, "utf-8");
            BufferedReader br = new BufferedReader(isr);
            String line = null;
            while ((line = br.readLine()) != null) {
                System.out.print(line.toString()); //输出内容
            }
        } catch (IOException e) {
            e.printStackTrace();
        }
    }

}

猜你喜欢

转载自blog.csdn.net/xljx_1/article/details/104110762