import ddf.minim.*; Minim minim; AudioPlayer player; float angle = 0; float scale = sqrt(0.5); class Event { float targetAngle; float targetScale; float targetZoom; int duration; boolean isPause; boolean changeScale; boolean changeZoom; Event(float targetAngle, float targetScale, float targetZoom, int duration, boolean isPause, boolean changeScale, boolean changeZoom) { this.targetAngle = targetAngle; this.targetScale = targetScale; this.targetZoom = targetZoom; this.duration = duration; this.isPause = isPause; this.changeScale = changeScale; this.changeZoom = changeZoom; } } Event[] events = { new Event(0, sqrt(0.5), 1, 1050, false, false, false), new Event(45, sqrt(0.5), 1, 4050, false, false, false), new Event(45, sqrt(0.5), 1, 1000, true, false, false), new Event(60, sqrt(0.5), 1, 5000, false, false, false), new Event(60, sqrt(0.5), 1, 1200, true, false, false), new Event(90, sqrt(0.5), 1, 8000, false, false, false), new Event(90, sqrt(0.5), 1, 5000, true, false, false), new Event(60, sqrt(0.5), 1, 8000, false, false, false), new Event(60, sqrt(0.5), 1, 2000, true, false, false), new Event(60, 0.89, 0.5, 4000, false, true, true), new Event(60, 0.89, 0.25, 5000, false, true, true), }; int currentEventIndex = 0; int eventStartTime; int cycleDuration = 5000; color[] cycleColors = { color(0, 0, 255), // Blue color(128, 0, 128), // Purple color(255, 192, 203), // Pink color(255, 165, 0), // Orange color(255, 255, 0), // Yellow color(0, 128, 0), // Green color(64, 224, 208), // Turquoise color(0, 0, 255), // Blue }; int maxDepth = 15; void setup() { size(800, 800); colorMode(RGB, 255, 255, 255, 1); background(0); eventStartTime = millis(); minim = new Minim(this); player = minim.loadFile("DarkKnight.mp3"); player.play(); } float currentZoom = 1.0; void draw() { background(0); if (currentEventIndex < events.length) { Event currentEvent = events[currentEventIndex]; int elapsedTime = millis() - eventStartTime; if (currentEvent.changeScale) { float startScale = currentEventIndex == 0 ? scale : events[currentEventIndex - 1].targetScale; float t = map(elapsedTime, 0, currentEvent.duration, 0, 1); scale = lerp(startScale, currentEvent.targetScale, t); } if (currentEvent.changeZoom) { float startZoom = currentEventIndex == 0 ? currentZoom : events[currentEventIndex - 1].targetZoom; float t = map(elapsedTime, 0, currentEvent.duration, 0, 1); currentZoom = lerp(startZoom, currentEvent.targetZoom, t); } if (!currentEvent.isPause) { float startAngle = currentEventIndex == 0 ? angle : radians(events[currentEventIndex - 1].targetAngle); float t = map(elapsedTime, 0, currentEvent.duration, 0, 1); angle = lerp(startAngle, radians(currentEvent.targetAngle), t); } if (elapsedTime >= currentEvent.duration) { angle = radians(currentEvent.targetAngle); scale = currentEvent.targetScale; currentZoom = currentEvent.targetZoom; currentEventIndex++; eventStartTime = millis(); } } pushMatrix(); translate(width / 2, height / 2); scale(currentZoom); translate(-width / 2, -height / 2); PVector start = new PVector(width / 2, height / 2); PVector v = new PVector(0, -height / 7); rec(start, v, scale, angle, maxDepth, 0); rec(start, v.mult(-1), scale, -angle, maxDepth, 0); popMatrix(); fill(255); textSize(16); textAlign(RIGHT); text("Angle: " + degrees(angle) + "°", width - 10, 20); text("Scale: " + nf(scale, 0, 2), width - 10, 40); text("Zoom: " + nf(currentZoom, 0, 2), width - 10, 60); saveFrame("frames/frame-####.png"); } void stop() { player.close(); minim.stop(); super.stop(); } int sumDurations(int currentIndex) { int sum = 0; for (int i = 0; i <= currentIndex; i++) { sum += events[i].duration; } return sum; } color getColorForDepth(int depth, int maxDepth) { float baseCycleProgress = (millis() % cycleDuration) / (float)cycleDuration; float depthOffset = (float)depth / maxDepth; float cycleProgress = (baseCycleProgress - depthOffset) % 1.0; if (cycleProgress < 0) { cycleProgress += 1.0; } int colorIndex = (int)(cycleProgress * (cycleColors.length - 1)); float lerpFactor = (cycleProgress * (cycleColors.length - 1)) - colorIndex; color startColor = cycleColors[colorIndex]; color endColor = cycleColors[(colorIndex + 1) % cycleColors.length]; return lerpColor(startColor, endColor, lerpFactor); } void rec(PVector start, PVector v, float sc, float a, int count, int currentDepth) { if (count <= 0) return; PVector end = start.copy().add(v); color currentColor = getColorForDepth(currentDepth, maxDepth); stroke(currentColor); strokeWeight(map(currentDepth, 0, maxDepth, 1, 0.5)); line(start.x, start.y, end.x, end.y); float newScale = sc * 1; rec(end, v.copy().rotate(a).mult(newScale), newScale, a, count - 1, currentDepth + 1); rec(end, v.copy().rotate(-a).mult(newScale), newScale, -a, count - 1, currentDepth + 1); }