canvas 图片跨域(一)

版权声明:本文为博主原创文章,如若转载,请注明出处。 https://blog.csdn.net/qq_37837134/article/details/79957283

在项目中,需要生成海报。有动态信息(微信头像、微信昵称、上传图片(oss链接)、二维码)+ 海报背景图生成一张海报。

技术支持:canvas  生成。

问题:canvas 图片跨域。

解决过程(填坑历程):

                                   1.从网上存在如图解决办法     img.crossOrigin  = ""   (专业采坑,数年)。亲测无效。很是不解。


                                2.网上也存在后端服务解决

                                        A.设置header头,或者nginx 服务配置等  允许访问

                                 但是,存在问题(图片大部分为了优化,都会存放在第三方cdn.上面。这是第三方的配置,是否允许,自己很难控制)

                     0个小时。。。。。。。

                     1个小时.。。。。。。。。。。

                      0下午。。。。。。。。。。。。

                      1下午。。。。。。。。。。。。。

                      0天。。。。。。。。。。。。。。。。

解决办法:采用所有图片路径,转化为base64流,来处理。相对于本地图片了。此时,就避开了跨域问题。


                  图片路径,转base64,后端处理,更方便。

               eg: php

                 

/**
 * @param $url
 * @return bool|string
 * Name: master_imgUrl_base64
 * User: wangjiapeng
 * Date: 2018/04/12
 * Explain:CDN远程图片URL下载,并转化为base64
 */
protected function master_imgUrl_base64($url){
    if($url){
        $header = array(
            'User-Agent: Mozilla/5.0 (Windows NT 6.1; Win64; x64; rv:45.0) Gecko/20100101 Firefox/45.0',
            'Accept-Language: zh-CN,zh;q=0.8,en-US;q=0.5,en;q=0.3',
            'Accept-Encoding: gzip, deflate',);

        $curl = curl_init();
        curl_setopt($curl, CURLOPT_URL, $url);
        curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);
        curl_setopt($curl, CURLOPT_FOLLOWLOCATION, true);
        curl_setopt($curl, CURLOPT_ENCODING, 'gzip');
        curl_setopt($curl, CURLOPT_HTTPHEADER, $header);
        $data = curl_exec($curl);
        $code = curl_getinfo($curl, CURLINFO_HTTP_CODE);
        curl_close($curl);
        if ($code == 200) {//把URL格式的图片转成base64_encode格式的!
            $imgBase64Code = "data:image/jpeg;base64," . base64_encode($data);
             return $imgBase64Code;
        }else{
             return false;
        }
    }else{
        return false;
    }
}

     

附加,海报中需要生成二维码。

技术支持:jquery.qrcode.min.js

方法:1.html   中放入盒子

<!--二维码-->
<div style="display: none;" id="qrcode">
   2.  js
