Three ways to draw in 2D. The Canvas API paints pixels imperatively, SVG describes shapes as scalable vector elements, and p5.js makes creative coding delightfully simple.
The Canvas 2D API draws pixels every frame. Here, particles drift, connect to nearby neighbours, and chase your cursor — a classic generative effect. Move your mouse over it.
const ctx = canvas.getContext('2d'); function frame() { ctx.clearRect(0, 0, w, h); for (const p of particles) { p.x += p.vx; p.y += p.vy; // move ctx.beginPath(); ctx.arc(p.x, p.y, 2, 0, Math.PI*2); ctx.fill(); // paint a pixel dot } requestAnimationFrame(frame); }
SVG is markup, not pixels — every shape is a DOM element you can style and animate. This scene animates with native SMIL (<animate>) plus a touch of JS, and stays razor-sharp at any zoom.
<!-- SVG animates itself with SMIL, no JS needed --> <circle cx="200" cy="120" r="34" fill="url(#sun)"> <animate attributeName="cy" values="120;90;120" dur="4s" repeatCount="indefinite" /> </circle>
p5.js wraps Canvas in a friendly, beginner-loved API built around setup() and draw(). This real p5 sketch paints a flowing trail wherever you move — drag inside it to draw, click to clear.
function setup() { createCanvas(600, 300); } function draw() { if (mouseIsPressed) { fill((frameCount*2) % 360, 80, 90); circle(mouseX, mouseY, 18); // follow the cursor } }
<animate> tags, and a genuine p5.js sketch loaded from cdn.jsdelivr.net/npm/p5 running its real setup()/draw() loop. The shared CSS shell styles the page chrome.