Long story short, I’m trying to create an animated background consisting of slowly falling transparent rectangles. I’ve found a script that allowed me to get pretty close with each shape being randomized in both initial starting position and its dimensions but it’s not entirely there because I think it can be a little more efficient. The animation is a tiny bit “stutterish” and it also seems to be a CPU / RAM hog as it makes other tabs in my browser lazy at reacting.
Here’s the overall script I’m toying with right now (uses jQuery 2.1.3) to give you an idea of what I’m shooting for:
<!DOCTYPE html>
<html lang='en' class=''>
<head>
<meta charset='UTF-8'>
<style>
body{margin:0;padding:0;height:100%;width:100%;background:#fff}
</style>
</head>
<body>
<canvas id="canvas"></canvas>
<script type="text/javascript" src="jquery.min.js" /></script>
<script>
var shapesBackground = {
shapeHeight: 60,
shapeWidth: 64,
shapes: [],
shapeImage: 'bg.png',
maxshapes: 10,
minScale: 0.4,
draw: function(){
this.setCanvasSize();
this.ctx.clearRect(0, 0, this.w, this.h);
for(var i = 0; i < this.shapes.length; i++) {
var shape = this.shapes[i];
shape.image = new Image();
shape.image.style.height = shape.height;
shape.image.src = this.shapeImage;
this.ctx.globalAlpha = shape.opacity;
this.ctx.drawImage (shape.image, shape.x, shape.y, shape.width, shape.height);
}
this.move();
},
move: function(){
for(var b = 0; b < this.shapes.length; b++) {
var shape = this.shapes[b];
shape.y += shape.ys;
if(shape.y > this.h) {
shape.x = Math.random() * this.w;
shape.y = -1 * this.shapeHeight;
}
}
},
setCanvasSize: function() {
this.canvas.width = window.innerWidth;
this.canvas.height = window.innerHeight;
this.w = this.canvas.width;
this.h = this.canvas.height;
},
initialize: function() {
this.canvas = $('#canvas')[0];
if(!this.canvas.getContext)
return;
this.setCanvasSize();
this.ctx = this.canvas.getContext('2d');
for(var a = 0; a < this.maxshapes; a++){
var scale = (Math.random() * (1 - this.minScale)) + this.minScale;
this.shapes.push({
x: Math.random() * this.w,
y: Math.random() * this.h,
ys: Math.random() + 1,
height: scale * getRandomInt(1,1000),
width: scale * getRandomInt(1,500),
opacity: scale
});
}
setInterval($.proxy(this.draw, this), 16);
}
};
function getRandomInt(min, max) {
return Math.floor(Math.random() * (max - min + 1)) + min;
}
$(document).ready(function(){
shapesBackground.initialize();
});
</script>
</body>
</html>
Just put an image of a square into the same folder that this HTML file will go in and name it “bg.png.” Then load it up in a browser and you’ll see the effect I’m shooting for.
What ways exist to get the same result only in a “lighter” (less heavy) way? To start with, I think the setInterval() is responsible for the animation stutter. Are there better ways to make the animation happen? I’m currently looking into using requestAnimationFrame() but I’ve never used this before. I’d also like to avoid using canvas if possible.
Thank in advance.