下载pdf

作者: 1263536889 | 来源:发表于2021-02-22 15:01 被阅读0次

    /* eslint-disable prefer-destructuring */
    // 不使用JQuery版的

    import html2canvas from 'html2canvas';
    import JsPDF from 'jspdf';
    import _ from 'lodash';

    /**

    • @param ele 要生成 pdf 的DOM元素(容器)
    • @param padfName PDF文件生成后的文件名字
    • */

    async function downloadPDF(ele, pdfName) {
    const eleW = ele.offsetWidth; // 获得该容器的宽
    const eleH = ele.offsetHeight; // 获得该容器的高

    const eleOffsetTop = ele.offsetTop; // 获得该容器到文档顶部的距离
    const eleOffsetLeft = ele.offsetLeft; // 获得该容器到文档最左的距离

    const canvas = document.createElement('canvas');
    let abs = 0;

    const winIn = document.documentElement.clientWidth || document.body.clientWidth; // 获得当前可视窗口的宽度(不包含滚动条)
    const winOut = window.innerWidth; // 获得当前窗口的宽度(包含滚动条)

    if (winOut > winIn) {
    abs = (winOut - winIn) / 2; // 获得滚动条宽度的一半
    }

    canvas.width = eleW * 2; // 将画布宽&&高放大两倍
    canvas.height = eleH * 2;

    const context = canvas.getContext('2d');

    context.scale(2, 2);
    context.translate(-eleOffsetLeft - abs, -eleOffsetTop);
    // 缩放比例
    const scale = 794 / eleW;
    const handlerData = async el => {
    const canvas = await html2canvas(el, {
    dpi: 300,
    useCORS: true,
    });
    const pageData = canvas.toDataURL('image/jpeg', 1.0);
    const contentWidth = canvas.width;
    const contentHeight = canvas.height;
    const imgWidth = 595.28;
    const imgHeight = (595.28 / contentWidth) * contentHeight;
    return {
    pageData,
    imgWidth,
    imgHeight,
    };
    };
    // 元素分组
    const handlerImage = e => {
    if (_.isEmpty(e)) return [];
    return _.map(e, el => {
    if (el.offsetHeight * scale > 1123) {
    return handlerImage(el.children);
    }
    return el;
    });
    };
    const nodes = _.flattenDeep(handlerImage(ele.children));
    // 元素分组
    const data = []; // --------------
    nodes.forEach((e, index) => {
    if (!index) {
    data.push([e]);
    } else {
    const h = _.sumBy(data[data.length - 1], 'offsetHeight') + e.offsetHeight;
    if (h * scale > 1123) {
    data.push([e]);
    } else {
    data[data.length - 1].push(e);
    }
    }
    });
    // 找到元素的offsetParent 为 main
    const getoffsetTop = (e, h) => {
    if (e.offsetParent.tagName === 'MAIN') {
    return e.offsetTop + h;
    }
    return getoffsetTop(e.offsetParent, h);
    };
    const a = data.map(e => {
    // --------------
    if (e[0].offsetParent.tagName === 'MAIN') {
    return e[0].offsetTop;
    }
    return getoffsetTop(e[0].offsetParent, e[0].offsetTop);
    });

    const image = a.map((e, index) => {
    if (index === a.length - 1) return eleH - e - 24;
    return Math.abs(a[index + 1] - e);
    });
    // imageData.pageData base64
    const imageData = await handlerData(ele);

    // create div
    const div = document.createElement('div');
    div.id = 'imgdiv';
    const img = new Image();
    img.src = imageData.pageData;
    img.width = imageData.imgWidth;
    img.height = imageData.imgHeight;
    img.id = 'dowanloadImg';
    div.appendChild(img);
    document.getElementById('download').appendChild(div);
    // 分块 画img
    const canvasImage = (imgData, x, y, nHeight, index) => {
    const canvasOther = document.createElement('canvas');
    canvasOther.width = eleW;
    canvasOther.height = nHeight;
    canvasOther.id = id-${index};
    canvasOther.type = 'canvasOther';
    const ctx = canvasOther.getContext('2d');
    ctx.drawImage(imgData, x, y, eleW, nHeight, 0, 0, eleW, nHeight); // 重绘
    const data = canvasOther.toDataURL('image/jpeg', 1.0);
    document.getElementById('imgdiv').appendChild(canvasOther);

    const width = 595.28;
    const height = (595.28 / eleW) * nHeight;
    return {
      data,
      width,
      height,
    };
    

    };
    // imgData 整张图片信息
    const imgData = document.getElementById('dowanloadImg');
    imgData.onload = async () => {
    // 根据image信息把imgData循环切割成多个图片
    const imageArray = image.map(async (nHeight, index) => {
    const data = await canvasImage(imgData, 0, _.sum(index ? _.chunk(image, index)[0] : [0]), nHeight, index);
    return data;
    });
    // del node
    document.getElementById('download').removeChild(document.getElementById('imgdiv'));
    // img => pdf
    const images = await Promise.all(imageArray);
    const {
    length,
    } = images;
    const pdf = new JsPDF('', 'pt', 'a4');
    images.forEach((e, index) => {
    const {
    data,
    width,
    height,
    } = e;
    const h = index ? 10 : 0;
    pdf.addImage(data, 'JPEG', -3, h, width, height);
    if (index === length - 1) return;
    pdf.addPage();
    });
    pdf.save(pdfName);
    };
    }

    export default {
    downloadPDF,
    };

    相关文章

      网友评论

          本文标题:下载pdf

          本文链接:https://www.haomeiwen.com/subject/rborgctx.html