Canvas月亮绘制 +简单动画实现

动画实现:

通过setInterval方法不停的调用context.clearRect()方法清理画布,然后再重新绘制页面。

此外,html5 还提供一个专门用于请求动画的API,那就是 requestAnimationFrame,顾名思义就是请求动画帧。

下一章研究:伪3D引擎 zdog

init();
function init(){
      if(moon.x <= canvas.width) {
           moon.x += 20;
           fillMoon(ctx, 2, moon.x, moon.y, 100, 35);
      } else {
           moon.x = 0;
      }
      requestAnimationFrame(init);
};

下面是实例:

<!DOCTYPE html>
<html>

    <head>
        <meta charset="utf-8">
        <meta name="viewport" content="width=device-width, initial-scale=1,maximum-scale=1,user-scalable=no">

        <title></title>
        <style>
            * {
                padding: 0;
                margin: 0;
            }
            
            #canvas {
                display: block;
                border: 1px solid #ccc;
                margin: 0 auto;
            }
        </style>
    </head>

    <body>
        <canvas id="canvas">您的浏览器不支持</canvas>
    </body>
    <script>
        var moon = {
            x: 100,
            y: 120
        };

        var canvas = document.getElementById("canvas");
        canvas.width = screen.width;
        canvas.height = screen.height;
        var ctx = canvas.getContext("2d");

        var time = 2000;

        setInterval(function() {
            if(moon.x <= canvas.width) {
                moon.x += 50;
                fillMoon(ctx, 2, moon.x, moon.y, 100, 35);
            } else {
                moon.x = 0;
            }

        }, time);

        //对月亮进行配置
        function fillMoon(ctx, d, x, y, R, rot, fillColor) //R半径,rot旋转角度
        {
            ctx.clearRect(0, 0, canvas.width, canvas.height);

            var skyStyle = ctx.createRadialGradient((canvas.width / 2), canvas.height, 0, (canvas.width / 2), canvas.height - 100, 250); //(startx,starty,endx,endy);
            skyStyle.addColorStop(0.0, "#176293"); //第一个参数为0-1之间的浮点数。表示颜色的位置
            skyStyle.addColorStop(1.0, "black");
            ctx.fillStyle = skyStyle;
            ctx.fillRect(0, 0, canvas.width, canvas.height);

            ctx.save();
            ctx.translate(x, y);
            ctx.rotate(rot * Math.PI / 180);
            ctx.scale(50, 50); //context.scale(scalewidth,scaleheight);放大倍数
            PathMoon(ctx, d);
            ctx.fillStyle = fillColor || "#fb5";
            ctx.fill();
            ctx.restore();

            //绘制星空
            for(var i = 0; i < 50; i++) {
                var r = Math.random() * 5 + 1; //10-20
                var rot = Math.random() * 360;
                var x = Math.random() * canvas.width + 3;
                var y = Math.random() * canvas.height * 0.65 + 5;
                drawStar(ctx, x, y, r, rot);
            }

        }
        //绘制月亮
        function PathMoon(ctx, d) {
            ctx.beginPath();
            ctx.arc(0, 0, 1, 0.5 * Math.PI, 1.5 * Math.PI, true);
            ctx.moveTo(0, -1);
            ctx.arcTo(d, 0, 0, 1, dis(0, -1, d, 0) / d);
            ctx.closePath();
        }

        function dis(x1, y1, x2, y2) {
            return Math.sqrt((x1 - x2) * (x1 - x2) + (y1 - y2) * (y1 - y2));
        }

        //对星星状态进行设置
        function drawStar(ctx, x, y, r, rot) {
            ctx.save(); //保存ctx状态
            ctx.translate(x, y); //移动
            ctx.rotate(rot / 180 * Math.PI); //旋转角度
            starPath(ctx, r);

            ctx.fillStyle = "#fb3";
            ctx.strokeStyle = "#fd5"
            ctx.lineWidth = 3;
            ctx.lineJoin = "round";
            ctx.fill();
            ctx.stroke();

            ctx.restore(); //回到之前ctx的状态
        }
        //封装五角星函数
        function starPath(ctx, r) {
            ctx.beginPath();
            for(var i = 0; i < 5; i++) {
                ctx.lineTo(Math.cos((18 + i * 72) / 180 * Math.PI) * r, -Math.sin((18 + i * 72) / 180 * Math.PI) * r);
                ctx.lineTo(Math.cos((54 + i * 72) / 180 * Math.PI) * (r / 2), -Math.sin((54 + i * 72) / 180 * Math.PI) * (r / 2));
            }
            ctx.closePath();
        }
    </script>

</html>

猜你喜欢

转载自www.cnblogs.com/liangtao999/p/11932811.html