open .fs {
"DESCRIPTION" : "Gray-Scott reaction-diffusion that grows liquid coral and ink-like cells." ,
"INPUTS" : [
{ "NAME" : "feed" , "TYPE" : "float" , "DEFAULT" : 0.055 , "MIN" : 0.010 , "MAX" : 0.080 } ,
{ "NAME" : "kill" , "TYPE" : "float" , "DEFAULT" : 0.062 , "MIN" : 0.030 , "MAX" : 0.075 } ,
{ "NAME" : "simSpeed" , "TYPE" : "float" , "DEFAULT" : 1.0 , "MIN" : 0.1 , "MAX" : 2.0 } ,
{ "NAME" : "seedRate" , "TYPE" : "float" , "DEFAULT" : 0.62 , "MIN" : 0.0 , "MAX" : 1.0 } ,
{ "NAME" : "colorPhase" , "TYPE" : "float" , "DEFAULT" : 0.56 , "MIN" : 0.0 , "MAX" : 1.0 }
] ,
"PASSES" : [
{ "TARGET" : "chem" , "PERSISTENT" : true , "FLOAT" : true } ,
{ }
]
}
#define TAU 6.28318530718
vec3 palette (float t) {
return 0.52 + 0.48 * cos (TAU * (t + colorPhase + vec3 (0.00 , 0.18 , 0.42 )));
}
vec2 chemistry (vec2 uv) {
return IMG_NORM_PIXEL (chem, uv).rg;
}
void main () {
vec2 uv = isf_FragNormCoord ;
if (PASSINDEX == 0 ) {
vec2 px = 1.0 / RENDERSIZE ;
vec2 c = chemistry (uv);
if (FRAMEINDEX < 2 || dot (c, c) < 0.000001 ) {
vec2 p = uv - 0.5 ;
p.x *= RENDERSIZE .x / RENDERSIZE .y;
float organic = sin (p.x * 31.0 ) + sin (p.y * 27.0 )
+ sin ((p.x + p.y) * 19.0 ) + sin (length (p) * 43.0 );
float seed = smoothstep (1.65 , 2.75 , organic)
* smoothstep (0.58 , 0.12 , length (p));
seed += smoothstep (0.155 , 0.115 , length (p));
seed += smoothstep (0.052 , 0.028 , length (p - vec2 (0.23 , 0.02 )));
seed += smoothstep (0.052 , 0.028 , length (p + vec2 (0.23 , -0.02 )));
seed += smoothstep (0.040 , 0.020 , length (p - vec2 (0.0 , 0.25 )));
seed += smoothstep (0.040 , 0.020 , length (p + vec2 (0.0 , 0.25 )));
seed = clamp (seed, 0.0 , 1.0 );
c = mix (vec2 (1.0 , 0.0 ), vec2 (0.52 , 0.28 ), seed);
}
vec2 lap = -c;
lap += 0.20 * chemistry (uv + vec2 (px.x, 0.0 ));
lap += 0.20 * chemistry (uv - vec2 (px.x, 0.0 ));
lap += 0.20 * chemistry (uv + vec2 (0.0 , px.y));
lap += 0.20 * chemistry (uv - vec2 (0.0 , px.y));
lap += 0.05 * chemistry (uv + px);
lap += 0.05 * chemistry (uv - px);
lap += 0.05 * chemistry (uv + vec2 (px.x, -px.y));
lap += 0.05 * chemistry (uv + vec2 (-px.x, px.y));
float u = c.r;
float v = c.g;
float reaction = u * v * v;
float stepSize = min (TIMEDELTA * 60.0 , 1.35 ) * simSpeed;
u += (0.16 * lap.r - reaction + feed * (1.0 - u)) * stepSize;
v += (0.08 * lap.g + reaction - (kill + feed) * v) * stepSize;
vec2 orbit = vec2 (
0.5 + 0.29 * cos (TIME * 0.31 ),
0.5 + 0.21 * sin (TIME * 0.47 )
);
vec2 od = uv - orbit;
od.x *= RENDERSIZE .x / RENDERSIZE .y;
vec2 orbit2 = vec2 (
0.5 + 0.24 * cos (TIME * 0.23 + 3.14159 ),
0.5 + 0.31 * sin (TIME * 0.39 + 1.4 )
);
vec2 od2 = uv - orbit2;
od2.x *= RENDERSIZE .x / RENDERSIZE .y;
float freshSeed = smoothstep (0.026 , 0.0 , length (od));
freshSeed += 0.8 * smoothstep (0.022 , 0.0 , length (od2));
freshSeed = clamp (freshSeed * seedRate, 0.0 , 1.0 );
v = max (v, freshSeed * 0.38 );
u = mix (u, 0.52 , freshSeed);
gl_FragColor = vec4 (clamp (u, 0.0 , 1.0 ), clamp (v, 0.0 , 1.0 ), 0.0 , 1.0 );
} else {
vec2 c = IMG_THIS_PIXEL (chem).rg;
float ink = smoothstep (0.012 , 0.24 , c.g);
float membrane = smoothstep (0.030 , 0.0 , abs (c.g - 0.075 ));
vec3 col = palette (c.g * 3.4 + c.r * 0.18 );
col *= 0.035 + 1.52 * ink;
col += membrane * palette (c.r + 0.17 ) * 0.92 ;
col += vec3 (0.003 , 0.006 , 0.014 );
col = col / (1.0 + 0.45 * col);
gl_FragColor = vec4 (col, 1.0 );
}
}