Published
Edited
Dec 15, 2020
2 stars
Insert cell
Insert cell
Insert cell
p = getRandomPalette()
Insert cell
//palette = shuffle(p)
// palette = ['#e0f0ea', '#303030', '#ffff00', '#ff0000']
palette = ["#540d6e", "#3bceac", "#ffd23f", "#ee4266", "#0ead69"]
Insert cell
Insert cell
Insert cell
seeds = new Array(6).fill(0).map(Math.random)
Insert cell
sh = () => raymarch({
// antiAliasing: 3,
eye: `vec3(-3, 2.5, -3) * .59`,
target: `vec3(0, -.05, 0)`,
distMax: 100,
sceneSDF: `
#define PI ${Math.PI}
#define TAU ${Math.PI * 2}

#define NUM_COLORS ${palette.length}.

uniform sampler2D u_texture;

${iqSDF.sdBox()}
${noise.replace('#pragma glslify: export(snoise)', '')}
${iqSDF.opUnion()}
${iqSDF.opSubtraction()}
${iqSDF.opIntersection()}
${glslSnippets.rotate3D()}
${motionToolkit.easeInOutQuad()}

highp float rand(vec2 co) {
highp float a = 12.9898;
highp float b = 78.233;
highp float c = 43758.5453;
highp float dt= dot(co.xy ,vec2(a,b));
highp float sn= mod(dt,3.14);
return fract(sin(sn) * c);
}

float wireframedBox(vec3 p, vec3 dim, float weight) {
float d = sdBox(p, dim + weight / 2.);
d = opSubtraction(sdBox(p, (dim - weight / 2.) + vec3(1, 0, 0)), d);
d = opSubtraction(sdBox(p, (dim - weight / 2.) + vec3(0, 1, 0)), d);
d = opSubtraction(sdBox(p, (dim - weight / 2.) + vec3(0, 0, 1)), d);
return d;
}

float glow = 0.;

vec2 sceneSDF(vec3 p) {
float t = easeInOutQuad(u_time) * PI;
float sinT = sin(t);
float cosT = cos(t);
vec3 pp = p;

vec2 d = vec2(10e5, 1.);
float dg = 10e5;

for(float i = 1.; i < 7.; i ++) {
float width = clamp(.01, .5, .25 + sin(easeInOutQuad(fract(u_time + ${seeds[0]} * i)) * TAU) * .25 * mod(${seeds[1]} * i, 1.));
float height = clamp(.01, 1., .5 + cos(easeInOutQuad(fract(u_time + ${seeds[2]} * i)) * TAU) * .5 * mod(${seeds[3]} * i, 1.));
float depth = clamp(.01, 1., .5 - sin(easeInOutQuad(fract(u_time + ${seeds[4]} * i)) * TAU) * .5 * mod(${seeds[5]} * i, 1.));


vec3 dims = vec3(width, height, depth);
//float colID = mod(i, NUM_COLORS - 1.) + 1.;
float colID = 1.;
if(mod(i, 3.) == 0.) colID = 3.;
float w = .05;
if(mod(i, 5.) == 0.) {
colID = 2.;
w = .02;
}

float box = wireframedBox(p, dims, w);
box = opUnion(box, wireframedBox(p, dims.xzy, w));
box = opUnion(box, wireframedBox(p, dims.yxz, w));
box = opUnion(box, wireframedBox(p, dims.yzx, w));
box = opUnion(box, wireframedBox(p, dims.zyx, w));
box = opUnion(box, wireframedBox(p, dims.zxy, w));
if(mod(i, 5.) == 0.) dg = opUnion(dg, box);
d = opUnion(vec2(box, colID), d);
}

return d;
}`,
computeColor: `
vec3 computeColor(vec3 ro, vec3 rd, vec3 pos, float d, float m) {
vec3 nor = calcNormal(pos);
vec3 ref = reflect(rd, nor); // reflected ray

// material
vec3 col = texture2D(u_texture, vec2((floor(m - 1.) + .5) / NUM_COLORS, .5)).rgb;

// lighting
float occ = calcAO(pos, nor); // ambient occlusion
vec3 lig = normalize(vec3(-0.4, 0.7, -0.6)); // sunlight
float amb = clamp(0.5 + 0.5 * nor.y, 0.0, 1.0); // ambient light
float dif = clamp(dot(nor, lig), 0.0, 1.0); // diffuse reflection from sunlight
// backlight
float bac = clamp(dot(nor, normalize(vec3(-lig.x, 0.0, -lig.z))), 0.0, 1.0) * clamp(1.0 - pos.y, 0.0, 1.0);
float dom = smoothstep(-0.1, 0.1, ref.y); // dome light
float fre = pow(clamp(1.0 + dot(nor, rd), 0.0, 1.0), 2.0); // fresnel
float spe = pow(clamp(dot(ref, lig), 0.0, 1.0), 16.0); // specular reflection

dif *= softshadow(pos, lig, 0.02, 2.5);
dom *= softshadow(pos, ref, 0.02, 2.5);

vec3 lin = vec3(0.0);
lin += 1.30 * dif * vec3(1.00, 0.80, 0.55);
lin += 2.00 * spe * vec3(1.00, 0.90, 0.70) * dif;
lin += 0.40 * amb * vec3(0.40, 0.60, 1.00) * occ;
lin += 0.50 * dom * vec3(0.40, 0.60, 1.00) * occ;
lin += 0.50 * bac * vec3(0.25, 0.25, 0.25) * occ;
lin += 0.25 * fre * vec3(1.00, 1.00, 1.00) * occ;
col = col * lin;

// mix in fog?
col = mix(col, vec3(0.8, 0.9, 1.0), 1.0 - exp(-0.0002 * d * d * d));
// col = mix(col, vec3(0.1), 1.0 - exp(-0.00001 * d * d * d));
// gamma
//col = pow(col, vec3(0.4545));

return col;
}`,
logShader: true
})
Insert cell
noise = glslSnippets.snoise4()
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
iqSDF
Insert cell
Insert cell
motionToolkit
Insert cell
Insert cell
glslSnippets
Insert cell
import {shuffle} from '@makio135/utilities'
Insert cell
import {getRandomPalette, displayPalettes, hexToRgb} from '@makio135/give-me-colors'
Insert cell

Purpose-built for displays of data

Observable is your go-to platform for exploring data and creating expressive data visualizations. Use reactive JavaScript notebooks for prototyping and a collaborative canvas for visual data exploration and dashboard creation.
Learn more