Lesson 7 of 10 · Shader animation
Oscillator stack
Three rings that never sync. Infinite motion.
One sin() is predictable. Three at mutually irrational frequencies are unpredictable forever.
sin(T*0.3) + sin(T*0.17) + sin(T*0.07). Those three frequencies never synchronize. The result: a signal that varies perpetually.
Three desynchronized clocks. The most elegant controlled chaos.
Oscillator stackSumming multiple oscillators at frequencies that are not multiples of each other. In audio synthesis it is called additive synthesis. Three oscillators are enough to break any cycle.
Remove the third
sin, it feels more predictable. Change 0.07 to 0.3, two frequencies match, the pattern simplifies.The code
void main(){
vec2 p = (2.*gl_FragCoord.xy - R) / min(R.x, R.y);
float r1 = 0.25 + sin(T * 0.3) * 0.1;
float r2 = 0.48 + sin(T * 0.17) * 0.12;
float r3 = 0.75 + sin(T * 0.07) * 0.14;
float d = length(p);
float ds = length(p + vec2(.05, -.07));
vec3 col = vec3(0.02, 0.02, 0.06);
col -= vec3(smoothstep(.08,.0,abs(ds-r1))+smoothstep(.09,.0,abs(ds-r2))+smoothstep(.1,.0,abs(ds-r3)))*.12;
col = max(col, vec3(0.));
col += vec3(0.95, 0.3, 0.9) * smoothstep(0.04, 0.0, abs(d-r1));
col += vec3(0.5, 0.4, 0.98) * smoothstep(0.05, 0.0, abs(d-r2));
col += vec3(0.3, 0.65, 0.95) * smoothstep(0.06, 0.0, abs(d-r3));
col += vec3(.4,.15,.4) * exp(-abs(d-r1)*5.) * .25;
col += vec3(.2,.15,.45) * exp(-abs(d-r2)*4.) * .2;
col += vec3(.12,.25,.4) * exp(-abs(d-r3)*3.) * .15;
col = hueShift(col, 0.0);
gl_FragColor = vec4(col, 1.);
}