You cannot select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
glsl/leaves_layers.js

107 lines
2.8 KiB
JavaScript

This file contains ambiguous Unicode characters!

This file contains ambiguous Unicode characters that may be confused with others in your current locale. If your use case is intentional and legitimate, you can safely ignore this warning. Use the Escape button to highlight these characters.

/*
Yes—p5s “frame buffers” are createGraphics() layers. In your sketch we can do three layers:
bgLayer—draw the gradient once (never clears).
leafLayer—redraw every frame for the animated leaves (clear each frame so motion is smooth).
clickLayer—optional persistent marks (e.g., mouse-added leaves/stars) that dont clear.
I also made leaf() draw into a given buffer and added safe defaults so calls without args dont break.
Key ideas:
Draw long-lived stuff (gradient) once to a buffer and reuse it.
For animated content, clear that buffer each frame (pg.clear()).
Compose with image() in the order you want (background → persistent → animated).
*/
let x1 = 30, y1 = 0, x4 = 480, y4 = 0;
let x2, y2, x3, y3;
let bgLayer, leafLayer, clickLayer;
function setup() {
createCanvas(1024, 800);
angleMode(RADIANS);
// off-screen buffers
bgLayer = createGraphics(width, height);
leafLayer = createGraphics(width, height);
clickLayer= createGraphics(width, height);
// paint the gradient ONCE to bgLayer
const c1 = color(50);
const c2 = color(212, 91, 70);
for (let y = 0; y < height; y++) {
const n = map(y, 0, height, 0, 1);
const newc = lerpColor(c1, c2, n);
bgLayer.stroke(newc);
bgLayer.line(0, y, width, y);
}
}
function draw() {
// clear the animated layer each frame (transparent)
leafLayer.clear();
// draw animated leaves into leafLayer
leaf(leafLayer); // uses defaults (0,0,0,1)
leaf(leafLayer, 200, 200, PI/4, 1);
leaf(leafLayer, 500, 400, PI/4, -1);
leaf(leafLayer, 100, 700); // uses defaults
// composite the layers to the main canvas
image(bgLayer, 0, 0);
image(clickLayer,0, 0);
image(leafLayer, 0, 0);
}
// draw a leaf into a specified buffer (pg)
function leaf(pg, leafX=0, leafY=0, leafRotation=0, scaleFactor=1) {
pg.push();
pg.translate(leafX, leafY);
pg.rotate(leafRotation);
pg.scale(scaleFactor, 1);
x2 = 100 * sin(frameCount * 0.5) + 1;
y2 = 100 * sin(frameCount * 0.005) + 10;
x3 = 180 * sin(frameCount * 0.005) + 10;
y3 = 150 * sin(frameCount * 0.005) + 10;
pg.noStroke();
pg.fill(160, 82, 45);
pg.beginShape();
pg.curveVertex(x1, y1);
pg.curveVertex(x1, y1);
pg.curveVertex(x2, y2);
pg.curveVertex(x3, y3);
pg.curveVertex(x4, y4);
pg.curveVertex(x4, y4);
pg.endShape();
pg.beginShape();
pg.curveVertex(x1, y1);
pg.curveVertex(x1, y1);
pg.curveVertex(x2, -y2);
pg.curveVertex(x3, -y3);
pg.curveVertex(x4, y4);
pg.curveVertex(x4, y4);
pg.endShape();
pg.pop();
}
// optional: add persistent clicks to their own buffer
function mousePressed() {
clickLayer.push();
clickLayer.noStroke();
clickLayer.fill(255, 230); // slight glow
clickLayer.ellipse(mouseX, mouseY, 10, 10);
clickLayer.pop();
}