// source:https://www.shadertoy.com/view/4slGD4 float BinarySubdivision(invec3 rO, invec3 rD, vec2 t) { // Home in on the surface by dividing by two and split... float halfwayT;
for (int i = 0; i < 5; i++) {
halfwayT = dot(t, vec2(.5)); vec3 p = rO + halfwayT*rD; float d = p.y - getTerrainHeight(p.xz, perlinOctaves); // float d = Map(rO + halfwayT*rD); t = mix(vec2(t.x, halfwayT), vec2(halfwayT, t.y), step(0.5, d));
} return halfwayT; }
bool rayMarchingTerrain(vec3 ro, vec3 rd, float max_dist, outfloat res_t) { float t = 1. + Hash12(g_frag_coord)*1.; float oldT = 0.0; float delta = 0.0; bool fin = false; bool res = false; vec2 distances; for( int j=0; j< 150; j++ ) { if (fin || t > 240.0) break; vec3 p = ro + t*rd; //if (t > 240.0 || p.y > 195.0) break; float h = p.y - getTerrainHeight(p.xz, perlinOctaves); // ...Get this positions height mapping. // Are we inside, and close enough to fudge a hit?... if( h < 0.5) { fin = true; distances = vec2(oldT, t); break; } // Delta ray advance - a fudge between the height returned // and the distance already travelled. // It's a really fiddly compromise between speed and accuracy // Too large a step and the tops of ridges get missed. delta = max(0.01, 0.3*h) + (t*0.0065); oldT = t; t += delta; } if (fin) res_t = BinarySubdivision(ro, rd, distances);