Source of: Aurora Currents, by GPT-6.1 Sol
103 lines, no comments ยท 1,030 tokens, written in 17 seconds for $0.011
1 let motes = [];
2 let time = 0;
3 let paused = false;
4 let paletteShift = 0;
5
6 function setup() {
7 createCanvas(windowWidth, windowHeight);
8 pixelDensity(1);
9 colorMode(HSB, 360, 100, 100, 100);
10 strokeWeight(1.2);
11 resetScene();
12 }
13
14 function resetScene() {
15 background(230, 55, 5);
16 noiseSeed(floor(random(100000)));
17 paletteShift = random(-25, 25);
18 time = 0;
19 const count = constrain(floor(width * height / 650), 450, 1800);
20 motes = Array.from({ length: count }, () => new Mote());
21 }
22
23 class Mote {
24 constructor() {
25 this.reset();
26 }
27
28 reset() {
29 this.x = random(width);
30 this.y = random(height);
31 this.speed = random(0.7, 2.4);
32 this.life = random(100, 500);
33 this.tint = random(-15, 15);
34 }
35
36 step() {
37 const oldX = this.x;
38 const oldY = this.y;
39 const scale = 0.0018;
40 const field = noise(this.x * scale, this.y * scale, time);
41 const angle = field * TWO_PI * 2.8;
42 let vx = cos(angle) * this.speed;
43 let vy = sin(angle) * this.speed;
44
45 if (mouseX > 0 && mouseX < width && mouseY > 0 && mouseY < height) {
46 const dx = this.x - mouseX;
47 const dy = this.y - mouseY;
48 const distance = sqrt(dx * dx + dy * dy);
49 const force = max(0, 1 - distance / 220) * 3;
50 if (distance > 1) {
51 vx += (-dy / distance) * force;
52 vy += (dx / distance) * force;
53 }
54 }
55
56 this.x += vx;
57 this.y += vy;
58 this.life--;
59
60 if (this.x < 0 || this.x > width || this.y < 0 || this.y > height || this.life < 0) {
61 this.reset();
62 return;
63 }
64
65 const hue = (155 + field * 120 + this.tint + paletteShift + 360) % 360;
66 stroke(hue, 65, 95, 35);
67 line(oldX, oldY, this.x, this.y);
68 }
69 }
70
71 function draw() {
72 if (paused) return;
73
74 blendMode(BLEND);
75 noStroke();
76 fill(230, 55, 5, 5);
77 rect(0, 0, width, height);
78
79 blendMode(ADD);
80 for (const mote of motes) mote.step();
81 blendMode(BLEND);
82 time += 0.002;
83 }
84
85 function mousePressed() {
86 resetScene();
87 }
88
89 function keyPressed() {
90 if (key === ' ') {
91 paused = !paused;
92 return false;
93 }
94 if (key === 's' || key === 'S') {
95 saveCanvas('aurora-currents', 'png');
96 }
97 }
98
99 function windowResized() {
100 resizeCanvas(windowWidth, windowHeight);
101 resetScene();
102 }
103