// Iron Vigil, a stand-in world from zaisma.com/developers/backgrounds. MIT licensed: free to start from. float h1(float n) { return fract(sin(n * 127.1) * 43758.5453); } float h2(vec2 p) { return fract(sin(dot(p, vec2(127.1, 311.7))) * 43758.5453); } vec2 h22(vec2 p) { p = vec2(dot(p, vec2(127.1, 311.7)), dot(p, vec2(269.5, 183.3))); return fract(sin(p) * 43758.5453); } float noise(vec2 p) { vec2 i = floor(p), f = fract(p); vec2 u = f * f * (3.0 - 2.0 * f); return mix(mix(h2(i), h2(i + vec2(1.0, 0.0)), u.x), mix(h2(i + vec2(0.0, 1.0)), h2(i + vec2(1.0, 1.0)), u.x), u.y); } float fbm(vec2 p) { float v = 0.0, a = 0.5; for (int i = 0; i < 5; i++) { v += a * noise(p); p = p * 2.03 + 1.7; a *= 0.5; } return v; } // Soft particles in a grid of cells: each cell holds at most one, at a random spot, drifting with the grid. float motes(vec2 p, float size, float chance, float seed) { vec2 id = floor(p), f = fract(p) - 0.5; vec2 r = h22(id + seed) - 0.5; float on = step(1.0 - chance, h2(id + seed * 1.3)); float d = length(f - r * 0.7); return on * smoothstep(size, 0.0, d); } float box(vec2 p, vec2 b) { vec2 d = abs(p) - b; return length(max(d, 0.0)) + min(max(d.x, d.y), 0.0); } float seg(vec2 p, vec2 a, vec2 b, float r) { vec2 pa = p - a, ba = b - a; return length(pa - ba * clamp(dot(pa, ba) / dot(ba, ba), 0.0, 1.0)) - r; } // Outward distance from the edge a to b of a counter-clockwise polygon. float edge(vec2 p, vec2 a, vec2 b) { vec2 e = normalize(b - a); return dot(p - a, vec2(e.y, -e.x)); } // A small human in a long coat, 1 tall, feet at 0: head, collar, a coat flaring and blowing right, legs below, a rifle on the back. float person(vec2 p, float t) { float hem = 0.22 + 0.04 * sin(t * 1.6); float coat = max(max(edge(p, vec2(-0.1, 0.8), vec2(-0.15, 0.2)), edge(p, vec2(-0.15, 0.2), vec2(hem, 0.17))), max(edge(p, vec2(hem, 0.17), vec2(0.11, 0.8)), p.y - 0.8)); float d = min(coat - 0.02, length(p - vec2(0.0, 0.9)) - 0.075); d = min(d, min(seg(p, vec2(-0.04, 0.2), vec2(-0.05, 0.0), 0.035), seg(p, vec2(0.05, 0.2), vec2(0.07, 0.0), 0.035))); return min(min(d, seg(p, vec2(-0.13, 1.02), vec2(0.07, 0.45), 0.018)), box(p - vec2(0.0, 0.79), vec2(0.13, 0.04)) - 0.02); } // The fallen walker, in its own units: an armoured torso on its side with its pod, a leg jutting up, a snapped gun. float wreck(vec2 p) { vec2 r = vec2(p.x * 0.9 - p.y * 0.44, p.x * 0.44 + p.y * 0.9); float d = min(box(r, vec2(0.36, 0.15)) - 0.04, box(r - vec2(-0.1, 0.21), vec2(0.17, 0.07)) - 0.03); d = min(d, min(seg(p, vec2(0.15, 0.22), vec2(0.22, 0.52), 0.065), length(p - vec2(0.22, 0.52)) - 0.078)); d = min(d, min(seg(p, vec2(0.22, 0.52), vec2(0.43, 0.68), 0.045), seg(p, vec2(0.43, 0.68), vec2(0.5, 0.6), 0.03))); d = min(d, seg(p, vec2(0.45, 0.52), vec2(0.58, 0.68), 0.022)); return min(d, min(seg(p, vec2(-0.3, 0.04), vec2(-0.72, 0.2), 0.022), box(p - vec2(-0.74, 0.21), vec2(0.045, 0.032)))); } // A digitigrade leg from hip h to ankle a: thigh, knee plate, shin, foot. float leg(vec2 q, vec2 h, vec2 a) { vec2 d = a - h, n = normalize(d); float L = min(length(d), 0.53); vec2 k = h + n * L * 0.5 + vec2(n.y, -n.x) * sqrt(0.0729 - L * L * 0.25); return min(min(seg(q, h, k, 0.066), seg(q, k, a, 0.045)), min(length(q - k) - 0.072, min(seg(q, a, a - vec2(0.06, 0.08), 0.03), box(q - a + vec2(0.035, 0.088), vec2(0.08, 0.016)) - 0.005))); } // The walker, 1 tall, feet at 0, facing left: wedge hull, shoulder plate, cannon arm, missile pod, stacks. walk = 0 stands still. float mech(vec2 q, float ph, float walk) { vec2 h = vec2(0.04, 0.56 + walk * 0.012 * cos(ph * 2.0)), s = vec2(sin(ph), cos(ph)) * walk; float d = min(leg(q, h, vec2(-0.06 + 0.12 * s.x, 0.1 + 0.05 * max(s.y, 0.0))), leg(q, h + vec2(0.07, 0.01), vec2(0.13 - 0.12 * s.x, 0.1 + 0.05 * max(-s.y, 0.0)))); q.y -= h.y - 0.56; float hull = max(box(q - vec2(-0.01, 0.715), vec2(0.285, 0.135)), max(max(dot(q - vec2(-0.13, 0.85), vec2(-0.55, 0.83)), dot(q - vec2(-0.31, 0.73), vec2(-0.82, -0.57))), dot(q - vec2(0.21, 0.58), vec2(0.86, -0.5)))); vec2 sp = q - vec2(-0.03, 0.79), pp = q - vec2(0.13, 0.9); float top = min(box(vec2(sp.x * 0.98 + sp.y * 0.17, sp.y * 0.98 - sp.x * 0.17), vec2(0.1, 0.09)) - 0.03, box(vec2(pp.x * 0.99 - pp.y * 0.12, pp.y * 0.99 + pp.x * 0.12), vec2(0.12, 0.045)) - 0.02); float gun = min(box(q - vec2(-0.13, 0.6), vec2(0.13, 0.05)) - 0.008, min(seg(q, vec2(-0.24, 0.6), vec2(-0.52, 0.6), 0.018), seg(q, vec2(-0.1, 0.68), vec2(-0.44, 0.69), 0.013))); float rest = min(min(box(q - vec2(-0.5, 0.6), vec2(0.03, 0.03)), seg(q, vec2(-0.05, 0.9), vec2(-0.03, 1.04), 0.005)), min(seg(q, vec2(0.25, 0.8), vec2(0.26, 0.99), 0.012), seg(q, vec2(0.21, 0.82), vec2(0.215, 0.96), 0.01))); return min(min(d, hull), min(min(top, gun), rest)); } void mainImage(out vec4 color, in vec2 pixel) { vec2 uv = pixel / iResolution.xy; float ar = iResolution.x / iResolution.y, t = iTime, px = 1.5 / iResolution.y; float wide = clamp((ar - 0.6) / 1.0, 0.0, 1.0), hz = mix(0.5, 0.36, wide), mx = ar * mix(0.58, 0.68, wide), ms = mix(0.4, 0.45, wide); // Heat shimmer bends the air low over the horizon vec2 q = vec2(uv.x * ar + sin(uv.y * 90.0 + t * 2.5) * 0.0012 * smoothstep(0.08, 0.0, abs(uv.y - hz - 0.02)), uv.y); float y = q.y - hz; vec2 sc = vec2(mx + 0.1 * ms, hz + 0.46 * ms); float sr = 0.4 * ms, sd = length(q - sc); // Dusk sky: violet-rose overhead, amber at the horizon, the sun's halo vec3 col = mix(mix(vec3(0.92, 0.52, 0.34), vec3(0.58, 0.25, 0.33), smoothstep(0.0, 0.3, y)), vec3(0.17, 0.08, 0.19), smoothstep(0.25, 0.8, y)); col += vec3(1.0, 0.5, 0.28) * exp(-sd * 4.5) * 0.4 + vec3(1.0, 0.72, 0.45) * exp(-sd * 16.0) * 0.25; // The planet's ring: a lit band tilted across the sky, split by a gap vec2 rq = q - vec2(ar * 0.5, hz - 1.68); rq = vec2(rq.x * 0.97 - rq.y * 0.24, rq.x * 0.24 + rq.y * 0.97) / vec2(2.6, 2.1); float e = (length(rq) - 1.0) * 2.1; float rings = smoothstep(0.05, 0.038, abs(e)) * (0.7 + 0.3 * sin(e * 90.0)) * (0.8 - e * 4.0) * 0.8 * (1.0 - 0.75 * smoothstep(0.005, 0.0, abs(e - 0.012))); col += vec3(1.0, 0.8, 0.6) * rings * mix(0.7, 0.25, smoothstep(0.0, 1.0, abs(q.x - sc.x) / ar)); // The huge soft sun and shafts of light fanning from it col = mix(col, mix(vec3(1.0, 0.56, 0.34), vec3(1.0, 0.8, 0.56), smoothstep(-0.4, 0.7, (q.y - sc.y) / sr)), smoothstep(sr + px * 2.0, sr - px * 2.0, sd) * 0.8); col += vec3(1.0, 0.62, 0.38) * smoothstep(0.35, 0.9, noise(vec2(atan(q.y - sc.y, q.x - sc.x) * 9.0, t * 0.04))) * exp(-sd * 2.2) * smoothstep(sr * 0.9, sr * 1.6, sd) * 0.32; // Long stratus clouds across sky and sun, lit from below float cl = noise(vec2(q.x * 1.2 + t * 0.01, y * 16.0)) * 0.6 + noise(vec2(q.x * 3.0 + t * 0.02, y * 34.0)) * 0.4; col = mix(col, mix(vec3(0.42, 0.18, 0.25), vec3(1.0, 0.66, 0.46), exp(-sd * 3.5)), smoothstep(0.52, 0.8, cl) * smoothstep(0.04, 0.12, y) * smoothstep(0.6, 0.25, y) * 0.6); // Far mesas, hazed into the sky float mesa = hz + 0.022 + 0.03 * smoothstep(0.35, 0.65, noise(vec2(q.x * 2.4, 3.0))); col = mix(col, mix(vec3(0.66, 0.34, 0.33), vec3(0.95, 0.58, 0.4), exp(-abs(q.x - sc.x) * 3.0) * 0.6), smoothstep(px, -px, q.y - mesa) * 0.85); // Walkers far off, marching left along the horizon float wx = q.x + t * 0.006, wid = floor(wx / 0.45), wh = h1(wid + 3.0), ws = 0.042 + 0.032 * wh; vec2 wq = vec2(wx - wid * 0.45 - 0.225 - (fract(wh * 7.0) - 0.5) * 0.18, y - 0.003 - (1.0 - wh) * 0.012) / ws; if (wh > 0.2 && abs(wq.x) < 0.6 && abs(wq.y - 0.5) < 0.56) col = mix(col, mix(vec3(0.62, 0.34, 0.34), vec3(0.42, 0.2, 0.25), wh), smoothstep(px, -px, mech(wq, t * 1.2 + wid * 2.0, 1.0) * ws) * (0.5 + 0.35 * wh)); // The colossus, rim-lit against the sun and hazed at its feet; visor, warning lamp, searchlight, kicked-up dust vec2 base = vec2(mx, hz - 0.05), mq = (q - base) / ms; if (abs(mq.x + 0.1) < 0.48 && mq.y < 1.06 && mq.y > -0.02) { float md = mech(mq, 0.0, 0.0) * ms, rim = 0.0; if (md < px && md > -0.02) rim = smoothstep(-0.2, 1.0, mech(mq + normalize(sc - q) * 0.025, 0.0, 0.0) * ms / (px * 2.0)) * (0.35 + exp(-sd * 2.5)); vec3 mc = mix(vec3(0.13, 0.065, 0.08), vec3(0.78, 0.45, 0.38), smoothstep(0.4, 0.0, mq.y) * 0.85) + vec3(0.12, 0.06, 0.1) * smoothstep(0.7, 0.95, mq.y); float seam = min(abs(mq.y - 0.7) + step(0.22, abs(mq.x + 0.03)), min(abs(mq.y - 0.635) + step(0.16, abs(mq.x - 0.03)), abs(mq.y - 0.86) + step(0.07, abs(mq.x - 0.12)))); mc += vec3(0.2, 0.1, 0.08) * smoothstep(0.005, 0.0015, seam); mc += vec3(1.0, 0.68, 0.42) * (rim * 1.6 + smoothstep(-0.008, 0.0, md) * 0.25) + vec3(1.0, 0.72, 0.35) * smoothstep(0.012, 0.0, seg(mq, vec2(-0.29, 0.73), vec2(-0.15, 0.82), 0.0)) * 0.9; col = mix(col, mc, smoothstep(px, -px, md)); } vec2 lamp = base + vec2(-0.03, 1.045) * ms, eye = base + vec2(-0.3, 0.7) * ms; col += vec3(1.0, 0.15, 0.1) * (smoothstep(0.007, 0.0, length(q - lamp)) + exp(-length(q - lamp) * 60.0) * 0.4) * smoothstep(0.5, 0.0, abs(fract(t * 0.6) - 0.25)); float ba = -2.45 + 0.2 * sin(t * 0.21), bl = dot(q - eye, vec2(cos(ba), sin(ba))), bx = abs(dot(q - eye, vec2(-sin(ba), cos(ba)))); float beam = smoothstep(0.012 + bl * 0.14, 0.0, bx) * step(0.0, bl) * exp(-bl * 2.4); col += vec3(1.0, 0.92, 0.8) * smoothstep(0.012, 0.0, length(q - eye)); vec2 kq = (q - base - vec2(0.03, 0.03) * ms) / ms; col = mix(col, vec3(0.85, 0.52, 0.4), exp(-length(kq * vec2(2.6, 8.0))) * (0.45 + 0.4 * noise(kq * vec2(6.0, 14.0) - vec2(t * 0.25, 0.0)))); // Mid dunes float mid = hz - 0.04 + 0.022 * sin(q.x * 2.6 + 0.4) + 0.012 * sin(q.x * 6.3); col = mix(col, mix(vec3(0.33, 0.15, 0.16), vec3(0.78, 0.44, 0.33), exp(-max(mid - q.y, 0.0) * 32.0) * 0.8), smoothstep(px, -px, q.y - mid)); // Near dunes: a fallen walker half sunk in sand drifted over it, one leg jutting up, its gun snapped; the figure on the crest float wcx = ar * mix(0.2, 0.37, wide), nx = ar * mix(0.64, 0.52, wide), sz = mix(0.22, 0.3, wide); float near = hz - mix(0.11, 0.14, wide) + 0.035 * sin(q.x * 1.9 - 1.0) + 0.012 * sin(q.x * 5.1 + 2.0) + 0.012 * exp(-pow((q.x - nx) * 6.0, 2.0)) + 0.03 * exp(-pow((q.x - wcx) / sz * 2.2, 2.0)); vec2 fw = (q - vec2(wcx, near - 0.035)) / sz, L = normalize(sc - q); float wd = wreck(fw) * sz; if (wd < 0.01) { float wr = smoothstep(-0.2, 1.0, wreck(fw + L * 0.03) * sz / (px * 2.0)); col = mix(col, vec3(0.07, 0.035, 0.04) + vec3(1.0, 0.62, 0.4) * wr * 0.5, smoothstep(px, -px, wd)); } float rip = smoothstep(0.55, 0.9, noise(vec2(q.x * 5.0, (near - q.y) * 60.0 + q.x * 8.0))); col = mix(col, mix(vec3(0.08, 0.035, 0.05), vec3(0.7, 0.38, 0.29), exp(-max(near - q.y, 0.0) * 70.0) * 0.8) + vec3(0.2, 0.09, 0.07) * rip * exp(-(near - q.y) * 6.0), smoothstep(px, -px, q.y - near)); vec2 fq = (q - vec2(nx, near - 0.003)) / 0.085; float fig = person(fq, t) * 0.085; if (fig < 0.01) { float frim = smoothstep(-0.2, 1.0, person(fq + L * 0.06, t) * 0.085 / (px * 1.5)); col = mix(col, vec3(0.05, 0.025, 0.03) + vec3(1.0, 0.66, 0.42) * frim * 0.9, smoothstep(px, -px, fig)); } // Dust: sunlit veils, the searchlight through them, grains blowing across float dust = noise(vec2(q.x * 2.5 - t * 0.12, y * 9.0)) * 0.6 + noise(vec2(q.x * 6.0 - t * 0.3, y * 20.0)) * 0.4; col = mix(col, mix(vec3(0.75, 0.42, 0.36), vec3(1.0, 0.7, 0.48), exp(-sd * 3.0)), smoothstep(0.2, 0.85, dust) * exp(-abs(y + 0.03) * 7.0) * 0.7); col += vec3(1.0, 0.86, 0.68) * beam * (0.18 + 0.5 * dust); for (int i = 0; i < 2; i++) { float fi = float(i), s = 22.0 - fi * 9.0; col += vec3(1.0, 0.8, 0.62) * motes(q * s * vec2(0.5, 1.0) + vec2(t * (0.8 + fi * 0.6), sin(q.x * 3.0 + t * 0.5 + fi) * 0.5), 0.1, 0.15, fi * 7.0) * (0.3 + fi * 0.1); } // Grade: soft shoulder, warm vignette col = col / (1.0 + col * 0.2); color = vec4(col * (1.0 - 0.35 * pow(length(uv - vec2(0.55, 0.5)) * 1.2, 2.0)), 1.0); }