天天看点

canvas实现贼好看的烟花效果

效果图:

canvas实现贼好看的烟花效果

废话不说,上代码:

<!DOCTYPE html>
<html lang="en">

<head>
    <meta charset="UTF-8" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <title>Document</title>
    <style>
        * {
            margin: 0;
            padding: 0;
        }
        
        body {
            background-color: #000;
        }
    </style>
</head>

<body>
    <canvas></canvas>
    <script>
        // 获取画布
        var can = document.querySelector("canvas");
        // 获取画笔
        var ctx = can.getContext("2d");
        // 不能用css改变画布大小
        // 让canvas的宽高等于屏幕的宽高
        var ch = (can.height = window.innerHeight);
        var cw = (can.width = window.innerWidth);
        var arrRain = [];
        // 我挑选的几种喜欢的颜色,也可以用随机数给rgb值来进行随机颜色
        var arryans = ['silver', 'gray', 'white', 'maroon', 'red', 'purple', 'fuchsia', 'green', 'yellow', ' blue', 'skyblue', ' blueviolet', 'chocolate']
            // 监听屏幕大小,屏幕发生改变让画布大小跟着改变
        window.onresize = function() {
            ch = can.height = window.innerHeight;
            cw = can.width = window.innerWidth;
            // console.log(ch, cw);
        };
        // 获取一个随机数,使烟花随机生成
        function rand(min, max) {
            return parseInt(Math.random() * (max - min) + min);
        }
        // 构造函数
        function Rain() {}
        // 为rain添加属性方法
        Rain.prototype = {
            // 初始化位置,以及烟花半径
            init: function() {
                this.x = rand(0, cw);
                this.y = ch;
                // 保证烟花在屏幕内炸开
                this.h = rand(0.5 * ch, 0.05 * ch);
                this.r = 1; //开始圆的半径
                this.vr = 1; //半径增长的速度
                this.vy = rand(4, 5);
                this.color = arryans[rand(0, 13)];
            },
            //画方法
            draw: function() {
                //小于h的时候,画矩形(烟花没炸开的时候)
                if (this.y > this.h) {
                    ctx.beginPath();
                    ctx.fillStyle = this.color;
                    ctx.fillRect(this.x, this.y, 4, 10);
                } else {
                    //画圆,把圆均分,每隔一个小扇形就给一个扇形颜色,做成隔行变色的效果
                    var num = 180;
                    var angle = Math.PI * 2 / num;
                    var star = 0;
                    var end = angle;
                    for (var i = 0; i < num; i++) {
                        ctx.beginPath();
                        ctx.arc(this.x, this.y, this.r * 2, star, end);
                        ctx.strokeStyle = this.color;
                        ctx.stroke();
                        ctx.closePath();
                        star = end + angle;
                        end = end + angle * 2;
                    }
                }
            },
            // y烟花移动
            move: function() {
                //小于h时,加y实现烟花移动
                if (this.y > this.h) {
                    this.y -= this.vy
                } else {
                    //实现烟花炸开的效果
                    if (this.r < 70) {
                        this.r += this.vr
                    } else {
                        //结束效果后初始化,继续从下方生成新烟花
                        this.init()
                    }
                }
                this.draw()
            }
        };
        // 生成烟花
        function createRain(num) {
            for (var i = 0; i < num; i++) {
                setTimeout(function() {
                    var rain = new Rain();
                    rain.init()
                    rain.draw()
                    arrRain.push(rain)
                }, 500 * i);
            }
        }
        createRain(50)
        setInterval(function() {
            ctx.beginPath()
            ctx.fillStyle = 'rgba(0,0,0,0.05)'
            ctx.fillRect(0, 0, cw, ch)
            for (var k of arrRain) {
                k.move()
            }
        }, 1000 / 60)
    </script>
</body>

</html>