canvas做loading动画

由于公司最近项目不是很忙,所以,自己利用闲暇的时间来研究了一阵子的htm5和css3,正巧,公司最近要对以前的项目进行一次统一的升级,而我被告知时,主要是在以前的版本中加入一些页面动画。有4人参与了动画特效的编写,我很幸运自己也被选中。

第一次做动效还是用css3,心里好激动。虽然自己对css3不是很了解,但是,我还是有信心自己能够胜任这次的任务。接下来近2个月的时间里,我都在做css3动效,由于自己只是擅长javascript和JQuery,对css了解也不是很熟悉,所以,做css3动画上还是很吃力的。中途遇到很多问题,自己也虚心请教了很多同事。(博主突然发现,我在现在的公司还是很历练人的。)经过那短短的近2个月的时间,我对css也有了进一步的了解。正好今天是周末,自己整理一下自己用到的知识。顺便做了些例子。

canvas这次没有用到项目中,而是我业余的研究。有写错的地方,还请高手指点~

废话不多说了,直接上效果图:

html代码:

<html>
<head>
<meta charset="UTF-8">
<title></title>
<script type="text/javascript" src="./loading.js"></script>
</head>
<body>
<div style="border:1px solid red; 200px;height:400px; margin-left:10px;float:left;">
<canvas id="loading1" style="200px;padding:0;margin:0;display:block;">
</canvas>
<canvas id="loading2" style="200px;padding:0;margin:0;display:block;">
</canvas>
</div>
<script type="text/javascript">
loading1();
new loading2({"id":"loading2"});
</script>
</body>
</html>

javascript代码:

function loading1(){
    var canvas = document.getElementById("loading1"),
        ctx = canvas.getContext("2d"),
        w = canvas.width,
        h = canvas.height,
        x = w/2,
        y = h/2,
        radius = 30;
        ctx.fillStyle = "#000";
        ctx.fillRect(0,0,w,h);

        var r = [3,4,4.5,5,6,7];
        var angle = [10,25,45,65,90,120];
        var alpha = [0.25,0.35,0.45,0.65,0.8,1];
        var x1=[],y1=[];
        
        setInterval(function(){
            ctx.fillStyle = "#000";
            ctx.fillRect(0,0,w,h);
            x1 = [];
            y1 = [];
            for(var i = 0; i < r.length; i ++){
                if(angle[i] >= 360) angle[i] = 0;
                ctx.beginPath();
                ctx.font = "1rem sans-serif";
                ctx.fillStyle = "rgba(156,236,255,"+alpha[i]+")";
                x1.push( x + radius*Math.cos(angle[i]*Math.PI/180));
                y1.push( y + radius*Math.sin(angle[i]*Math.PI/180));
                ctx.arc(x1[i],y1[i],r[i],0,2*Math.PI, true);
                ctx.closePath();
                ctx.fill();
                angle[i] += 5;
            }
        },25);
}

function isEmpty(obj){
    var name;
    for(name in obj){
        return false;
    }
    return true;
}

function loading2(arg){
    this.init(arg);
}
loading2.prototype = {
    constructor:loading2,
    init: function (arg) {
        var isConsist = !isEmpty(arg);
        this.block = isConsist ? arg.block ? arg.block : 12 : 12;
        this.height = isConsist ? arg.height ? arg.height : 15 : 15;
        this.width = isConsist ? arg.width ? arg.width : 3 : 3;
        this.time = isConsist ? arg.time ? arg.time : 100 : 100;
        
        this.cvs = document.getElementById(arg.id),
        this.ctx = this.cvs.getContext("2d");
        this.ctx.width = this.height*6;
        this.ctx.height = this.height*6;
        
        this.ctx.translate(this.ctx.width/2, this.ctx.height/2);
        var radius = 2;
        this.view(radius);
    },
    loop: function(alpha){
        this.ctx.rotate(Math.PI*2/this.block);
        this.ctx.beginPath();
        this.ctx.fillStyle = "rgba(0,0,0,"+alpha+")";
        this.ctx.arc(0, this.ctx.width/2-this.height*2,this.width/2, 0 ,Math.PI, true);
        this.ctx.arc(0, this.ctx.width/2-this.height, this.width/2, Math.PI, 0, true);
        this.ctx.closePath();
        this.ctx.fill();
    },
    view: function(radius){
        var that = this;
        this.ctx.rotate(Math.PI*2/this.block);
        for(var i = 1; i <= this.block; i ++){
            this.loop(i/this.block);
        }
        setTimeout(function(){
            that.ctx.clearRect(-that.ctx.width/2, -that.ctx.height/2, that.ctx.width, that.ctx.height);
            radius >= that.block? radius = 1:radius += 1;
            that.view(radius);
        }, that.time);
    
    }
}

整段javascript中,我认为最难懂的是loop中的代码,这段代码也是canvas中的画图的重点。

首先,canvas对象通过getContext("2d");返回一个context对象。canvas对象所有的画图,旋转,转变,缩放等功能全是通过context对象实现的。

canvas对象有width和height属性,默认的width、height值为300px; 可通过context.width,context.height重新设值;

canvas画矩形:

context.fillRect(x,y,width,height)设置canvas被填充的矩形,以相canvas中坐标点(x,y)为起点,宽度为width,高位height的矩形进行填充。在填充矩形前,可以通过context.fillStyle可以设置填充的样式(css);

canvas画圆:

context.beginPath(); //起始一条路径,或重置当前路径

context.fillStyle;//可以设置canvas要填充的样式

context.arc(x,y,radius,startAngle,endAngle,flag); //以canvas内坐标点(x,y)为圆心radius为半径,起始弧度为startAngle,终止弧度为endAngle,flag为bool值,当flag值为true时,表示逆时针旋转,当flag为false,表示以顺时针旋转;

context.closePath();

context.fill();//填充当前绘图路径;

canvas旋转rotate:

在loading2中view方法的代码中,有用到context.rotate()方法,rotate(angle)方法是用来旋转当前绘图,接收一个参数,以弧度计,表示旋转角度;

canvas重新映射画布(0,0)坐标点:

context.translate(x,y)表示将canvas的左上角平移到点(x,y)处;

值得注意的有

  • canvas中的弧度表示:默认你逆时针旋转。这和数学中默认的弧度旋转方向相反;

  •  画弧。在canvas中画圆弧时候,可以在context.beginPath()和context.closePath()中画多个圆弧。当圆弧不是闭合状态时,所画的圆弧会相互连接起来。loading效果图中每一个旋转的块都是这样画出来的。

好了,以上就是我对canvas画loading图的了解,我说的不到位的,或是说的不准确、不正确的。欢迎大家指正~

原文地址:https://www.cnblogs.com/sxshijingjing/p/4214898.html