<!DOCTYPE html>
<html lang="en-us">
<head>
  <meta charset="utf-8">
  <meta name="robots" content="noindex">
  <meta name="viewport" content="width=device-width, initial-scale=1, viewport-fit=cover">
  <title>Square Flower</title>
  <style>
    html, body {
      height: 100%;
      display: flex;
      align-items: center;
      justify-content: center;
      background-color: #222;
    }
  </style>
  <script src="https://cdnjs.cloudflare.com/ajax/libs/p5.js/1.10.0/p5.js"></script>
<!--
  © Adam Murray 2025
  https://adammurray.link/

  Creative Commons License
  Attribution-NonCommercial-ShareAlike 4.0 International
  https://creativecommons.org/licenses/by-nc-sa/4.0/
-->
<script>
let b = -20;
let g = 0;
let maxScale = null;
let bDelta = -0.77;
let gDelta = -1;
let sqrs = [];

function setup() {
  const dim = Math.min(Math.min(1000, windowWidth), windowHeight) - 60;
  createCanvas(dim, dim).parent("processing-canvas");

  maxScale = Math.max(width, height) / 14.0;

  for (i = 0; i < 35; i++) {
    sqrs.push(new SquareZoomer(random(0.075) - 0.01, random(0.1) + 0.1));
  }

  strokeWeight(1.7);
  noFill();
}

function draw() {
  // animate background:
  b += bDelta;
  g += gDelta;
  if (b > 100 || b < -200) bDelta *= -1;
  if (g > 80 || g < -190) gDelta *= -1;
  background(0, g, b);

  // draw the squares:
  for (i = 0; i < sqrs.length; i++) {
    sqrs[i].draw();
  }
}

// This handles drawing a single square:
class SquareZoomer {
  constructor(angleDelta, zoomDelta) {
    this.angle = 0;
    this.zoom = 0.05;
    this.angleDelta = angleDelta;
    this.zoomDelta = zoomDelta;
    this.c = color(random(120) + 80, random(160) + 95, 255, 15);
  }

  draw() {
    stroke(this.c);

    this.drawSquare(width / 2, height / 2, 10, this.angle, this.zoom);

    // animate the rotation and zoom of this square
    this.angle += this.angleDelta;
    this.zoom += this.zoomDelta;

    if (this.zoom > maxScale || this.zoom < 0) {
      this.zoomDelta *= -1;
    }
  }

  drawSquare(x, y, size, angle, zoom) {
    push();
    translate(x, y);
    rotate(angle);
    scale(zoom);

    let halfSize = size / 2;
    rect(-halfSize, -halfSize, size, size);

    // undo the translate, rotate, and scale transformations:
    pop();
  }
}
</script>
</head>
<body>  
  <div id="processing-canvas"></div>
</body>
</html>