render3d: under a fog wall the volumetric air is marched only to it, SSGI stops where it is solid, and card casters that fill the wall stop rebuilding
The volumetric pass marched 800 m in a fixed number of steps whatever the wall: it now stops at the wall with steps in proportion (at least 8) - 0.57 -> 0.33 ms at 30 m by the pass timers. SSGI skipped only past 900 m; it now also skips past 0.85 of a wall, where the fog is solid (u_ao_far). applyFog samples the fog's colour only where its weight is above zero. A card layer whose casters inside the wall are 80% or more of it (a kilometre's wall) casts from its static list and is not refiltered and re-uploaded every 4 m of camera motion. Fog off: the frame unchanged (0 pixels over 8). Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
parent
5b3cfac48e
commit
329439cf61
32 changed files with 36 additions and 14 deletions
|
|
@ -11,7 +11,10 @@ function fog_casters(render3d_st: mut Render3dState, l: Layer) -> int {
|
|||
if w <= 0.0 { return l.sh_buf }
|
||||
let dx = render3d_st.cam_pos[0] - l.fog_x
|
||||
let dz = render3d_st.cam_pos[2] - l.fog_z
|
||||
if l.fog_wall == w and l.fog_src == l.n_sh and dx * dx + dz * dz < FOG_CAST_STEP * FOG_CAST_STEP { return l.fog_buf }
|
||||
if l.fog_wall == w and l.fog_src == l.n_sh and (l.fog_all or dx * dx + dz * dz < FOG_CAST_STEP * FOG_CAST_STEP) {
|
||||
if l.fog_all { return l.sh_buf }
|
||||
return l.fog_buf
|
||||
}
|
||||
l.fog_wall = w; l.fog_src = l.n_sh
|
||||
l.fog_x = render3d_st.cam_pos[0]; l.fog_z = render3d_st.cam_pos[2]
|
||||
let far = w + R3D_FOG_MARGIN + FOG_CAST_THROW + FOG_CAST_STEP
|
||||
|
|
@ -30,11 +33,15 @@ function fog_casters(render3d_st: mut Render3dState, l: Layer) -> int {
|
|||
n += 1
|
||||
}
|
||||
l.fog_n = n
|
||||
# a wall that keeps nearly the whole layer (a kilometre): the static list, and no rebuild as the camera
|
||||
# moves - copying and uploading 60k cards every 4 m bought nothing there
|
||||
l.fog_all = n * 5 >= total * 4
|
||||
if l.fog_all { return l.sh_buf }
|
||||
if n > 0 { gpu_buffer_upload(render3d_st, l.fog_buf, n * INST_FLOATS * 4, data_of(dst), GPU_DYNAMIC) }
|
||||
return l.fog_buf
|
||||
}
|
||||
|
||||
function fog_casters_n(render3d_st: Render3dState, l: Layer) -> int {
|
||||
if render3d_st.r3d_fog_wall <= 0.0 { return l.n_sh }
|
||||
if render3d_st.r3d_fog_wall <= 0.0 or l.fog_all { return l.n_sh }
|
||||
return l.fog_n
|
||||
}
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue