makeLoop = (ctx, width, height) => {
const hypnoSquare = (x, y, w, h, period = 300) => {
let frames = 0;
period = Number.isFinite(period) && period > 0 ? period : 1;
const offset = Math.PI * 2 * Math.random()
return () => {
let step = Math.cos(frames++ / period + offset);
step = step * step * 10 + 5;
for (let i = 0, flip = true; i < Math.min(w/2, h/2); i += step) {
ctx.fillStyle = (flip = !flip) ? "black" : "white";
ctx.fillRect(x + i, y + i, w - 2*i, h - 2*i);
}
}
}
const randomCoordinates = () => {
let x1, x2, y1, y2, x, y, w = 0, h = 0;
while (w < width / 16 || w > width / 4) {
x1 = Math.random() * width;
x2 = Math.random() * width;
x = Math.min(x1, x2);
w = Math.abs(x1 - x2);
}
while (h < height / 16 || h > height / 4) {
y1 = Math.random() * height;
y2 = Math.random() * height;
y = Math.min(y1, y2);
h = Math.abs(y1 - y2);
}
const period = 100 + 300 * Math.random();
return {x, y, w, h, period};
};
const squares = [];
for (let i = 0; i < 100; i++) {
const {x, y, w, h, period} = randomCoordinates();
squares.push(hypnoSquare(x, y, w, h, period));
}
return () => {for (const sq of squares) sq()};
}