Skip to content

Instantly share code, notes, and snippets.

Embed
What would you like to do?
amazon canvas demo refactor
// Create a canvas element of the specified size.
const canvasWidth = 1000,
canvasHeight = 100,
canvas = document.querySelector("canvas");
canvas.width = canvasWidth;
canvas.height = canvasHeight;
const snowflake = canvas.getContext("2d");
class Snowflake {
constructor(x, y, dx, dy, radius, counter) {
Object.assign(this, { x, y, dx, dy, radius, counter });
}
draw() {
snowflake.beginPath();
// Draw a path along a 'circle'
// .-- at this x position
// | .-- and this y position
// v v v-- with this size
snowflake.arc(this.x, this.y, this.radius, 0, Math.PI * 2, false);
// ^ ^ ^-- Draw the path clockwise
// | . -- ... and going all the way around
// .-- starting from the top
// White outline
snowflake.strokeStyle = "white";
snowflake.stroke();
// Fill it in with white
snowflake.fillStyle = "white";
snowflake.fill();
}
update() {
// If the snowflake would fall off the screen, start drawing it from the top again.
if (this.y + this.radius > canvas.height)
this.y = 0;
// (0,0) in (x,y) coordinates is traditionally the _top left_ corner of the screen
// Which explains why `this.y = 0` moves the snowflake to the top...
// ... and why "adding" the change moves the snowflakes down
this.x += this.dx; // dx and dy means "the change in that direction"
this.y += this.dy;
this.draw();
}
}
// Let's make 70 snowflakes. Why 70? Why not?
const snowflakes = [...Array(70)].map(_ => {
// Pick a random size for the snowflake. Anything between "1" and "5".
const radius = 1 + Math.random() * 6;
// Start drawing the snowflake at a random spot
// 1. take the canvas width,
// 2. subtract the width of the snowflake (so that it will never be cut off)
// 3. and then multiply that by some number between 0 and 1
// ... you'll end up with a net result of "place the snowflake somewhere in the picture"
const x = Math.random() * (canvasWidth - (radius * 2) /* the width of the snowflake */)
+ radius; // (But since we start drawing snowflakes from the top, we
// need to offset that so we don't accidentally cut any off)
// Start at top; some circles will start off screen so that the snow "falls" naturally.
const y = 0 - Math.random() * 50;
// Figure out how fast each snowflake will fall and what direction they're going to drift.
const dx = (Math.random() - 0.5) * 2;
const dy = 0.5 + Math.random() * 0.5; // use gravity
// Add the new snowflake to the list of snowflakes
return new Snowflake(x, y, dx, dy, radius, 0);
});
const animate = () => {
requestAnimationFrame(animate); // recurisvely run
// If this isn't called every time, the snowflakes will become lines as the
// previous position is never cleared
snowflake.clearRect(0, 0, innerWidth, innerHeight);
snowflakes.forEach(s => s.update());
};
animate();
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
You can’t perform that action at this time.