#version 330 compatibility const float pi = 3.141592653589793; const vec3 X = vec3(1.0, 0.0, 0.0); const vec3 Y = vec3(0.0, 1.0, 0.0); const vec3 Z = vec3(0.0, 0.0, 1.0); uint hash(uint a); float uniform01(uint a) { return float(a) / 4294967296.0; } uint hash(int a) { return hash(uint(a)); } uint hash(float a) { return hash(floatBitsToUint(a)); } uint hash(uvec2 a) { return hash(a.x ^ hash(a.y)); } uint hash(uvec3 a) { return hash(a.x ^ hash(a.yz)); } uint hash(uvec4 a) { return hash(a.x ^ hash(a.yzw)); } uint hash(ivec2 a) { return hash(uint(a.x) ^ hash(a.y)); } uint hash(ivec3 a) { return hash(uint(a.x) ^ hash(a.yz)); } uint hash(ivec4 a) { return hash(uint(a.x) ^ hash(a.yzw)); } uint hash(vec2 a) { return hash(floatBitsToUint(a.x) ^ hash(a.y)); } uint hash(vec3 a) { return hash(floatBitsToUint(a.x) ^ hash(a.yz)); } uint hash(vec4 a) { return hash(floatBitsToUint(a.x) ^ hash(a.yzw)); } uint hash_burtle_1(uint a) { a = (a ^ 61u) ^ (a >> 16u); a = a + (a << 3u); a = a ^ (a >> 4u); a = a * 0x27d4eb2du; a = a ^ (a >> 15u); return a; } uint hash_burtle_2(uint a) { a = (a+0x7ed55d16u) + (a<<12u); a = (a^0xc761c23cu) ^ (a>>19u); a = (a+0x165667b1u) + (a<<5u); a = (a+0xd3a2646cu) ^ (a<<9u); a = (a+0xfd7046c5u) + (a<<3u); a = (a^0xb55a4f09u) ^ (a>>16u); return a; } uint hash_burtle_3(uint a) { a -= (a<<6u); a ^= (a>>17u); a -= (a<<9u); a ^= (a<<4u); a -= (a<<3u); a ^= (a<<10u); a ^= (a>>15u); return a; } uint hash_burtle_4(uint a) { a += ~(a<<15u); a ^= (a>>10u); a += (a<<3u); a ^= (a>>6u); a += ~(a<<11u); a ^= (a>>16u); return a; } uint hash_burtle_5(uint a) { a = (a+0x479ab41du) + (a<<8u); a = (a^0xe4aa10ceu) ^ (a>>5u); a = (a+0x9942f0a6u) - (a<<14u); a = (a^0x5aedd67du) ^ (a>>3u); a = (a+0x17bea992u) + (a<<7u); return a; } uint hash_burtle_6(uint a) { a = (a^0xdeadbeefu) + (a<<4u); a = a ^ (a>>10u); a = a + (a<<7u); a = a ^ (a>>13u); return a; } uint hash_burtle_7(uint a) { a = a ^ (a>>4u); a = (a^0xdeadbeefu) + (a<<5u); a = a ^ (a>>11u); return a; } uint hash_burtle_8(uint a) { a = (a+0x479ab41du) + (a<<8u); a = (a^0xe4aa10ceu) ^ (a>>5u); a = (a+0x9942f0a6u) - (a<<14u); a = (a^0x5aedd67du) ^ (a>>3u); a = (a+0x17bea992u) + (a<<7u); return a; } uint hash_burtle_9(uint a) { a = (a+0x7ed55d16u) + (a<<12u); a = (a^0xc761c23cu) ^ (a>>19u); a = (a+0x165667b1u) + (a<<5u); a = (a+0xd3a2646cu) ^ (a<<9u); a = (a+0xfd7046c5u) + (a<<3u); a = (a^0xb55a4f09u) ^ (a>>16u); return a; } uint hash_burtle_10(uint a) { a = (a+0x7fb9b1eeu) + (a<<12u); a = (a^0xab35dd63u) ^ (a>>19u); a = (a+0x41ed960du) + (a<<5u); a = (a+0xc7d0125eu) ^ (a<<9u); a = (a+0x071f9f8fu) + (a<<3u); a = (a^0x55ab55b9u) ^ (a>>16u); return a; } uint hash_burtle_11(uint a) { a -= (a<<6u); a ^= (a>>17u); a -= (a<<9u); a ^= (a<<4u); a -= (a<<3u); a ^= (a<<10u); a ^= (a>>15u); return a; } uint hash_burtle_12(uint a) { a += ~(a<<15u); a ^= (a>>10u); a += (a<<3u); a ^= (a>>6u); a += ~(a<<11u); a ^= (a>>16u); return a; } uniform float Exposure; //slider[0.0,1.0,100.0] uniform float FOV; //slider[0.0,0.4,2.0] NotLockable uniform vec3 Eye; //slider[(-50,-50,-50),(0,0,-10),(50,50,50)] NotLockable uniform vec3 Target; //slider[(-50,-50,-50),(0,0,0),(50,50,50)] NotLockable uniform vec3 Up; //slider[(0,0,0),(0,1,0),(0,0,0)] NotLockable uniform vec2 pixelSize; #if 0 varying vec3 Forward; varying vec3 UpOrtho; varying vec3 Right; varying vec2 coord; varying vec2 texCoord; void main(void) { Forward = normalize(Target - Eye); UpOrtho = normalize(Up - dot(Forward, Up) * Forward); Right = normalize(cross(Forward, UpOrtho)); coord = (gl_ProjectionMatrix * gl_Vertex).xy; coord.x *= pixelSize.y / pixelSize.x; texCoord = (gl_Vertex.xy + vec2(1.0)) * 0.5; gl_Position = gl_Vertex; } #endif varying vec3 Forward; varying vec3 UpOrtho; varying vec3 Right; varying vec2 coord; varying vec2 texCoord; //uniform float FOV; //uniform vec3 Eye; //uniform vec2 pixelSize; uniform sampler2D backbuffer; uniform int subframe; uniform float time; struct Random { uint seed, index; }; struct Camera { vec3 origin, X, Y, Z; float fieldOfView; }; struct Ray { vec3 origin, direction; float wavelength; vec2 index; }; uint hash(uint n); Ray camera(Random PRNG, Camera C, vec2 coord); float raytrace(Random PRNG, Ray V); vec3 film(Random PRNG, float wavelength, float intensity); Random srand(Random PRNG, int seed) { PRNG.seed = hash(PRNG.seed ^ hash(uint(seed))); return PRNG; } void main(void) { Random PRNG; PRNG.seed = hash(vec3(gl_FragCoord.xy, time)); PRNG.index = uint(subframe); Camera C; C.origin = Eye; C.X = Right; C.Y = UpOrtho; C.Z = Forward; C.fieldOfView = FOV; Ray V = camera(srand(PRNG, 1), C, coord); float I = raytrace(srand(PRNG, 2), V); vec3 rgb = film(srand(PRNG, 3), V.wavelength, I); vec4 next = vec4(rgb, 1.0); if (! (next == next)) next = vec4(0.0); if (! (dot(next, next) < 1.0/0.0)) next = vec4(0.0); vec4 prev = texture(backbuffer, texCoord); gl_FragColor = prev + next; } float uniform01(Random PRNG) { return uniform01(PRNG.seed); } float uniform01(Random PRNG, int i) { return uniform01(srand(PRNG, i)); } float uniform1(Random PRNG) { return uniform01(PRNG, 1); } vec2 uniform2(Random PRNG) { return vec2(uniform01(PRNG, 1), uniform01(PRNG, 2)); } vec3 uniform3(Random PRNG) { return vec3(uniform01(PRNG, 1), uniform01(PRNG, 2), uniform01(PRNG, 3)); } vec4 uniform4(Random PRNG) { return vec4(uniform01(PRNG, 1), uniform01(PRNG, 2), uniform01(PRNG, 3), uniform01(PRNG, 4)); } vec2 uniformDisc(vec2 u01) { float r = sqrt(u01.x); float t = 2.0 * pi * u01.y; return r * vec2(cos(t), sin(t)); } vec2 uniformDisc(Random PRNG) { return uniformDisc(uniform2(PRNG)); } vec2 gaussian(vec2 u01) { float s = u01.x; float t = 2.0 * pi * u01.y; if (s > 0.0) return vec2(cos(t), sin(t)) * sqrt(-2.0 * log(s) / s); else return vec2(0.0); } vec2 gaussian2(Random PRNG) { return gaussian(uniform2(PRNG)); } float gaussian1(Random PRNG) { return gaussian2(PRNG).x; } vec4 gaussian4(Random PRNG) { vec4 u = uniform4(PRNG); return vec4(gaussian(u.xy), gaussian(u.zw)); } vec3 gaussian3(Random PRNG) { return gaussian4(PRNG).xyz; } mat3 localCoordinates(vec3 normal) { vec3 w = X; if (abs(dot(Y, normal)) < abs(dot(w, normal))) w = Y; if (abs(dot(Z, normal)) < abs(dot(w, normal))) w = Z; vec3 a = normalize(cross(w, normal)); vec3 b = normalize(cross(a, normal)); if (dot(normal, cross(a, b)) < 0.0) { vec3 t = a; a = b; b = t; } return mat3(a, b, normal); } vec3 cosHemisphere(vec2 uDisc, vec3 normal) { mat3 m = localCoordinates(normal); vec3 w = vec3(uDisc, sqrt(max(0.0, 1.0 - dot(uDisc, uDisc)))); return m * w; } float halton(uint b, uint i) { float f = 1.0; float r = 0.0; if (b > 1u) while (i > 0u) { f /= float(b); r += f * float(i % b); i /= b; } return r; } vec2 halton(uvec2 b, uint i) { return vec2(halton(b.x, i), halton(b.y, i)); } vec3 halton(uvec3 b, uint i) { return vec3(halton(b.x, i), halton(b.y, i), halton(b.z, i)); } vec4 halton(uvec4 b, uint i) { return vec4(halton(b.x, i), halton(b.y, i), halton(b.z, i), halton(b.w, i)); } float halton(Random PRNG, int b1) { float h = halton(uint(b1), PRNG.index) + uniform1(PRNG); return h - floor(h); } vec2 halton(Random PRNG, int b1, int b2) { vec2 h = halton(uvec2(b1, b2), PRNG.index) + uniform2(PRNG); return h - floor(h); } vec3 halton(Random PRNG, int b1, int b2, int b3) { vec3 h = halton(uvec3(b1, b2, b3), PRNG.index) + uniform3(PRNG); return h - floor(h); } vec4 halton(Random PRNG, int b1, int b2, int b3, int b4) { vec4 h = halton(uvec4(b1, b2, b3, b4), PRNG.index) + uniform4(PRNG); return h - floor(h); } float halton1(Random PRNG) { return halton(PRNG, 2); } vec2 halton2(Random PRNG) { return halton(PRNG, 2, 3); } vec3 halton3(Random PRNG) { return halton(PRNG, 2, 3, 5); } vec4 halton4(Random PRNG) { return halton(PRNG, 2, 3, 5, 7); } vec2 haltonDisc(Random PRNG) { return uniformDisc(halton2(PRNG)); } struct Transform { mat4 forward; mat4 backward; }; Transform compose(Transform S, Transform T) { Transform R; R.forward = S.forward * T.forward; R.backward = T.backward * S.backward; return R; } Transform compose(Transform A, Transform B, Transform C) { return compose(compose(A, B), C); } Transform compose(Transform A, Transform B, Transform C, Transform D) { return compose(compose(compose(A, B), C), D); } vec3 forwardP(Transform T, vec3 p) { vec4 q = T.forward * vec4(p, 1.0); return q.xyz / q.w; } vec3 backwardP(Transform T, vec3 p) { vec4 q = T.backward * vec4(p, 1.0); return q.xyz / q.w; } vec3 forwardN(Transform T, vec3 n) { return normalize(inverse(transpose(mat3(T.forward))) * n); } vec3 backwardN(Transform T, vec3 n) { return normalize(inverse(transpose(mat3(T.backward))) * n); } Transform Identity() { Transform T; T.forward = mat4(1.0); T.backward = mat4(1.0); return T; } Transform Scale(float s) { Transform T; T.forward = mat4 ( s, 0.0, 0.0, 0.0 , 0.0, s, 0.0, 0.0 , 0.0, 0.0, s, 0.0 , 0.0, 0.0, 0.0, 1.0 ); s = 1.0 / s; T.backward = mat4 ( s, 0.0, 0.0, 0.0 , 0.0, s, 0.0, 0.0 , 0.0, 0.0, s, 0.0 , 0.0, 0.0, 0.0, 1.0 ); return T; } Transform Scale(vec3 s) { Transform T; T.forward = mat4 ( s.x, 0.0, 0.0, 0.0 , 0.0, s.y, 0.0, 0.0 , 0.0, 0.0, s.z, 0.0 , 0.0, 0.0, 0.0, 1.0 ); s = 1.0 / s; T.backward = mat4 ( s.x, 0.0, 0.0, 0.0 , 0.0, s.y, 0.0, 0.0 , 0.0, 0.0, s.z, 0.0 , 0.0, 0.0, 0.0, 1.0 ); return T; } Transform Translate(vec3 v) { Transform T; T.forward = mat4 ( 1.0, 0.0, 0.0, v.x , 0.0, 1.0, 0.0, v.y , 0.0, 0.0, 1.0, v.z , 0.0, 0.0, 0.0, 1.0 ); v = -v; T.backward = mat4 ( 1.0, 0.0, 0.0, v.x , 0.0, 1.0, 0.0, v.y , 0.0, 0.0, 1.0, v.z , 0.0, 0.0, 0.0, 1.0 ); return T; } Transform Rotate(vec4 q) { q = normalize(q); float i = q.x; float j = q.y; float k = q.z; float r = q.w; Transform T; T.forward = mat4 ( 1.0 - 2.0 * (j * j + k * k), 2.0 * (i * j - k * r), 2.0 * (i * k + j * r), 0.0 , 2.0 * (i * j + k * r), 1.0 - 2.0 * (i * i + k * k), 2.0 * (j * k - i * r), 0.0 , 2.0 * (i * k - j * r), 2.0 * (j * k + i * r), 1.0 - 2.0 * (i * i + j * j), 0.0 , 0.0, 0.0, 0.0, 1.0 ); T.backward = transpose(T.forward); return T; } struct Surface { vec3 position; vec3 normal; float de; }; Surface Invert(Surface s) { s.normal = - s.normal; s.de = - s.de; return s; } Surface Union(Surface a, Surface b) { if (a.de < b.de) return a; else return b; } Surface Union(Surface a, Surface b, Surface c) { return Union(Union(a, b), c); } Surface Union(Surface a, Surface b, Surface c, Surface d) { return Union(Union(Union(a, b), c), d); } Surface Union(Surface a, Surface b, Surface c, Surface d, Surface e) { return Union(Union(Union(Union(a, b), c), d), e); } Surface Union(Surface a, Surface b, Surface c, Surface d, Surface e, Surface f) { return Union(Union(Union(Union(Union(a, b), c), d), e), f); } Surface Intersection(Surface a, Surface b) { if (a.de > b.de) return a; else return b; } Surface Intersection(Surface a, Surface b, Surface c) { return Intersection(Intersection(a, b), c); } Surface Intersection(Surface a, Surface b, Surface c, Surface d) { return Intersection(Intersection(Intersection(a, b), c), d); } Surface Intersection(Surface a, Surface b, Surface c, Surface d, Surface e) { return Intersection(Intersection(Intersection(Intersection(a, b), c), d), e); } Surface Intersection(Surface a, Surface b, Surface c, Surface d, Surface e, Surface f) { return Intersection(Intersection(Intersection(Intersection(Intersection(a, b), c), d), e), f); } Surface Sphere(Transform T, Ray V) { vec3 world = V.origin; vec3 object = backwardP(T, world); vec3 normal = normalize(object); vec3 nearest = normal; Surface s; s.position = forwardP(T, object); s.normal = forwardN(T, normal); s.de = distance(s.position, forwardP(T, nearest)); return s; } Surface Plane(Transform T, Ray V, vec3 normal, float dist) { normal = normalize(normal); vec3 world = V.origin; vec3 object = backwardP(T, world); vec3 nearest = object - (dot(object, normal) - dist) * normal; Surface s; s.position = forwardP(T, object); s.normal = forwardN(T, normal); s.de = distance(s.position, forwardP(T, nearest)); return s; } Surface Cuboid(Transform T, Ray V, vec3 size) { return Intersection ( Plane(T, V, X, size.x) , Plane(T, V, -X, size.x) , Plane(T, V, Y, size.y) , Plane(T, V, -Y, size.y) , Plane(T, V, Z, size.z) , Plane(T, V, -Z, size.z) ); } Surface Cube(Transform T, Ray V, float size) { return Cuboid(T, V, vec3(size)); } Surface Cube(Transform T, Ray V) { return Cube(T, V, 1.0); } struct Hit { Surface surface; Ray ray; float factor; float emit; }; Hit Union(in Hit a, in Hit b) { if (a.surface.de < b.surface.de) return a; else return b; } Hit Union(in Hit a, in Hit b, in Hit c) { return Union(Union(a, b), c); } Hit Union(in Hit a, in Hit b, in Hit c, in Hit d) { return Union(Union(Union(a, b), c), d); } Hit Union(in Hit a, in Hit b, in Hit c, in Hit d, in Hit e) { return Union(Union(Union(Union(a, b), c), d), e); } Hit Union(in Hit a, in Hit b, in Hit c, in Hit d, in Hit e, in Hit f) { return Union(Union(Union(Union(Union(a, b), c), d), e), f); } Hit Union(in Hit a, in Hit b, in Hit c, in Hit d, in Hit e, in Hit f, in Hit g) { return Union(Union(Union(Union(Union(Union(a, b), c), d), e), f), g); } Hit Intersection(in Hit a, in Hit b) { if (a.surface.de > b.surface.de) return a; else return b; } Hit Intersection(in Hit a, in Hit b, in Hit c) { return Intersection(Intersection(a, b), c); } Hit Intersection(in Hit a, in Hit b, in Hit c, in Hit d) { return Intersection(Intersection(Intersection(a, b), c), d); } Hit Intersection(in Hit a, in Hit b, in Hit c, in Hit d, in Hit e) { return Intersection(Intersection(Intersection(Intersection(a, b), c), d), e); } Hit Intersection(in Hit a, in Hit b, in Hit c, in Hit d, in Hit e, in Hit f) { return Intersection(Intersection(Intersection(Intersection(Intersection(a, b), c), d), e), f); } Hit Light(Surface S, Ray V, float brightness) { Hit h; h.surface = S; h.ray = V; h.factor = 0.0; h.emit = brightness; return h; } Hit Diffuse(Random PRNG, Surface S, Ray V, float albedo) { V.direction = cosHemisphere(haltonDisc(PRNG), S.normal); Hit h; h.surface = S; h.ray = V; h.factor = albedo; h.emit = 0.0; return h; } struct Fresnel { float Rs, Rp, Ts, Tp; }; Fresnel fresnel(vec3 incident, vec3 normal, float n1, float n2) { float dotNI = dot(incident, normal); float eta = n1 / n2; float c1 = -dotNI; float c2 = 1.0 - (1.0 - c1 * c1) * (eta * eta); Fresnel f; if (c2 < 0.0) { f.Rs = 1.0; f.Rp = 1.0; f.Ts = 0.0; f.Tp = 0.0; } else { c2 = sqrt(c2); float rs = (eta * c1 - c2) / (eta * c1 + c2); float rp = (eta * c2 - c1) / (eta * c2 + c1); float ts = 2.0 * eta * c1 / (eta * c1 + c2); float tp = 2.0 * eta * c1 / (eta * c2 + c1); f.Rs = rs * rs; f.Rp = rp * rp; f.Ts = ts * ts; f.Tp = tp * tp; } return f; } Hit Transparent(Random PRNG, Surface S, Ray V, vec2 index) { vec2 nk1 = V.index; vec2 nk2 = index; bool inside = false; if (dot(V.direction, S.normal) > 0.0) { vec2 t = nk1; nk1 = nk2; nk2 = t; S = Invert(S); inside = true; } Fresnel F = fresnel(V.direction, S.normal, nk1.x, nk2.x); float R = 0.5 * (F.Rs + F.Rp); float T = 0.5 * (F.Ts + F.Tp); float RT = R + T; float hRT = halton1(PRNG); hRT -= floor(hRT); if (mix(0.0, RT, hRT) < R) { V.direction = reflect(V.direction, S.normal); V.index = nk1; } else { V.direction = refract(V.direction, S.normal, nk1.x / nk2.x); V.index = nk2; } if (inside) { S = Invert(S); } Hit h; h.surface = S; h.ray = V; h.factor = 1.0; h.emit = 0.0; return h; } float absorption(float k, float nm, float dist) { return exp(-4.0 * pi * k * dist / (1.0e-9 * nm)); } float D65(float nm) { const float d65_min = 300.0; const float d65_max = 780.0; const float d65_step = 5.0; const float d65_v[97] = float[97] ( 0.034100 , 1.664300 , 3.294500 , 11.765200 , 20.236000 , 28.644700 , 37.053500 , 38.501100 , 39.948800 , 42.430200 , 44.911700 , 45.775000 , 46.638300 , 49.363700 , 52.089100 , 51.032300 , 49.975500 , 52.311800 , 54.648200 , 68.701500 , 82.754900 , 87.120400 , 91.486000 , 92.458900 , 93.431800 , 90.057000 , 86.682300 , 95.773600 , 104.865000 , 110.936000 , 117.008000 , 117.410000 , 117.812000 , 116.336000 , 114.861000 , 115.392000 , 115.923000 , 112.367000 , 108.811000 , 109.082000 , 109.354000 , 108.578000 , 107.802000 , 106.296000 , 104.790000 , 106.239000 , 107.689000 , 106.047000 , 104.405000 , 104.225000 , 104.046000 , 102.023000 , 100.000000 , 98.167100 , 96.334200 , 96.061100 , 95.788000 , 92.236800 , 88.685600 , 89.345900 , 90.006200 , 89.802600 , 89.599100 , 88.648900 , 87.698700 , 85.493600 , 83.288600 , 83.493900 , 83.699200 , 81.863000 , 80.026800 , 80.120700 , 80.214600 , 81.246200 , 82.277800 , 80.281000 , 78.284200 , 74.002700 , 69.721300 , 70.665200 , 71.609100 , 72.979000 , 74.349000 , 67.976500 , 61.604000 , 65.744800 , 69.885600 , 72.486300 , 75.087000 , 69.339800 , 63.592700 , 55.005400 , 46.418200 , 56.611800 , 66.805400 , 65.094100 , 63.382800 ); float f = (nm - d65_min) / d65_step; int i0 = int(floor(f)); int i1 = i0 + 1; float f1 = f - float(i0); if (i0 < 0) return 0.0; if (i1 > 97 - 1) return 0.0; return mix(d65_v[i0], d65_v[i1], f1) * 0.01; } float Glass_n(float wavelength) { float l2 = 1.0e-6 * wavelength * wavelength; return sqrt(1.0 + l2 * ( 1.34533359 / (l2 - 0.00997743871) + 0.209073176 / (l2 - 0.0470450767) + 0.937357162 / (l2 - 111.886764) )); } float Glass_k(float wavelength) { const vec2 glass_lk[13] = vec2[13] ( vec2(1000.0 * 0.390, 2.8886e-8) , vec2(1000.0 * 0.400, 1.9243e-8) , vec2(1000.0 * 0.405, 1.6869e-8) , vec2(1000.0 * 0.420, 1.2087e-8) , vec2(1000.0 * 0.436, 9.7490e-9) , vec2(1000.0 * 0.460, 8.8118e-9) , vec2(1000.0 * 0.500, 4.7818e-9) , vec2(1000.0 * 0.546, 3.4794e-9) , vec2(1000.0 * 0.580, 3.6961e-9) , vec2(1000.0 * 0.620, 3.9510e-9) , vec2(1000.0 * 0.660, 6.3120e-9) , vec2(1000.0 * 0.700, 4.4608e-9) , vec2(1000.0 * 1.060, 6.7549e-9) ); if (wavelength < glass_lk[0][0]) return glass_lk[0][1]; for (int i0 = 0; i0 < 12; ++i0) { int i1 = i0 + 1; float l0 = glass_lk[i0][0]; float l1 = glass_lk[i1][0]; if (l0 <= wavelength && wavelength <= l1) { float f1 = (wavelength - l0) / (l1 - l0); float k0 = glass_lk[i0][1]; float k1 = glass_lk[i1][1]; return mix(k0, k1, f1); } } return glass_lk[12][1]; } vec2 Glass_nk(float wavelength) { return vec2(Glass_n(wavelength), Glass_k(wavelength)); } Hit Glass(Random PRNG, Surface S, Ray V) { return Transparent(PRNG, S, V, Glass_nk(V.wavelength)); } vec2 Quartz_nk(float wavelength) { const float quartz_min = 390; const float quartz_step = 2; const vec2 quartz_nk[221] = vec2[221] ( vec2(1.490867, 0.000009) , vec2(1.490629, 0.000007) , vec2(1.490396, 0.000005) , vec2(1.490165, 0.000003) , vec2(1.489938, 0.000002) , vec2(1.489714, 0.000001) , vec2(1.489494, 0.000001) , vec2(1.489276, 0.000000) , vec2(1.489062, 0.000000) , vec2(1.488850, 0.000000) , vec2(1.488641, 0.000000) , vec2(1.488435, 0.000000) , vec2(1.488231, 0.000000) , vec2(1.488031, 0.000000) , vec2(1.487833, 0.000000) , vec2(1.487638, 0.000000) , vec2(1.487446, 0.000000) , vec2(1.487256, 0.000000) , vec2(1.487069, 0.000000) , vec2(1.486884, 0.000000) , vec2(1.486702, 0.000000) , vec2(1.486522, 0.000000) , vec2(1.486345, 0.000000) , vec2(1.486170, 0.000000) , vec2(1.485997, 0.000000) , vec2(1.485827, 0.000000) , vec2(1.485659, 0.000000) , vec2(1.485493, 0.000000) , vec2(1.485329, 0.000000) , vec2(1.485167, 0.000000) , vec2(1.485008, 0.000000) , vec2(1.484851, 0.000000) , vec2(1.484695, 0.000000) , vec2(1.484542, 0.000000) , vec2(1.484390, 0.000000) , vec2(1.484241, 0.000000) , vec2(1.484094, 0.000000) , vec2(1.483948, 0.000000) , vec2(1.483804, 0.000000) , vec2(1.483662, 0.000000) , vec2(1.483522, 0.000000) , vec2(1.483383, 0.000000) , vec2(1.483247, 0.000000) , vec2(1.483111, 0.000000) , vec2(1.482978, 0.000000) , vec2(1.482846, 0.000000) , vec2(1.482716, 0.000000) , vec2(1.482588, 0.000000) , vec2(1.482461, 0.000000) , vec2(1.482335, 0.000000) , vec2(1.482211, 0.000000) , vec2(1.482089, 0.000000) , vec2(1.481968, 0.000000) , vec2(1.481848, 0.000000) , vec2(1.481730, 0.000000) , vec2(1.481613, 0.000000) , vec2(1.481498, 0.000000) , vec2(1.481384, 0.000000) , vec2(1.481271, 0.000000) , vec2(1.481160, 0.000000) , vec2(1.481050, 0.000000) , vec2(1.480941, 0.000000) , vec2(1.480834, 0.000000) , vec2(1.480727, 0.000000) , vec2(1.480622, 0.000000) , vec2(1.480518, 0.000000) , vec2(1.480416, 0.000000) , vec2(1.480314, 0.000000) , vec2(1.480214, 0.000000) , vec2(1.480115, 0.000000) , vec2(1.480016, 0.000000) , vec2(1.479919, 0.000000) , vec2(1.479823, 0.000000) , vec2(1.479729, 0.000000) , vec2(1.479635, 0.000000) , vec2(1.479542, 0.000000) , vec2(1.479450, 0.000000) , vec2(1.479359, 0.000000) , vec2(1.479269, 0.000000) , vec2(1.479181, 0.000000) , vec2(1.479093, 0.000000) , vec2(1.479006, 0.000000) , vec2(1.478920, 0.000000) , vec2(1.478835, 0.000000) , vec2(1.478751, 0.000000) , vec2(1.478667, 0.000000) , vec2(1.478585, 0.000000) , vec2(1.478503, 0.000000) , vec2(1.478423, 0.000000) , vec2(1.478343, 0.000000) , vec2(1.478264, 0.000000) , vec2(1.478186, 0.000000) , vec2(1.478108, 0.000000) , vec2(1.478032, 0.000000) , vec2(1.477956, 0.000000) , vec2(1.477881, 0.000000) , vec2(1.477807, 0.000000) , vec2(1.477733, 0.000000) , vec2(1.477660, 0.000000) , vec2(1.477588, 0.000000) , vec2(1.477517, 0.000000) , vec2(1.477447, 0.000000) , vec2(1.477377, 0.000000) , vec2(1.477308, 0.000000) , vec2(1.477239, 0.000000) , vec2(1.477171, 0.000000) , vec2(1.477104, 0.000000) , vec2(1.477038, 0.000000) , vec2(1.476972, 0.000000) , vec2(1.476907, 0.000000) , vec2(1.476842, 0.000000) , vec2(1.476778, 0.000000) , vec2(1.476715, 0.000000) , vec2(1.476652, 0.000000) , vec2(1.476590, 0.000000) , vec2(1.476529, 0.000000) , vec2(1.476468, 0.000000) , vec2(1.476408, 0.000000) , vec2(1.476348, 0.000000) , vec2(1.476289, 0.000000) , vec2(1.476230, 0.000000) , vec2(1.476172, 0.000000) , vec2(1.476115, 0.000000) , vec2(1.476058, 0.000000) , vec2(1.476001, 0.000000) , vec2(1.475946, 0.000000) , vec2(1.475890, 0.000000) , vec2(1.475835, 0.000000) , vec2(1.475781, 0.000000) , vec2(1.475727, 0.000000) , vec2(1.475674, 0.000000) , vec2(1.475621, 0.000000) , vec2(1.475568, 0.000000) , vec2(1.475517, 0.000000) , vec2(1.475465, 0.000000) , vec2(1.475414, 0.000000) , vec2(1.475364, 0.000000) , vec2(1.475314, 0.000000) , vec2(1.475264, 0.000000) , vec2(1.475215, 0.000000) , vec2(1.475166, 0.000000) , vec2(1.475118, 0.000000) , vec2(1.475070, 0.000000) , vec2(1.475022, 0.000000) , vec2(1.474975, 0.000000) , vec2(1.474929, 0.000000) , vec2(1.474883, 0.000000) , vec2(1.474837, 0.000000) , vec2(1.474791, 0.000000) , vec2(1.474746, 0.000000) , vec2(1.474702, 0.000000) , vec2(1.474657, 0.000000) , vec2(1.474614, 0.000000) , vec2(1.474570, 0.000000) , vec2(1.474527, 0.000000) , vec2(1.474484, 0.000000) , vec2(1.474442, 0.000000) , vec2(1.474400, 0.000000) , vec2(1.474358, 0.000000) , vec2(1.474317, 0.000000) , vec2(1.474276, 0.000000) , vec2(1.474235, 0.000000) , vec2(1.474195, 0.000000) , vec2(1.474155, 0.000000) , vec2(1.474115, 0.000000) , vec2(1.474076, 0.000000) , vec2(1.474037, 0.000000) , vec2(1.473998, 0.000000) , vec2(1.473960, 0.000000) , vec2(1.473922, 0.000000) , vec2(1.473884, 0.000000) , vec2(1.473847, 0.000000) , vec2(1.473810, 0.000000) , vec2(1.473773, 0.000000) , vec2(1.473737, 0.000000) , vec2(1.473700, 0.000000) , vec2(1.473665, 0.000000) , vec2(1.473629, 0.000000) , vec2(1.473594, 0.000000) , vec2(1.473559, 0.000000) , vec2(1.473524, 0.000000) , vec2(1.473489, 0.000000) , vec2(1.473455, 0.000000) , vec2(1.473421, 0.000000) , vec2(1.473387, 0.000000) , vec2(1.473354, 0.000000) , vec2(1.473321, 0.000000) , vec2(1.473288, 0.000000) , vec2(1.473255, 0.000000) , vec2(1.473223, 0.000000) , vec2(1.473191, 0.000000) , vec2(1.473159, 0.000000) , vec2(1.473127, 0.000000) , vec2(1.473096, 0.000000) , vec2(1.473065, 0.000000) , vec2(1.473034, 0.000000) , vec2(1.473003, 0.000000) , vec2(1.472973, 0.000000) , vec2(1.472942, 0.000000) , vec2(1.472912, 0.000000) , vec2(1.472883, 0.000000) , vec2(1.472853, 0.000000) , vec2(1.472824, 0.000000) , vec2(1.472795, 0.000000) , vec2(1.472766, 0.000000) , vec2(1.472737, 0.000000) , vec2(1.472709, 0.000000) , vec2(1.472680, 0.000000) , vec2(1.472652, 0.000000) , vec2(1.472625, 0.000000) , vec2(1.472597, 0.000000) , vec2(1.472570, 0.000000) , vec2(1.472542, 0.000000) , vec2(1.472515, 0.000000) , vec2(1.472489, 0.000000) , vec2(1.472462, 0.000000) , vec2(1.472436, 0.000000) , vec2(1.472409, 0.000000) , vec2(1.472383, 0.000000) , vec2(1.472357, 0.000000) , vec2(1.472332, 0.000000) ); float x = (wavelength - quartz_min) / quartz_step; int i0 = int(floor(x)); int i1 = i0 + 1; float f1 = x - float(i0); if (i0 < 0) return quartz_nk[0]; if (i1 > 221 - 1) return quartz_nk[221 - 1]; vec2 y0 = quartz_nk[i0]; vec2 y1 = quartz_nk[i1]; return mix(y0, y1, f1); } Hit Quartz(Random PRNG, Surface S, Ray V) { return Transparent(PRNG, S, V, Quartz_nk(V.wavelength)); } vec2 Water_nk(float wavelength) { const float water_min = 375; const float water_step = 25; const vec2 water_nk[20] = vec2[20] ( vec2(1.341, 3.50E-9) , vec2(1.339, 1.86E-9) , vec2(1.338, 1.30E-9) , vec2(1.337, 1.02E-9) , vec2(1.336, 9.35E-10) , vec2(1.335, 1.00E-9) , vec2(1.334, 1.32E-9) , vec2(1.333, 1.96E-9) , vec2(1.333, 3.60E-9) , vec2(1.332, 1.09E-8) , vec2(1.332, 1.39E-8) , vec2(1.331, 1.64E-8) , vec2(1.331, 2.23E-8) , vec2(1.331, 3.35E-8) , vec2(1.330, 9.15E-8) , vec2(1.330, 1.56E-7) , vec2(1.330, 1.48E-7) , vec2(1.329, 1.25E-7) , vec2(1.329, 1.82E-7) , vec2(1.329, 2.93E-7) ); float x = (wavelength - water_min) / water_step; int i0 = int(floor(x)); int i1 = i0 + 1; float f1 = x - float(i0); if (i0 < 0) return water_nk[0]; if (i1 > 20 - 1) return water_nk[20 - 1]; vec2 y0 = water_nk[i0]; vec2 y1 = water_nk[i1]; return mix(y0, y1, f1); } Hit Water(Random PRNG, Surface S, Ray V) { return Transparent(PRNG, S, V, Water_nk(V.wavelength)); } vec3 xyz2rgb(in vec3 l) { const vec3 whitePoint = vec3(0.9505, 1.0000, 1.0890); const mat3 matrix = mat3 ( 3.2406, -1.5372, -0.4986 , -0.9689, 1.8758, 0.0415 , 0.0557, -0.2040, 1.0570 ); return (whitePoint * l) * matrix; } vec3 observer(in float wavelength) { const int wavelength_min = 390; const int wavelength_max = 830; const vec3 tristimulus_curve[441] = vec3[441] ( vec3(3.769647e-3, 4.146161e-4, 1.847260e-2) , vec3(4.532416e-3, 5.028333e-4, 2.221101e-2) , vec3(5.446553e-3, 6.084991e-4, 2.669819e-2) , vec3(6.538868e-3, 7.344436e-4, 3.206937e-2) , vec3(7.839699e-3, 8.837389e-4, 3.847832e-2) , vec3(9.382967e-3, 1.059646e-3, 4.609784e-2) , vec3(1.120608e-2, 1.265532e-3, 5.511953e-2) , vec3(1.334965e-2, 1.504753e-3, 6.575257e-2) , vec3(1.585690e-2, 1.780493e-3, 7.822113e-2) , vec3(1.877286e-2, 2.095572e-3, 9.276013e-2) , vec3(2.214302e-2, 2.452194e-3, 1.096090e-1) , vec3(2.601285e-2, 2.852216e-3, 1.290077e-1) , vec3(3.043036e-2, 3.299115e-3, 1.512047e-1) , vec3(3.544325e-2, 3.797466e-3, 1.764441e-1) , vec3(4.109640e-2, 4.352768e-3, 2.049517e-1) , vec3(4.742986e-2, 4.971717e-3, 2.369246e-1) , vec3(5.447394e-2, 5.661014e-3, 2.725123e-1) , vec3(6.223612e-2, 6.421615e-3, 3.117820e-1) , vec3(7.070048e-2, 7.250312e-3, 3.547064e-1) , vec3(7.982513e-2, 8.140173e-3, 4.011473e-1) , vec3(8.953803e-2, 9.079860e-3, 4.508369e-1) , vec3(9.974848e-2, 1.005608e-2, 5.034164e-1) , vec3(1.104019e-1, 1.106456e-2, 5.586361e-1) , vec3(1.214566e-1, 1.210522e-2, 6.162734e-1) , vec3(1.328741e-1, 1.318014e-2, 6.760982e-1) , vec3(1.446214e-1, 1.429377e-2, 7.378822e-1) , vec3(1.566468e-1, 1.545004e-2, 8.013019e-1) , vec3(1.687901e-1, 1.664093e-2, 8.655573e-1) , vec3(1.808328e-1, 1.785302e-2, 9.295791e-1) , vec3(1.925216e-1, 1.907018e-2, 9.921293e-1) , vec3(2.035729e-1, 2.027369e-2, 1.051821) , vec3(2.137531e-1, 2.144805e-2, 1.107509) , vec3(2.231348e-1, 2.260041e-2, 1.159527) , vec3(2.319245e-1, 2.374789e-2, 1.208869) , vec3(2.403892e-1, 2.491247e-2, 1.256834) , vec3(2.488523e-1, 2.612106e-2, 1.305008) , vec3(2.575896e-1, 2.739923e-2, 1.354758) , vec3(2.664991e-1, 2.874993e-2, 1.405594) , vec3(2.753532e-1, 3.016909e-2, 1.456414) , vec3(2.838921e-1, 3.165145e-2, 1.505960) , vec3(2.918246e-1, 3.319038e-2, 1.552826) , vec3(2.989200e-1, 3.477912e-2, 1.595902) , vec3(3.052993e-1, 3.641495e-2, 1.635768) , vec3(3.112031e-1, 3.809569e-2, 1.673573) , vec3(3.169047e-1, 3.981843e-2, 1.710604) , vec3(3.227087e-1, 4.157940e-2, 1.748280) , vec3(3.288194e-1, 4.337098e-2, 1.787504) , vec3(3.349242e-1, 4.517180e-2, 1.826609) , vec3(3.405452e-1, 4.695420e-2, 1.863108) , vec3(3.451688e-1, 4.868718e-2, 1.894332) , vec3(3.482554e-1, 5.033657e-2, 1.917479) , vec3(3.494153e-1, 5.187611e-2, 1.930529) , vec3(3.489075e-1, 5.332218e-2, 1.934819) , vec3(3.471746e-1, 5.470603e-2, 1.932650) , vec3(3.446705e-1, 5.606335e-2, 1.926395) , vec3(3.418483e-1, 5.743393e-2, 1.918437) , vec3(3.390240e-1, 5.885107e-2, 1.910430) , vec3(3.359926e-1, 6.030809e-2, 1.901224) , vec3(3.324276e-1, 6.178644e-2, 1.889000) , vec3(3.280157e-1, 6.326570e-2, 1.871996) , vec3(3.224637e-1, 6.472352e-2, 1.848545) , vec3(3.156225e-1, 6.614749e-2, 1.817792) , vec3(3.078201e-1, 6.757256e-2, 1.781627) , vec3(2.994771e-1, 6.904928e-2, 1.742514) , vec3(2.909776e-1, 7.063280e-2, 1.702749) , vec3(2.826646e-1, 7.238339e-2, 1.664439) , vec3(2.747962e-1, 7.435960e-2, 1.629207) , vec3(2.674312e-1, 7.659383e-2, 1.597360) , vec3(2.605847e-1, 7.911436e-2, 1.568896) , vec3(2.542749e-1, 8.195345e-2, 1.543823) , vec3(2.485254e-1, 8.514816e-2, 1.522157) , vec3(2.433039e-1, 8.872657e-2, 1.503611) , vec3(2.383414e-1, 9.266008e-2, 1.486673) , vec3(2.333253e-1, 9.689723e-2, 1.469595) , vec3(2.279619e-1, 1.013746e-1, 1.450709) , vec3(2.219781e-1, 1.060145e-1, 1.428440) , vec3(2.151735e-1, 1.107377e-1, 1.401587) , vec3(2.075619e-1, 1.155111e-1, 1.370094) , vec3(1.992183e-1, 1.203122e-1, 1.334220) , vec3(1.902290e-1, 1.251161e-1, 1.294275) , vec3(1.806905e-1, 1.298957e-1, 1.250610) , vec3(1.707154e-1, 1.346299e-1, 1.203696) , vec3(1.604471e-1, 1.393309e-1, 1.154316) , vec3(1.500244e-1, 1.440235e-1, 1.103284) , vec3(1.395705e-1, 1.487372e-1, 1.051347) , vec3(1.291920e-1, 1.535066e-1, 9.991789e-1) , vec3(1.189859e-1, 1.583644e-1, 9.473958e-1) , vec3(1.090615e-1, 1.633199e-1, 8.966222e-1) , vec3(9.951424e-2, 1.683761e-1, 8.473981e-1) , vec3(9.041850e-2, 1.735365e-1, 8.001576e-1) , vec3(8.182895e-2, 1.788048e-1, 7.552379e-1) , vec3(7.376817e-2, 1.841819e-1, 7.127879e-1) , vec3(6.619477e-2, 1.896559e-1, 6.725198e-1) , vec3(5.906380e-2, 1.952101e-1, 6.340976e-1) , vec3(5.234242e-2, 2.008259e-1, 5.972433e-1) , vec3(4.600865e-2, 2.064828e-1, 5.617313e-1) , vec3(4.006154e-2, 2.121826e-1, 5.274921e-1) , vec3(3.454373e-2, 2.180279e-1, 4.948809e-1) , vec3(2.949091e-2, 2.241586e-1, 4.642586e-1) , vec3(2.492140e-2, 2.307302e-1, 4.358841e-1) , vec3(2.083981e-2, 2.379160e-1, 4.099313e-1) , vec3(1.723591e-2, 2.458706e-1, 3.864261e-1) , vec3(1.407924e-2, 2.546023e-1, 3.650566e-1) , vec3(1.134516e-2, 2.640760e-1, 3.454812e-1) , vec3(9.019658e-3, 2.742490e-1, 3.274095e-1) , vec3(7.097731e-3, 2.850680e-1, 3.105939e-1) , vec3(5.571145e-3, 2.964837e-1, 2.948102e-1) , vec3(4.394566e-3, 3.085010e-1, 2.798194e-1) , vec3(3.516303e-3, 3.211393e-1, 2.654100e-1) , vec3(2.887638e-3, 3.344175e-1, 2.514084e-1) , vec3(2.461588e-3, 3.483536e-1, 2.376753e-1) , vec3(2.206348e-3, 3.629601e-1, 2.241211e-1) , vec3(2.149559e-3, 3.782275e-1, 2.107484e-1) , vec3(2.337091e-3, 3.941359e-1, 1.975839e-1) , vec3(2.818931e-3, 4.106582e-1, 1.846574e-1) , vec3(3.649178e-3, 4.277595e-1, 1.720018e-1) , vec3(4.891359e-3, 4.453993e-1, 1.596918e-1) , vec3(6.629364e-3, 4.635396e-1, 1.479415e-1) , vec3(8.942902e-3, 4.821376e-1, 1.369428e-1) , vec3(1.190224e-2, 5.011430e-1, 1.268279e-1) , vec3(1.556989e-2, 5.204972e-1, 1.176796e-1) , vec3(1.997668e-2, 5.401387e-1, 1.094970e-1) , vec3(2.504698e-2, 5.600208e-1, 1.020943e-1) , vec3(3.067530e-2, 5.800972e-1, 9.527993e-2) , vec3(3.674999e-2, 6.003172e-1, 8.890075e-2) , vec3(4.315171e-2, 6.206256e-1, 8.283548e-2) , vec3(4.978584e-2, 6.409398e-1, 7.700982e-2) , vec3(5.668554e-2, 6.610772e-1, 7.144001e-2) , vec3(6.391651e-2, 6.808134e-1, 6.615436e-2) , vec3(7.154352e-2, 6.999044e-1, 6.117199e-2) , vec3(7.962917e-2, 7.180890e-1, 5.650407e-2) , vec3(8.821473e-2, 7.351593e-1, 5.215121e-2) , vec3(9.726978e-2, 7.511821e-1, 4.809566e-2) , vec3(1.067504e-1, 7.663143e-1, 4.431720e-2) , vec3(1.166192e-1, 7.807352e-1, 4.079734e-2) , vec3(1.268468e-1, 7.946448e-1, 3.751912e-2) , vec3(1.374060e-1, 8.082074e-1, 3.446846e-2) , vec3(1.482471e-1, 8.213817e-1, 3.163764e-2) , vec3(1.593076e-1, 8.340701e-1, 2.901901e-2) , vec3(1.705181e-1, 8.461711e-1, 2.660364e-2) , vec3(1.818026e-1, 8.575799e-1, 2.438164e-2) , vec3(1.931090e-1, 8.682408e-1, 2.234097e-2) , vec3(2.045085e-1, 8.783061e-1, 2.046415e-2) , vec3(2.161166e-1, 8.879907e-1, 1.873456e-2) , vec3(2.280650e-1, 8.975211e-1, 1.713788e-2) , vec3(2.405015e-1, 9.071347e-1, 1.566174e-2) , vec3(2.535441e-1, 9.169947e-1, 1.429644e-2) , vec3(2.671300e-1, 9.269295e-1, 1.303702e-2) , vec3(2.811351e-1, 9.366731e-1, 1.187897e-2) , vec3(2.954164e-1, 9.459482e-1, 1.081725e-2) , vec3(3.098117e-1, 9.544675e-1, 9.846470e-3) , vec3(3.241678e-1, 9.619834e-1, 8.960687e-3) , vec3(3.384319e-1, 9.684390e-1, 8.152811e-3) , vec3(3.525786e-1, 9.738289e-1, 7.416025e-3) , vec3(3.665839e-1, 9.781519e-1, 6.744115e-3) , vec3(3.804244e-1, 9.814106e-1, 6.131421e-3) , vec3(3.940988e-1, 9.836669e-1, 5.572778e-3) , vec3(4.076972e-1, 9.852081e-1, 5.063463e-3) , vec3(4.213484e-1, 9.863813e-1, 4.599169e-3) , vec3(4.352003e-1, 9.875357e-1, 4.175971e-3) , vec3(4.494206e-1, 9.890228e-1, 3.790291e-3) , vec3(4.641616e-1, 9.910811e-1, 3.438952e-3) , vec3(4.794395e-1, 9.934913e-1, 3.119341e-3) , vec3(4.952180e-1, 9.959172e-1, 2.829038e-3) , vec3(5.114395e-1, 9.980205e-1, 2.565722e-3) , vec3(5.280233e-1, 9.994608e-1, 2.327186e-3) , vec3(5.448696e-1, 9.999930e-1, 2.111280e-3) , vec3(5.618898e-1, 9.997557e-1, 1.915766e-3) , vec3(5.790137e-1, 9.989839e-1, 1.738589e-3) , vec3(5.961882e-1, 9.979123e-1, 1.577920e-3) , vec3(6.133784e-1, 9.967737e-1, 1.432128e-3) , vec3(6.305897e-1, 9.957356e-1, 1.299781e-3) , vec3(6.479223e-1, 9.947115e-1, 1.179667e-3) , vec3(6.654866e-1, 9.935534e-1, 1.070694e-3) , vec3(6.833782e-1, 9.921156e-1, 9.718623e-4) , vec3(7.016774e-1, 9.902549e-1, 8.822531e-4) , vec3(7.204110e-1, 9.878596e-1, 8.010231e-4) , vec3(7.394495e-1, 9.849324e-1, 7.273884e-4) , vec3(7.586285e-1, 9.815036e-1, 6.606347e-4) , vec3(7.777885e-1, 9.776035e-1, 6.001146e-4) , vec3(7.967750e-1, 9.732611e-1, 5.452416e-4) , vec3(8.154530e-1, 9.684764e-1, 4.954847e-4) , vec3(8.337389e-1, 9.631369e-1, 4.503642e-4) , vec3(8.515493e-1, 9.571062e-1, 4.094455e-4) , vec3(8.687862e-1, 9.502540e-1, 3.723345e-4) , vec3(8.853376e-1, 9.424569e-1, 3.386739e-4) , vec3(9.011588e-1, 9.336897e-1, 3.081396e-4) , vec3(9.165278e-1, 9.242893e-1, 2.804370e-4) , vec3(9.318245e-1, 9.146707e-1, 2.552996e-4) , vec3(9.474524e-1, 9.052333e-1, 2.324859e-4) , vec3(9.638388e-1, 8.963613e-1, 2.117772e-4) , vec3(9.812596e-1, 8.883069e-1, 1.929758e-4) , vec3(9.992953e-1, 8.808462e-1, 1.759024e-4) , vec3(1.017343, 8.736445e-1, 1.603947e-4) , vec3(1.034790, 8.663755e-1, 1.463059e-4) , vec3(1.051011, 8.587203e-1, 1.335031e-4) , vec3(1.065522, 8.504295e-1, 1.218660e-4) , vec3(1.078421, 8.415047e-1, 1.112857e-4) , vec3(1.089944, 8.320109e-1, 1.016634e-4) , vec3(1.100320, 8.220154e-1, 9.291003e-5) , vec3(1.109767, 8.115868e-1, 8.494468e-5) , vec3(1.118438, 8.007874e-1, 7.769425e-5) , vec3(1.126266, 7.896515e-1, 7.109247e-5) , vec3(1.133138, 7.782053e-1, 6.507936e-5) , vec3(1.138952, 7.664733e-1, 5.960061e-5) , vec3(1.143620, 7.544785e-1, 5.460706e-5) , vec3(1.147095, 7.422473e-1, 5.005417e-5) , vec3(1.149464, 7.298229e-1, 4.590157e-5) , vec3(1.150838, 7.172525e-1, 4.211268e-5) , vec3(1.151326, 7.045818e-1, 3.865437e-5) , vec3(1.151033, 6.918553e-1, 3.549661e-5) , vec3(1.150002, 6.791009e-1, 3.261220e-5) , vec3(1.148061, 6.662846e-1, 2.997643e-5) , vec3(1.144998, 6.533595e-1, 2.756693e-5) , vec3(1.140622, 6.402807e-1, 2.536339e-5) , vec3(1.134757, 6.270066e-1, 2.334738e-5) , vec3(1.127298, 6.135148e-1, 2.150221e-5) , vec3(1.118342, 5.998494e-1, 1.981268e-5) , vec3(1.108033, 5.860682e-1, 1.826500e-5) , vec3(1.096515, 5.722261e-1, 1.684667e-5) , vec3(1.083928, 5.583746e-1, 1.554631e-5) , vec3(1.070387, 5.445535e-1, 1.435360e-5) , vec3(1.055934, 5.307673e-1, 1.325915e-5) , vec3(1.040592, 5.170130e-1, 1.225443e-5) , vec3(1.024385, 5.032889e-1, 1.133169e-5) , vec3(1.007344, 4.895950e-1, 1.048387e-5) , vec3(9.895268e-1, 4.759442e-1, 0.000000) , vec3(9.711213e-1, 4.623958e-1, 0.000000) , vec3(9.523257e-1, 4.490154e-1, 0.000000) , vec3(9.333248e-1, 4.358622e-1, 0.000000) , vec3(9.142877e-1, 4.229897e-1, 0.000000) , vec3(8.952798e-1, 4.104152e-1, 0.000000) , vec3(8.760157e-1, 3.980356e-1, 0.000000) , vec3(8.561607e-1, 3.857300e-1, 0.000000) , vec3(8.354235e-1, 3.733907e-1, 0.000000) , vec3(8.135565e-1, 3.609245e-1, 0.000000) , vec3(7.904565e-1, 3.482860e-1, 0.000000) , vec3(7.664364e-1, 3.355702e-1, 0.000000) , vec3(7.418777e-1, 3.228963e-1, 0.000000) , vec3(7.171219e-1, 3.103704e-1, 0.000000) , vec3(6.924717e-1, 2.980865e-1, 0.000000) , vec3(6.681600e-1, 2.861160e-1, 0.000000) , vec3(6.442697e-1, 2.744822e-1, 0.000000) , vec3(6.208450e-1, 2.631953e-1, 0.000000) , vec3(5.979243e-1, 2.522628e-1, 0.000000) , vec3(5.755410e-1, 2.416902e-1, 0.000000) , vec3(5.537296e-1, 2.314809e-1, 0.000000) , vec3(5.325412e-1, 2.216378e-1, 0.000000) , vec3(5.120218e-1, 2.121622e-1, 0.000000) , vec3(4.922070e-1, 2.030542e-1, 0.000000) , vec3(4.731224e-1, 1.943124e-1, 0.000000) , vec3(4.547417e-1, 1.859227e-1, 0.000000) , vec3(4.368719e-1, 1.778274e-1, 0.000000) , vec3(4.193121e-1, 1.699654e-1, 0.000000) , vec3(4.018980e-1, 1.622841e-1, 0.000000) , vec3(3.844986e-1, 1.547397e-1, 0.000000) , vec3(3.670592e-1, 1.473081e-1, 0.000000) , vec3(3.497167e-1, 1.400169e-1, 0.000000) , vec3(3.326305e-1, 1.329013e-1, 0.000000) , vec3(3.159341e-1, 1.259913e-1, 0.000000) , vec3(2.997374e-1, 1.193120e-1, 0.000000) , vec3(2.841189e-1, 1.128820e-1, 0.000000) , vec3(2.691053e-1, 1.067113e-1, 0.000000) , vec3(2.547077e-1, 1.008052e-1, 0.000000) , vec3(2.409319e-1, 9.516653e-2, 0.000000) , vec3(2.277792e-1, 8.979594e-2, 0.000000) , vec3(2.152431e-1, 8.469044e-2, 0.000000) , vec3(2.033010e-1, 7.984009e-2, 0.000000) , vec3(1.919276e-1, 7.523372e-2, 0.000000) , vec3(1.810987e-1, 7.086061e-2, 0.000000) , vec3(1.707914e-1, 6.671045e-2, 0.000000) , vec3(1.609842e-1, 6.277360e-2, 0.000000) , vec3(1.516577e-1, 5.904179e-2, 0.000000) , vec3(1.427936e-1, 5.550703e-2, 0.000000) , vec3(1.343737e-1, 5.216139e-2, 0.000000) , vec3(1.263808e-1, 4.899699e-2, 0.000000) , vec3(1.187979e-1, 4.600578e-2, 0.000000) , vec3(1.116088e-1, 4.317885e-2, 0.000000) , vec3(1.047975e-1, 4.050755e-2, 0.000000) , vec3(9.834835e-2, 3.798376e-2, 0.000000) , vec3(9.224597e-2, 3.559982e-2, 0.000000) , vec3(8.647506e-2, 3.334856e-2, 0.000000) , vec3(8.101986e-2, 3.122332e-2, 0.000000) , vec3(7.586514e-2, 2.921780e-2, 0.000000) , vec3(7.099633e-2, 2.732601e-2, 0.000000) , vec3(6.639960e-2, 2.554223e-2, 0.000000) , vec3(6.206225e-2, 2.386121e-2, 0.000000) , vec3(5.797409e-2, 2.227859e-2, 0.000000) , vec3(5.412533e-2, 2.079020e-2, 0.000000) , vec3(5.050600e-2, 1.939185e-2, 0.000000) , vec3(4.710606e-2, 1.807939e-2, 0.000000) , vec3(4.391411e-2, 1.684817e-2, 0.000000) , vec3(4.091411e-2, 1.569188e-2, 0.000000) , vec3(3.809067e-2, 1.460446e-2, 0.000000) , vec3(3.543034e-2, 1.358062e-2, 0.000000) , vec3(3.292138e-2, 1.261573e-2, 0.000000) , vec3(3.055672e-2, 1.170696e-2, 0.000000) , vec3(2.834146e-2, 1.085608e-2, 0.000000) , vec3(2.628033e-2, 1.006476e-2, 0.000000) , vec3(2.437465e-2, 9.333376e-3, 0.000000) , vec3(2.262306e-2, 8.661284e-3, 0.000000) , vec3(2.101935e-2, 8.046048e-3, 0.000000) , vec3(1.954647e-2, 7.481130e-3, 0.000000) , vec3(1.818727e-2, 6.959987e-3, 0.000000) , vec3(1.692727e-2, 6.477070e-3, 0.000000) , vec3(1.575417e-2, 6.027677e-3, 0.000000) , vec3(1.465854e-2, 5.608169e-3, 0.000000) , vec3(1.363571e-2, 5.216691e-3, 0.000000) , vec3(1.268205e-2, 4.851785e-3, 0.000000) , vec3(1.179394e-2, 4.512008e-3, 0.000000) , vec3(1.096778e-2, 4.195941e-3, 0.000000) , vec3(1.019964e-2, 3.902057e-3, 0.000000) , vec3(9.484317e-3, 3.628371e-3, 0.000000) , vec3(8.816851e-3, 3.373005e-3, 0.000000) , vec3(8.192921e-3, 3.134315e-3, 0.000000) , vec3(7.608750e-3, 2.910864e-3, 0.000000) , vec3(7.061391e-3, 2.701528e-3, 0.000000) , vec3(6.549509e-3, 2.505796e-3, 0.000000) , vec3(6.071970e-3, 2.323231e-3, 0.000000) , vec3(5.627476e-3, 2.153333e-3, 0.000000) , vec3(5.214608e-3, 1.995557e-3, 0.000000) , vec3(4.831848e-3, 1.849316e-3, 0.000000) , vec3(4.477579e-3, 1.713976e-3, 0.000000) , vec3(4.150166e-3, 1.588899e-3, 0.000000) , vec3(3.847988e-3, 1.473453e-3, 0.000000) , vec3(3.569452e-3, 1.367022e-3, 0.000000) , vec3(3.312857e-3, 1.268954e-3, 0.000000) , vec3(3.076022e-3, 1.178421e-3, 0.000000) , vec3(2.856894e-3, 1.094644e-3, 0.000000) , vec3(2.653681e-3, 1.016943e-3, 0.000000) , vec3(2.464821e-3, 9.447269e-4, 0.000000) , vec3(2.289060e-3, 8.775171e-4, 0.000000) , vec3(2.125694e-3, 8.150438e-4, 0.000000) , vec3(1.974121e-3, 7.570755e-4, 0.000000) , vec3(1.833723e-3, 7.033755e-4, 0.000000) , vec3(1.703876e-3, 6.537050e-4, 0.000000) , vec3(1.583904e-3, 6.078048e-4, 0.000000) , vec3(1.472939e-3, 5.653435e-4, 0.000000) , vec3(1.370151e-3, 5.260046e-4, 0.000000) , vec3(1.274803e-3, 4.895061e-4, 0.000000) , vec3(1.186238e-3, 4.555970e-4, 0.000000) , vec3(1.103871e-3, 4.240548e-4, 0.000000) , vec3(1.027194e-3, 3.946860e-4, 0.000000) , vec3(9.557493e-4, 3.673178e-4, 0.000000) , vec3(8.891262e-4, 3.417941e-4, 0.000000) , vec3(8.269535e-4, 3.179738e-4, 0.000000) , vec3(7.689351e-4, 2.957441e-4, 0.000000) , vec3(7.149425e-4, 2.750558e-4, 0.000000) , vec3(6.648590e-4, 2.558640e-4, 0.000000) , vec3(6.185421e-4, 2.381142e-4, 0.000000) , vec3(5.758303e-4, 2.217445e-4, 0.000000) , vec3(5.365046e-4, 2.066711e-4, 0.000000) , vec3(5.001842e-4, 1.927474e-4, 0.000000) , vec3(4.665005e-4, 1.798315e-4, 0.000000) , vec3(4.351386e-4, 1.678023e-4, 0.000000) , vec3(4.058303e-4, 1.565566e-4, 0.000000) , vec3(3.783733e-4, 1.460168e-4, 0.000000) , vec3(3.526892e-4, 1.361535e-4, 0.000000) , vec3(3.287199e-4, 1.269451e-4, 0.000000) , vec3(3.063998e-4, 1.183671e-4, 0.000000) , vec3(2.856577e-4, 1.103928e-4, 0.000000) , vec3(2.664108e-4, 1.029908e-4, 0.000000) , vec3(2.485462e-4, 9.611836e-5, 0.000000) , vec3(2.319529e-4, 8.973323e-5, 0.000000) , vec3(2.165300e-4, 8.379694e-5, 0.000000) , vec3(2.021853e-4, 7.827442e-5, 0.000000) , vec3(1.888338e-4, 7.313312e-5, 0.000000) , vec3(1.763935e-4, 6.834142e-5, 0.000000) , vec3(1.647895e-4, 6.387035e-5, 0.000000) , vec3(1.539542e-4, 5.969389e-5, 0.000000) , vec3(1.438270e-4, 5.578862e-5, 0.000000) , vec3(1.343572e-4, 5.213509e-5, 0.000000) , vec3(1.255141e-4, 4.872179e-5, 0.000000) , vec3(1.172706e-4, 4.553845e-5, 0.000000) , vec3(1.095983e-4, 4.257443e-5, 0.000000) , vec3(1.024685e-4, 3.981884e-5, 0.000000) , vec3(9.584715e-5, 3.725877e-5, 0.000000) , vec3(8.968316e-5, 3.487467e-5, 0.000000) , vec3(8.392734e-5, 3.264765e-5, 0.000000) , vec3(7.853708e-5, 3.056140e-5, 0.000000) , vec3(7.347551e-5, 2.860175e-5, 0.000000) , vec3(6.871576e-5, 2.675841e-5, 0.000000) , vec3(6.425257e-5, 2.502943e-5, 0.000000) , vec3(6.008292e-5, 2.341373e-5, 0.000000) , vec3(5.620098e-5, 2.190914e-5, 0.000000) , vec3(5.259870e-5, 2.051259e-5, 0.000000) , vec3(4.926279e-5, 1.921902e-5, 0.000000) , vec3(4.616623e-5, 1.801796e-5, 0.000000) , vec3(4.328212e-5, 1.689899e-5, 0.000000) , vec3(4.058715e-5, 1.585309e-5, 0.000000) , vec3(3.806114e-5, 1.487243e-5, 0.000000) , vec3(3.568818e-5, 1.395085e-5, 0.000000) , vec3(3.346023e-5, 1.308528e-5, 0.000000) , vec3(3.137090e-5, 1.227327e-5, 0.000000) , vec3(2.941371e-5, 1.151233e-5, 0.000000) , vec3(2.758222e-5, 1.080001e-5, 0.000000) , vec3(2.586951e-5, 1.013364e-5, 0.000000) , vec3(2.426701e-5, 9.509919e-6, 0.000000) , vec3(2.276639e-5, 8.925630e-6, 0.000000) , vec3(2.136009e-5, 8.377852e-6, 0.000000) , vec3(2.004122e-5, 7.863920e-6, 0.000000) , vec3(1.880380e-5, 7.381539e-6, 0.000000) , vec3(1.764358e-5, 6.929096e-6, 0.000000) , vec3(1.655671e-5, 6.505136e-6, 0.000000) , vec3(1.553939e-5, 6.108221e-6, 0.000000) , vec3(1.458792e-5, 5.736935e-6, 0.000000) , vec3(1.369853e-5, 5.389831e-6, 0.000000) , vec3(1.286705e-5, 5.065269e-6, 0.000000) , vec3(1.208947e-5, 4.761667e-6, 0.000000) , vec3(1.136207e-5, 4.477561e-6, 0.000000) , vec3(1.068141e-5, 4.211597e-6, 0.000000) , vec3(1.004411e-5, 3.962457e-6, 0.000000) , vec3(9.446399e-6, 3.728674e-6, 0.000000) , vec3(8.884754e-6, 3.508881e-6, 0.000000) , vec3(8.356050e-6, 3.301868e-6, 0.000000) , vec3(7.857521e-6, 3.106561e-6, 0.000000) , vec3(7.386996e-6, 2.922119e-6, 0.000000) , vec3(6.943576e-6, 2.748208e-6, 0.000000) , vec3(6.526548e-6, 2.584560e-6, 0.000000) , vec3(6.135087e-6, 2.430867e-6, 0.000000) , vec3(5.768284e-6, 2.286786e-6, 0.000000) , vec3(5.425069e-6, 2.151905e-6, 0.000000) , vec3(5.103974e-6, 2.025656e-6, 0.000000) , vec3(4.803525e-6, 1.907464e-6, 0.000000) , vec3(4.522350e-6, 1.796794e-6, 0.000000) , vec3(4.259166e-6, 1.693147e-6, 0.000000) , vec3(4.012715e-6, 1.596032e-6, 0.000000) , vec3(3.781597e-6, 1.504903e-6, 0.000000) , vec3(3.564496e-6, 1.419245e-6, 0.000000) , vec3(3.360236e-6, 1.338600e-6, 0.000000) , vec3(3.167765e-6, 1.262556e-6, 0.000000) , vec3(2.986206e-6, 1.190771e-6, 0.000000) , vec3(2.814999e-6, 1.123031e-6, 0.000000) , vec3(2.653663e-6, 1.059151e-6, 0.000000) , vec3(2.501725e-6, 9.989507e-7, 0.000000) , vec3(2.358723e-6, 9.422514e-7, 0.000000) , vec3(2.224206e-6, 8.888804e-7, 0.000000) , vec3(2.097737e-6, 8.386690e-7, 0.000000) , vec3(1.978894e-6, 7.914539e-7, 0.000000) , vec3(1.867268e-6, 7.470770e-7, 0.000000) , vec3(1.762465e-6, 7.053860e-7, 0.000000) ); float l = wavelength - wavelength_min; int i0 = int(floor(l)); int i1 = i0 + 1; float f1 = l - float(i0); if (i0 < 0) return vec3(0.0); if (i1 > 441 - 1) return vec3(0.0); return mix(tristimulus_curve[i0], tristimulus_curve[i1], f1); } float fp4plus(float wavelength) { const int fp4plus_u[350] = int[350] ( 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 , 0x00, 0x00, 0x00, 0x00, 0x0d, 0x22, 0x35, 0x42, 0x4f, 0x5a , 0x62, 0x68, 0x6d, 0x71, 0x75, 0x78, 0x7c, 0x7f, 0x81, 0x83 , 0x86, 0x87, 0x89, 0x8b, 0x8d, 0x8f, 0x91, 0x94, 0x95, 0x98 , 0x9b, 0x9c, 0x9f, 0xa1, 0xa3, 0xa5, 0xa7, 0xa9, 0xab, 0xac , 0xad, 0xaf, 0xb0, 0xb1, 0xb2, 0xb3, 0xb4, 0xb4, 0xb5, 0xb5 , 0xb6, 0xb6, 0xb6, 0xb7, 0xb7, 0xb7, 0xb8, 0xb8, 0xb9, 0xb9 , 0xba, 0xbb, 0xbb, 0xbc, 0xbd, 0xbd, 0xbe, 0xbe, 0xc0, 0xc0 , 0xc2, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7, 0xc8, 0xca, 0xcb , 0xcc, 0xcd, 0xce, 0xcf, 0xd0, 0xd1, 0xd2, 0xd2, 0xd3, 0xd4 , 0xd4, 0xd5, 0xd5, 0xd6, 0xd6, 0xd7, 0xd7, 0xd7, 0xd8, 0xd8 , 0xd8, 0xd8, 0xd9, 0xd9, 0xda, 0xda, 0xda, 0xda, 0xda, 0xda , 0xda, 0xda, 0xda, 0xda, 0xda, 0xda, 0xda, 0xda, 0xda, 0xda , 0xda, 0xda, 0xda, 0xda, 0xda, 0xda, 0xda, 0xd9, 0xd9, 0xd9 , 0xd9, 0xd8, 0xd8, 0xd8, 0xd8, 0xd7, 0xd7, 0xd7, 0xd7, 0xd6 , 0xd6, 0xd6, 0xd6, 0xd5, 0xd5, 0xd5, 0xd5, 0xd5, 0xd5, 0xd5 , 0xd6, 0xd6, 0xd6, 0xd7, 0xd7, 0xd8, 0xd8, 0xda, 0xda, 0xdb , 0xdc, 0xdd, 0xde, 0xde, 0xdf, 0xe0, 0xe0, 0xe0, 0xe1, 0xe2 , 0xe2, 0xe2, 0xe3, 0xe3, 0xe3, 0xe3, 0xe3, 0xe3, 0xe3, 0xe3 , 0xe3, 0xe3, 0xe3, 0xe3, 0xe2, 0xe2, 0xe3, 0xe3, 0xe3, 0xe3 , 0xe3, 0xe4, 0xe4, 0xe5, 0xe6, 0xe6, 0xe7, 0xe7, 0xe8, 0xe9 , 0xe9, 0xea, 0xea, 0xeb, 0xec, 0xec, 0xed, 0xee, 0xee, 0xef , 0xef, 0xf0, 0xf1, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf5, 0xf6 , 0xf6, 0xf7, 0xf8, 0xf8, 0xf9, 0xf9, 0xfa, 0xfa, 0xfb, 0xfb , 0xfb, 0xfc, 0xfc, 0xfc, 0xfd, 0xfd, 0xfd, 0xfe, 0xfe, 0xfe , 0xfe, 0xfe, 0xfe, 0xfe, 0xfe, 0xfe, 0xfe, 0xfe, 0xfe, 0xfe , 0xfd, 0xfd, 0xfd, 0xfc, 0xfc, 0xfb, 0xfb, 0xfb, 0xfa, 0xfa , 0xfa, 0xfa, 0xfa, 0xfa, 0xfa, 0xfa, 0xfa, 0xfa, 0xfa, 0xfa , 0xfa, 0xf9, 0xf8, 0xf6, 0xf4, 0xf1, 0xee, 0xeb, 0xe8, 0xe5 , 0xe2, 0xde, 0xdb, 0xd7, 0xd3, 0xcf, 0xcb, 0xc7, 0xc2, 0xbd , 0xb8, 0xb2, 0xad, 0xa7, 0xa1, 0x9b, 0x94, 0x8c, 0x84, 0x7c , 0x72, 0x68, 0x5c, 0x4f, 0x3d, 0x2e, 0x1c, 0x0d, 0x00, 0x00 , 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 , 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 , 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 ); float f = wavelength - 350.0; int i0 = int(floor(f)); int i1 = i0 + 1; float f1 = f - float(i0); if (i0 < 0) return 0.0; if (i1 > 350 - 1) return 0.0; return mix(float(fp4plus_u[i0]), float(fp4plus_u[i1]), f1) / float(0xfe); } Hit scene(Random PRNG, Ray V); uniform int Steps; //slider[0,100,1000] uniform int Depth; //slider[0,10,100] uniform float Acne; //slider[-24.0,-18.0,8.0] struct Raytrace { int steps; int depth; float acne; }; Raytrace raytrace_de_uniforms() { Raytrace R; R.steps = Steps; R.depth = Depth; R.acne = pow(2.0, Acne); return R; } Hit raytrace_de_1(Random PRNG, Ray V, Raytrace R, float s) { Hit h = scene(srand(PRNG, 0), V); for (int i = 0; i < R.steps; ++i) { h = scene(srand(PRNG, i), V); V.origin += s * h.surface.de * V.direction; } return h; } float raytrace_de(Random PRNG, Ray V, Raytrace R) { float I = 0.0; float f = 1.0; float s = 1.0; for (int i = 0; i < R.depth; ++i) { Hit h = raytrace_de_1(srand(PRNG, i), V, R, s); f *= absorption(V.index.y, V.wavelength, distance(V.origin, h.surface.position)); I += f * h.emit; f *= h.factor; V = h.ray; V.origin += R.acne * V.direction; s = sign(scene(srand(PRNG, i), V).surface.de); if (! (f > 0)) break; } return I; } uniform float Aperture; //slider[0,0.1,10.0] uniform float Size;// slider[0.0,35.0,1000.0] uniform vec2 Wavelengths; //slider[(0.0,0.0),(300.0,780.0),(1000.0,1000.0)] struct Pinhole { float aperture; float size; vec2 wavelengths; }; Pinhole pinhole_uniforms() { Pinhole P; P.aperture = Aperture / 1000.0; P.size = Size / 1000.0; P.wavelengths = Wavelengths; return P; } Ray pinhole(Random PRNG, Camera C, vec2 pixel, Pinhole P) { vec2 rect = halton2(srand(PRNG, 1)); vec2 disc = haltonDisc(srand(PRNG, 2)); float wave = halton1(srand(PRNG, 3)); float dist = P.size / 2.0 / tan(C.fieldOfView / 2.0); vec2 p = pixel + dFdx(pixel) * rect.x + dFdy(pixel) * rect.y; vec3 from = C.origin - dist * C.Z + P.size / 2.0 * (p.x * C.X + p.y * C.Y); vec3 to = C.origin + P.aperture * (disc.x * C.X + disc.y * C.Y); Ray V; V.origin = to; V.direction = normalize(to - from); V.wavelength = mix(P.wavelengths.x, P.wavelengths.y, wave); V.index = vec2(1.0, 0.0); return V; } uint hash(uint a) { return hash_burtle_9(a); } Ray camera(Random PRNG, Camera C, vec2 coord) { return pinhole(PRNG, C, coord, pinhole_uniforms()); } float raytrace(Random PRNG, Ray V) { return raytrace_de(PRNG, V, raytrace_de_uniforms()); } vec3 film(Random PRNG, float wavelength, float intensity) { return xyz2rgb(observer(wavelength) * intensity); } Hit scene(Random PRNG, Ray V) { return Union ( Light(Invert(Sphere(Scale(10.0), V)), V, D65(V.wavelength)) , Diffuse(PRNG, Plane(Identity(), V, Y, 0.0), V, 0.5) , Glass(PRNG, Sphere(Translate(Y), V), V) ); }