You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

JSPDF搭配html2Canvas在IOS浏览器中无法下载PDF文件问题

问题根因

iOS端浏览器(尤其是Safari内核的所有浏览器)存在两个和该功能相关的兼容性限制:

  • iOS Safari对canvas最大可渲染尺寸有严格限制,超过上限后canvas.toDataURL()会返回空值,导致后续PDF生成逻辑中断
  • jsPDF默认的save()方法在iOS下受浏览器安全策略限制,无法直接触发文件下载行为

修复方案

你可以直接替换原有JS代码为下方兼容版本:

$('#print').click(function (e) { 
    e.preventDefault();
    let HTML_Width = $(".report").width();
    let HTML_Height = $(".report").height();
    let top_left_margin = 1;
    let PDF_Width = HTML_Width + (top_left_margin * 2);
    let PDF_Height = (PDF_Width * 1.5) + (top_left_margin * 2);
    let canvas_image_width = HTML_Width;
    let canvas_image_height = HTML_Height;

    // 适配iOS canvas尺寸限制,超过最大尺寸自动缩放
    const MAX_IOS_CANVAS_HEIGHT = 16384;
    let scaleRate = 1;
    if (HTML_Height > MAX_IOS_CANVAS_HEIGHT) {
        scaleRate = MAX_IOS_CANVAS_HEIGHT / HTML_Height;
        canvas_image_width = HTML_Width * scaleRate;
        canvas_image_height = HTML_Height * scaleRate;
    }

    let totalPDFPages = Math.ceil(HTML_Height / PDF_Height) - 1;

    html2canvas($(".report")[0], {
        scale: scaleRate, // 传入缩放参数,避免canvas尺寸超限
        useCORS: true, // 存在跨域图片时需要保留该配置
        logging: false
    }).then(function (canvas) {
        let imgData = canvas.toDataURL("image/jpeg", 1.0);
        let pdf = new jsPDF('p', 'pt', [PDF_Width, PDF_Height]);
        pdf.addImage(imgData, 'JPG', top_left_margin, top_left_margin, canvas_image_width, canvas_image_height, 'FAST');
        for (let i = 1; i <= totalPDFPages; i++) {
            pdf.addPage(PDF_Width, PDF_Height);
            pdf.addImage(imgData, 'JPG', top_left_margin, -(PDF_Height * i) + (top_left_margin * 4), canvas_image_width, canvas_image_height);
        }

        // 替换默认save方法,手动适配iOS下载
        if (/(iPhone|iPad|iPod)/i.test(navigator.userAgent)) {
            // iOS环境:手动生成blob并触发a标签下载
            const pdfBlob = pdf.output('blob');
            const blobUrl = URL.createObjectURL(pdfBlob);
            const a = document.createElement('a');
            a.href = blobUrl;
            a.download = 'Report.pdf';
            a.target = '_blank';
            document.body.appendChild(a);
            a.click();
            // 延迟释放资源,避免iOS下提前释放导致下载失败
            setTimeout(() => {
                document.body.removeChild(a);
                URL.revokeObjectURL(blobUrl);
            }, 1000);
        } else {
            // 非iOS环境用原有逻辑
            pdf.save("Report.pdf");
        }

        $(".html-content").hide();
    });
});

额外注意事项

  • 如果报表里包含跨域图片,需要确保图片服务配置了CORS头,否则iOS下图片会渲染空白
  • 不要给点击事件加额外的非用户触发的异步封装(比如非交互触发的setTimeout),否则iOS会判定为非用户主动操作,拦截下载行为

内容的提问来源于stack exchange,提问作者Osama Amr

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.26 02:27:02