使用canvas下载/打印图片,绘制文字、下划线

427 阅读2分钟

有一个心理测评项目,测评结束后,要使用echarts图表展示出来,并且可以下载/打印图表

1、获取到echarts并复制

let echarts = document.getElementsByTagName("canvas")[0];
let echartsCanvas = echarts.cloneNode(true); // 避免修改属性影响到页面上的图表
echartsCanvas.style.background = "#FFFFFF";

2、创建画布

let canvas = echartsCanvas.getContext("2d"); //创建画布

3、创建img

let img = new Image();
img.src = echarts.toDataURL();

4、在onload中绘制图形、位置、文字等

img.onload = () => {
    echartsCanvas.setAttribute("width", img.width);
    echartsCanvas.setAttribute("height", img.height+50);
    echartsCanvas.setAttribute("style", "background:#ffffff;");
    
    canvas.fillStyle = "rgba(255, 255, 255, 1)"; // 填充背景色
    canvas.fillRect(0, 0, img.width, img.height+50); // 制"已填充"的矩形
    // 绘制图片,drawImage(要绘制的图像, 在画布上放置图像的x坐标位置, 在画布上放置图像的y坐标位置, 要使用的图像的宽度, 要使用的图像的高度)
    canvas.drawImage(img, 0, 50, img.width, img.height); // 上方留出信息空白
    
    // 图片标题文字绘制
    canvas.font = "32px Arial";
    canvas.fillStyle = "black";
    let tittext = "测评结果";
    let titLength = tittext.length*32; // 文字整体宽度
    let position = echartsCanvas.width/2 - titLength/2;
    canvas.fillText(tittext, position, 30); // (要绘制的文字, 开始绘制文本的x坐标位置, 开始绘制文本的y坐标位置)
    
    // 绘制下划线
    canvas.beginPath(); // 开始一条路径
    canvas.moveTo(position, 40); // 开始绘制的位置, (开始绘制的X坐标, 开始绘制的y坐标)
    canvas.lineTo(position+titLength, 40); // 结束绘制的位置, (结束绘制的X坐标, 结束绘制的y坐标)
    canvas.strokeStyle = 'black'; // 下划线颜色
    canvas.stroke(); // 绘制下划线
    
    // 合成图片
    const synthesisUrl = echartsCanvas.toDataURL("image/png");
    // 下载图片
    downloadImg(synthesisUrl)
    // 打印图片
    printImg(synthesisUrl)
}

5、下载图片

downloadImg(synthesisUrl) {
    const alink = document.createElement("a"); // 创建a标签
    alink.href = synthesisUrl;
    alink.download = "测评结果"; // 重命名文件
    alink.click();
    URL.revokeObjectURL(synthesisUrl); // 释放内存
}

下载下来的图片,如图所示(没有给图表填充数据,仅做示例测试):

测评结果 (1).png

6、打印图片

打印内容,通常我是调起浏览器的打印(比如在浏览器空白处右键→点击打印,看到的那个效果),然后在浏览器打印中,由客户自己去设置要打印的纸张等设置

printImg(synthesisUrl) {
    const iframe = document.createElement("iframe");
    iframe.onload = () => {
       iframe.style.display = "none";
       let doc = iframe.contentWindow.document;
       doc.write(`
           <div style="display:flex; justify-content:center; align-items:center; flex-direction:column;">
              <div class="height" style="width:100%; height:20px;"></div>
              <img src="` + synthesisUrl + `" alt="Canvas Image" style="width: 100%;">
            </div>
        `);
        // 动态添加CSS以控制打印样式,隐藏页眉页脚
        let style = doc.createElement('style');
        style.type = 'text/css';
        style.innerHTML = `
            /* 只在火狐浏览器下生效的CSS */
            @-moz-document url-prefix() {
              @media print {
                    .height {
                      height: 20px;
                    }
                }
            }
            @media print {
                @page {
                    margin: 0;
                }
                body, html {
                    display:flex;
                    justify-content: center;
                    align-items: center;
                }
            }
        `;
        doc.head.appendChild(style);
        setTimeout(() => {
          iframe.contentWindow.print()
        },1000);
    }
    iframe.type = "application/pdf"
    document.body.appendChild(iframe);
}

调起浏览器打印如图所示:

QQ图片20240624141122.png