Skip to content

Instantly share code, notes, and snippets.

@CharStiles
Last active November 22, 2021 05:15
Show Gist options
  • Star 2 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save CharStiles/327768a23e5e64b7a9d6163ae305b15b to your computer and use it in GitHub Desktop.
Save CharStiles/327768a23e5e64b7a9d6163ae305b15b to your computer and use it in GitHub Desktop.
// Author: charstiles
// Title: raymarch at at parsons
#ifdef GL_ES
precision mediump float;
#endif
uniform vec2 u_resolution;
uniform vec2 u_mouse;
uniform float u_time;
const int step = 128;
const float maxDist = 10.3;
const float PI = 3.141592658;
const float smallNumber = 0.02;
// http://www.iquilezles.org/www/articles/palettes/palettes.htm
// As t runs from 0 to 1 (our normalized palette index or domain),
//the cosine oscilates c times with a phase of d.
//The result is scaled and biased by a and b to meet the desired constrast and brightness.
vec3 cosPalette( float t, vec3 a, vec3 b, vec3 c, vec3 d )
{
return a + b*cos( 6.28318*(c*t+d) );
}
float sphere(vec3 pos, float rad){
return length(pos) - rad;
}
// Repeat around the origin by a fixed angle.
// For easier use, num of repetitions is use to specify the angle.
float pModPolar(inout vec2 p, float repetitions) {
float angle = 2.*PI/repetitions;
float a = atan(p.y, p.x) + angle/2.;
float r = length(p);
float c = floor(a/angle);
a = mod(a,angle) - angle/2.;
p = vec2(cos(a), sin(a))*r;
// For an odd number of repetitions, fix cell index of the cell in -x direction
// (cell index would be e.g. -5 and 5 in the two halves of the cell):
if (abs(c) >= (repetitions/2.)) c = abs(c);
return c;
}
vec3 hsv2rgb(vec3 c)
{
vec4 K = vec4(1.0, 2.0 / 3.0, 1.0 / 3.0, 3.0);
vec3 p = abs(fract(c.xxx + K.xyz) * 6.0 - K.www);
return c.z * mix(K.xxx, clamp(p - K.xxx, 0.0, 1.0), c.y);
}
float smin( float a, float b, float k )
{
float h = clamp( 0.5+0.5*(b-a)/k, 0.0, 1.0 );
return mix( b, a, h ) - k*h*(1.0-h);
}
float scene(vec3 pos){
vec3 modSpace = vec3(5.,2.,2.);
pos = mod(pos,modSpace) - 1.;
float s = sphere(pos, 0.4);
pModPolar(pos.xy,3.0);
float s2 = sphere(pos +( sin(u_time)*0.6), 0.2);
return smin(s,s2,(cos(u_time*2.)+1.)* 0.2);
}
vec3 lookAt(vec2 uv, vec3 camOrigin, vec3 camTarget){
vec3 zAxis = normalize(camTarget - camOrigin);
vec3 up = vec3(0,1,0);
vec3 xAxis = normalize(cross(up, zAxis));
vec3 yAxis = normalize(cross(zAxis, xAxis));
float fov = 2.;
vec3 dir = (normalize(uv.x * xAxis + uv.y * yAxis + zAxis * fov));
return dir;
}
vec3 estimateNormal(vec3 p) {
vec3 n = vec3(
scene(vec3(p.x + smallNumber, p.yz)) -
scene(vec3(p.x - smallNumber, p.yz)),
scene(vec3(p.x, p.y + smallNumber, p.z)) -
scene(vec3(p.x, p.y - smallNumber, p.z)),
scene(vec3(p.xy, p.z + smallNumber)) -
scene(vec3(p.xy, p.z - smallNumber))
);
return normalize(n);
}
float lighting(vec3 origin, vec3 dir, vec3 normal) {
vec3 lightPos = vec3(cos(u_time)*20., sin(u_time), 12.);
vec3 light = normalize(lightPos - origin);
float diffuse = max(0., dot(light, normal));
vec3 reflectedRay = 2. * dot(light, normal) * normal - light;
float specular = max(0., (pow(dot(reflectedRay, light), 3.)));
float ambient = 0.05;
return ambient + diffuse + specular;
}
vec4 trace(vec3 camOrigin, vec3 dir){
vec3 ray = camOrigin;
float totalDist = 0.;
float dist;
for(int i = 0 ; i < step; i ++){
dist = scene(ray);
totalDist += dist;
if (dist < 0.001){
vec3 n = estimateNormal(ray);
float l = lighting(ray, dir, n);
vec3 color = cosPalette(totalDist,
vec3(0.5, 0.5, 0.5),
vec3(0.5, 0.5, 0.5),
vec3(1.0, 1.0, 0.5),
vec3(0.80, 0.90, 0.30));
return vec4(color * l, 1.0);
// return vec4(cosPalette(totalDist,
// vec3(0.5, 0.5, 0.5),
// vec3(0.5, 0.5, 0.5),
// vec3(1.0, 1.0, 0.5),
// vec3(0.80, 0.90, 0.30)), 1.0);
//return vec4(hsv2rgb(vec3(totalDist,
//1.0,1.0)),1.0);//;/maxDist);
}
if (totalDist > maxDist){
return vec4(0);
}
ray += dist*dir;
}
return vec4(0.0);
}
void main() {
vec2 uv = gl_FragCoord.xy/u_resolution.xy;
uv = (uv *2.0) - vec2(1.0);
uv.x *= u_resolution.x/u_resolution.y;
vec3 camOrigin = vec3(0.0,0.0,-1.0);
vec3 rayOrigin = vec3(uv.x + camOrigin.x,
uv.y + camOrigin.y,
camOrigin.z + 1.0);
vec3 camTarget = vec3(0,sin(u_time), 2);
vec3 dir = lookAt(uv, camOrigin, camTarget);
//vec3 dir = rayOrigin - camOrigin;
vec4 color = trace(camOrigin,dir);
gl_FragColor = color;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment