canvas 绘制 的简单使用 绘制图像 绘制文字 绘制线条 生成图片并本地下载 以及注意事项

近期的项目里用到了一个 绘制 录取通知书的功能  我想到使用canvas 来绘制 顺便记录一下遇到的问题

写一个 画布组件 这个组件带有 width  和 height 属性 用来设置 宽高 id用于获取document元素

<canvas id="canvas" width="800" height="516"></canvas>

然后就是 获取元素并创建上下文对象


let canvas;

let ctx;

canvas = document.getElementById('canvas');
    //上下文对象
ctx = canvas.getContext('2d');

//使用vue 的话 讲变量声明在最外层 并在 初始化完成之后获取 


//vue3 onMounted

onMounted(()=>{

    //确保组件以及渲染 之后再获取元素 
    nextTick(()=>{
        draw();
    })

})


function draw(){
    canvas = document.getElementById('canvas');
        //上下文对象
    ctx = canvas.getContext('2d');
}


绘制图像

image图像 x y 图像在画布的坐标 width height 图像绘制的宽高


ctx.drawImage(image, x, y, width, height);



需要注意的是 image 需要时一个img元素

img 可以是document.getElement... 获取html 中的元素

也可以通过 new Image() 创建

let image = new Image();

//图片加载完成的回调
image.onload = () => {
    ctx.drawImage(image, x, y, width, height);
}

//给image的src属性赋值 赋值之后等图片加载完成 调用 onload回调 完成绘制
image.src = 'http://......' 图片链接  也可以是本地引入的图片资源 注意不能使用本地路径

需要注意 canvas 绘制 是后面绘制覆盖前面的

而图片加载是一个异步的功能

如果你需要绘制多个图片需要前面绘制的图片绘制完成之后再去绘制下一张图像 不然可能出现 一些需要显示在上方的图像 因为加载速度原因 被遮盖

我的解决方案为

let canvas;
let ctx;

async function draw(){

    canvas = document.getElementById('canvas');

    ctx = canvas.getContext('2d');
    
    // 此处img 是一个图片链接
    await drawImg(img, 67, 251, 133, 186);
    //await 等待前面图像绘制完成之后再开始绘制下一张 保证绘制元素的显示层级
    await drawImg(img, 10, 10, 120, 133);

    ...绘制其他元素
}


function drawImg(img, x, y, width, height){
    return new Promise((resolve, reject) => {
        let image = new Image();
        image.onload = () => {
            ctx.drawImage(image, x, y, width, height);
            resolve();
        };
        image.src = img;
    });
}

绘制文字

function drawText(){
    //设置文字的样式
    ctx.font = '20px Arial';
    //设置文字的颜色
    ctx.fillStyle = '#333333';    
    //绘制文字
    ctx.fillText('绘制内容', 380, 285);

    
}

如果你后续需要绘制其他样式的文字 重新设置文字样式 然后绘制就可以了

function drawText(){

    //绘制粗体文字
    ctx.font = 'bold 30px Arial';
    ctx.fillStyle = 'red';
    ctx.fillText('文字', 380, 285);
}

绘制线条 

    //线条的颜色
    ctx.strokeStyle = 'black';
    //宽度
    ctx.lineWidth = 1;
    // 开始新的线条绘制
    ctx.beginPath();
    // 线条的起始位置
    ctx.moveTo(startX, startY);
    //线条的结束位置
    ctx.lineTo(endX, endY);
    //绘制
    ctx.stroke();

//封装函数
function drawLine(startX, startY, endX, endY){
    ctx.beginPath();
    ctx.moveTo(startX, startY);
    ctx.lineTo(endX, endY);
    ctx.stroke();
}

转为图片并下载

    //创建一个 a标签
    const el = document.createElement('a');
    //将绘制好的canvas 转换为图像链接 base64格式
    el.href = canvas.toDataURL('image/png');
    //设置元素下载名称
    el.download = '录取通知书.png';
    //触发点击时间开始下载
    el.click();
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值