$("#qrcode").qrcode({
    render: "canvas",
    text: data.info.u_url  (要生成的url:例 https://blog.csdn.net/qq_37837134)
});
var codeCanvas=document.getElementById("qrcode").getElementsByTagName("canvas")[0];
var codeContext = codeCanvas.getContext("2d");
var imgsSrc1 = codeCanvas.toDataURL('image/jpg');

do_canvasa(data.info,imgsSrc1);    //  此方法  为canvas 生成海报   参数一:微信头像、微信昵称等     参数二:二维码
3.
function do_canvasa(data,imgsSrc1) {
    //获取canvas
    var canvas = document.getElementById('canvas');
//设置宽高
//想获取高清图请*2,一般的直接等于Width就行
    var Height = window.innerHeight*2;
    var Width = window.innerWidth*2;
//canvas绘制需要的对象
    var ctx = canvas.getContext("2d");
    canvas.width = Width;
    canvas.height = Height;
//获取图片
    var mainImg = document.getElementById('mainImg');
//获取图片

    var imgs = {
        bg: data.img_posters, //大背景
        via: data.wx_img, //头像
        pho:data.upload_img, //照片
        qrCode: imgsSrc1, //二维码
    };

    var draw = {};
//载入图片
    draw.into = function(){
        var imgNum = 0;
        for(var key in imgs){
            var img = new Image();
            img.crossOrigin = "";
            img.src = imgs[key];
            imgs[key] = img;
            imgs[key].onload = function(){
                imgNum++;
                if(imgNum == Object.keys(imgs).length) draw.drawImg();
            }
        }
    }
    //绘制canvas
    draw.drawImg = function(){
        //背景图
        ctx.drawImage(imgs.bg, 0, 0, Width, Height);
        //头像
        ctx.save();
        ctx.arc(Width*0.14, Height*0.12, Width*0.075, 0, 360);
        ctx.clip();
        ctx.drawImage(imgs.via, Width*0.065, Height*0.07, Width*0.16, calcHeight(imgs.via, Width*0.16));
        ctx.restore();
        //昵称5
        //颜色
        ctx.fillStyle = '#fff';
        //字体设置 三个参数,font-weight font-size font-family
        ctx.font = '26px microsoft yahei';
        //说明
        // (scaled-0.62)
        ctx.fillText(''+data.wx_name+'', Width*0.225, Height*0.105);
        ctx.font = '24px microsoft yahei';
        ctx.fillStyle = 'red';
        ctx.textAlign="center";
        ctx.fillText(''+data.order_num+'', Width*0.34, Height*0.134);
        //照片
        ctx.save();
        ctx.strokeStyle = '#fff';
        ctx.lineWidth = 20;
        ctx.lineJoin = "round";
        if(imgs.pho.height > imgs.pho.width) {
            ctx.strokeRect((Width-Height*0.3 / imgs.pho.height * imgs.pho.width)/2, (Height-Height*0.3)/2 + 80, Height*0.3 / imgs.pho.height * imgs.pho.width, Height*0.3 );
            ctx.fillRect((Width-Height*0.3 / imgs.pho.height * imgs.pho.width)/2, (Height-Height*0.3)/2 + 80, Height*0.3 / imgs.pho.height * imgs.pho.width, Height*0.3 );
            ctx.drawImage(imgs.pho, (Width-Height*0.3 / imgs.pho.height * imgs.pho.width)/2, (Height-Height*0.3)/2 + 80, Height*0.3 / imgs.pho.height * imgs.pho.width, Height*0.3);
        } else if(imgs.pho.height < imgs.pho.width){
            ctx.strokeRect((Width-Width*0.7)/2, (Height - Width*0.7 / imgs.pho.width * imgs.pho.height) / 2 + 80, Width*0.7, Width*0.7 / imgs.pho.width * imgs.pho.height);
            ctx.fillRect((Width-Width*0.7)/2, (Height - Width*0.7 / imgs.pho.width * imgs.pho.height) / 2 + 80, Width*0.7, Width*0.7 / imgs.pho.width * imgs.pho.height);
            ctx.drawImage(imgs.pho, (Width-Width*0.7)/2,(Height - Width*0.7 / imgs.pho.width * imgs.pho.height) / 2 + 80, Width*0.7, Width*0.7 / imgs.pho.width * imgs.pho.height);
        } else {
            ctx.strokeRect((Width-440)/2, (Height-Width*0.7)/2 + 120, 440, 440);
            ctx.fillRect((Width-440)/2, (Height-Width*0.7)/2 + 120, 440, 440);
            ctx.drawImage(imgs.pho, (Width-440)/2, (Height-Width*0.7)/2 + 120, 440, 440);
        }

        ctx.restore();
        //二维码
        ctx.drawImage(imgs.qrCode, (Width-Width*0.22)/2 , Height*0.76, Width*0.22, calcHeight(imgs.qrCode, Width*0.22));
        //获取base64格式的src
        var imgSrc = canvas.toDataURL('image/jpg');
        mainImg.src = imgSrc;
    }

    draw.into();

    function calcHeight(obj, w){
        return w / obj.width * obj.height;
    }

}

我为人人,人人为我;美美与共,天下大同;

阅读更多
想对作者说点什么? 我来说一句

没有更多推荐了,返回首页