// requestAnimationFrame shim by Paul Irish: // http://paulirish.com/2011/requestanimationframe-for-smart-animating/ window.requestAnimFrame = (function(){ return window.requestAnimationFrame || window.webkitRequestAnimationFrame || window.mozRequestAnimationFrame || window.oRequestAnimationFrame || window.msRequestAnimationFrame || function( callback ){ window.setTimeout(callback, 1000 / 60); }; })(); $(document).ready(function() { var bgCanvas = $("#myBackground").get(0); var bgContext = bgCanvas.getContext("2d"); var bgRendered = false; var canvas = $("#myCanvas").get(0); var context = canvas.getContext("2d"); var up = 90, right = 0, down = 270, left = 180; var fullWidth = document.body.clientWidth; var fullHeight = document.body.clientHeight; bgCanvas.width = fullWidth; bgCanvas.height = fullHeight; canvas.width = fullWidth; canvas.height = fullHeight; function WokkaWokka(size, direction, speed, posX, posY) { this.startAngle = 0.25; this.endAngle = 1.75; this.gapClosing = true; this.size = size; this.direction = direction; this.speed = speed; this.posX = posX; this.posY = posY; } function randomWokkaWokka() { var size = Math.floor((Math.random()*50)+1); var direction = Math.floor((Math.random()*4)+1)*90; if(direction===360){direction = 0;} var speed = Math.floor((Math.random()*20)+1); var posX = Math.floor((Math.random()*fullWidth)+1); var posY = Math.floor((Math.random()*fullHeight)+1); return new WokkaWokka(size, direction, speed, posX, posY); } var WokkaWokkas = new Array(); var i, WW; for (i=0;i<250;i++) { WW = randomWokkaWokka(); WokkaWokkas.push(WW); } function renderGrid(gridPixelSize, color) { bgContext.save(); bgContext.lineWidth = 0.5; bgContext.strokeStyle = color; // horizontal grid lines for (var i = 0; i <= canvas.height; i = i + gridPixelSize) { bgContext.beginPath(); bgContext.moveTo(0, i); bgContext.lineTo(canvas.width, i); bgContext.closePath(); bgContext.stroke(); } // vertical grid lines for (var j = 0; j <= canvas.width; j = j + gridPixelSize) { bgContext.beginPath(); bgContext.moveTo(j, 0); bgContext.lineTo(j, canvas.height); bgContext.closePath(); bgContext.stroke(); } bgContext.restore(); bgRendered = true; } function setAngles(WWM) { if (WWM.startAngle <= 0) WWM.gapClosing = true; else if (WWM.startAngle > 0.25) WWM.gapClosing = false; if (WWM.gapClosing) { WWM.startAngle = WWM.startAngle + 0.05; WWM.endAngle = WWM.endAngle - 0.05; } else { WWM.startAngle = WWM.startAngle - 0.05; WWM.endAngle = WWM.endAngle + 0.05; } } function renderContent(WWM) { context.save(); context.beginPath(); context.fillStyle = "Yellow"; context.strokeStyle = "Yellow"; context.save(); context.translate(WWM.posX, WWM.posY); context.rotate(-WWM.direction * Math.PI / 180); context.translate(-WWM.posX, -WWM.posY); context.arc(WWM.posX, WWM.posY, WWM.size, (WWM.startAngle) * Math.PI, (WWM.endAngle) * Math.PI); context.lineTo(WWM.posX, WWM.posY); context.stroke(); context.fill(); context.restore(); context.restore(); } function animationLoop() { canvas.width = canvas.width; if (!bgRendered) { renderGrid(20, "red"); } for (var i = 0; i < WokkaWokkas.length; i++) { var WWM = WokkaWokkas[i]; renderContent(WWM); setAngles(WWM); switch (WWM.direction) { case up: WWM.posY -= WWM.speed; if (WWM.posY <= 0) WWM.direction = down; break; case down: WWM.posY += WWM.speed; if (WWM.posY > fullHeight) WWM.direction = up; break; case left: WWM.posX -= WWM.speed; if (WWM.posX < 0) WWM.direction = right; break; case right: WWM.posX += WWM.speed; if (WWM.posX > fullWidth) WWM.direction = left; break; } } requestAnimFrame(animationLoop); } animationLoop(); });
<canvas id="myBackground" style="position: absolute; z-index: 0;"> <p>Canvas not supported.</p> </canvas> <canvas id="myCanvas" style="position: absolute; z-index: 1;"> <p>Canvas not supported.</p> </canvas>
* { margin: 0; padding: 0; } html, body { height: 100%; width: 100%; background-color: #000; } canvas { display: block; }