perf(scene): hatch LOD — solid-fill substitute + sub-pixel skip (Phase 3.3)

Hatch fills drew the full per-family pattern loop every frame regardless
of zoom. Two LOD tiers, neither of which existed:

  * **Shader-side solid substitute.** When the densest line family's
    spacing × scale projects to less than 2 px, individual lines blur
    into a solid color and the per-fragment family loop is wasted ALU
    (and produces moiré). Pass `world_per_pixel` through Uniforms; the
    hatch fragment shader now returns `h.color` directly in that case.
  * **CPU-side sub-pixel skip.** When the entire hatch AABB projects
    to less than 2 px, drop the draw call. Adds `world_aabb` to
    HatchGpu plus a per-frame `compute_hatch_lod` pass (mirrors the
    existing scissor pass) and `hatch_skip_flags`. The render pass
    skips flagged hatches.

Factored a shared `aabb_below_pixel` helper for future LOD callers.

The Uniforms layout is unchanged in size (96 B) — the trailing
`_pad: vec2<f32>` becomes `world_per_pixel: f32, _pad: f32`, so wgsl
modules that don't read the new field keep working with their old
`_pad: vec2<f32>` declarations.

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
This commit is contained in:
Hakan SevenandClaude Opus 4.7 committed 2026-05-15 23:18:21 +03:00
1 parent fbbac423d4
commit e7675be0bc
5 files changed
+102 -7

No files matched your search

+5
View File
@@ -106,6 +106,10 @@ pub struct HatchGpu {
/// frame's `compute_hatch_scissors` can translate the world rect into
/// a pixel scissor.
pub vp_scissor: Option<[f32; 4]>,
/// World-space XY bounding rect [min_x, min_y, max_x, max_y] of the
/// boundary polygon. Used by the per-frame LOD pass to skip hatches
/// whose entire footprint projects to less than ~2 px (Phase 3.3).
pub world_aabb: [f32; 4],
_uniform_buf: wgpu::Buffer,
_boundary_buf: wgpu::Buffer,
_family_buf: wgpu::Buffer,
@@ -273,6 +277,7 @@ impl HatchGpu {
vertex_buffer,
bind_group,
vp_scissor: model.vp_scissor,
world_aabb: [min_x, min_y, max_x, max_y],
_uniform_buf,
_boundary_buf,
_family_buf,