在JavaScript中,如果你要制作一個煙花效果,該怎么做呢?下面就是幾個制作煙花效果的實例:
//第一個實例 function firework(_x, _y) { var canvas = document.getElementById("myCanvas"), ctx = canvas.getContext("2d"), cw = canvas.width = window.innerWidth, ch = canvas.height = window.innerHeight, particles = [], hue = 120, limiterTotal = 15, limiterTick = 0, timerTotal = 80, timerTick = 0, soundEffect = new Audio(); //初始化每個粒子 function Particle() { this.x = _x; this.y = _y; this.vx = Math.random() * 10 - 5; this.vy = Math.random() * -15 - 5; this.gravity = 0.2; this.hue = hue; this.alpha = 1; this.decay = Math.random() * 0.05 + 0.005; } //繪制每個粒子 Particle.prototype.draw = function() { ctx.beginPath(); ctx.arc(this.x, this.y, Math.random() * 4 + 1, 0, Math.PI * 2); ctx.closePath(); ctx.fillStyle = "hsla(" + this.hue + ",100%," + this.alpha + "%,1)"; ctx.fill(); }; //改變每個粒子的運動狀態 Particle.prototype.update = function(i) { this.x += this.vx; this.y += this.vy; this.vy += this.gravity; this.alpha -= this.decay; if (this.alpha <= 0) { particles.splice(i, 1); } }; //主要流程 function loop() { window.requestAnimationFrame(loop); //創建出舞臺背景 ctx.globalCompositeOperation = "destination-out";//混合模式 ctx.fillStyle = "rgba(0,0,0," + 15 / 90 + ")"; ctx.fillRect(0, 0, cw, ch); ctx.globalCompositeOperation = "lighter"; //更新粒子 var i = particles.length; while (i--) { particles[i].draw(); particles[i].update(i); } //添加新的粒子 if (limiterTick >= limiterTotal) { particles.push(new Particle()); limiterTick = 0; } else { limiterTick++; } //循環結束后執行下一次煙花 if (timerTick >= timerTotal) { soundEffect.src = "sound/explosion.mp3";//煙花爆炸音效 soundEffect.play(); firework(_x, _y);//再次觸發 timerTick = 0; } else { timerTick++; } } //開始執行 loop(); }
以上代碼實現了不斷發射煙花的效果,一份沒有流程注釋的代碼可能難以直觀地理解,因此可以在實現的過程中添加代碼注釋,這樣可以幫助理解代碼的結構。
還有一種實現JavaScript煙花效果的方法就是通過canvas這個HTML5標簽實現,有趣的是,使用canvas標簽是使用JavaScript代碼實現圖形和繪畫的底層途徑,即可繪制出個性化的圖形,發揮你的想象力,下面是實現煙花效果的canvas代碼示范:
//第二個實例 var cvs = document.getElementById('cvs'); var ctx = cvs.getContext('2d'); cvs.width = window.innerWidth; cvs.height = window.innerHeight; var fireworks = []; function Firework() { this.x = Math.random() * cvs.width; this.y = Math.random() * cvs.height + cvs.height * 2 / 3; this.vx = Math.random() * 4 - 2; this.vy = Math.random() * -5 - 8; this.alpha = Math.random() * 360; this.color = 'hsl(' + this.alpha + ',100%,60%)'; this.fireworkers = []; } Firework.prototype.render = function () { this.vy += 0.1; this.x += this.vx; this.y += this.vy; this.alpha -= 1; ctx.save(); ctx.globalCompositeOperation = 'lighter'; ctx.beginPath(); ctx.arc(this.x, this.y, 5, 0, Math.PI * 2); ctx.closePath(); ctx.fillStyle = blink(); ctx.fill(); ctx.restore(); if (this.alpha < 0) this.end(); } Firework.prototype.end = function () { for (var i = 0; i < 40; ++i) { var r = Math.random() * 2; var alpha = Math.random() * 360; var color = 'hsl(' + alpha + ',100%,60%)'; var firework = new Fireworkers(this.x, this.y, r ,color); this.fireworkers.push(firework); } fireworks.splice(fireworks.indexOf(this),1); } function Fireworkers(x, y, r, color) { this.x = x; this.y = y; this.vx = Math.random() * 4 - 2; this.vy = Math.random() * 4 - 2; this.size = r; this.alpha =1; this.color = color; } Fireworkers.prototype.render = function () { this.y += this.vy; this.vy += 0.001; this.x += this.vx; this.vx *= 0.99; this.alpha -= 0.01; ctx.save(); ctx.globalCompositeOperation = 'lighter'; ctx.beginPath(); ctx.arc(this.x, this.y, this.size, 0, Math.PI * 2); ctx.closePath(); ctx.fillStyle = this.color; ctx.fill(); ctx.restore(); if (this.alpha < 0) this.end(); } Fireworkers.prototype.end = function () { this.fireworkers.splice(this.fireworkers.indexOf(this), 1); } function blink() { var alpha = Math.random() * 360; return 'hsl(' + alpha + ',100%,60%)'; } function loop() { requestAnimationFrame(loop); ctx.fillStyle = 'rgba(0,0,0,0.1)'; ctx.fillRect(0, 0, cvs.width, cvs.height); if (Math.random() < 0.5) { var firework = new Firework(); fireworks.push(firework); } var i = fireworks.length; while (i --) { fireworks[i].render(); if (!fireworks[i].fireworkers.length && fireworks.length > 300) { fireworks = []; } } } loop();
在以上代碼實例中,我們使用canvas標簽繪制出不同顏色不同大小的圓點,并根據粒子運動的方向和速度來調整粒子的狀態,最終完成我們想要的煙花效果。
無論哪種實現方式,當我們在學習和使用JavaScript代碼的時候,需要深入的了解JS語言的特性和運行機制,才能更好地實現我們想要的功能。