From 94b91f1cc0e27c6b29bf1e8093e986a351d064b5 Mon Sep 17 00:00:00 2001 From: monkey-w1n5t0n Date: Sun, 28 Jun 2026 23:06:17 +0200 Subject: [PATCH] fix(manifold): correct SandwichStage 3D depth sort so tilt occludes right The painter's-algorithm sort was descending, but z2 (depth) increases toward the camera in both the top-down and tilted-from-above views, so nearest was painted first (underneath). This showed the last layer on top in the default top-down view and made the stack occlude inside-out when tilted back. Sort ascending: farthest first, nearest last. --- manifold/src/console/SandwichStage.tsx | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/manifold/src/console/SandwichStage.tsx b/manifold/src/console/SandwichStage.tsx index e5db0ff..d07e135 100644 --- a/manifold/src/console/SandwichStage.tsx +++ b/manifold/src/console/SandwichStage.tsx @@ -137,7 +137,12 @@ export function SandwichStage({ engine, version, pos, layerCount, names }: Sandw const lp = project(-0.5, 0.5, H(k, 0, N), k); labels.push({ x: lp.x, y: lp.y, hue, name: namesRef.current[k] || `p${k}` }); } - quads.sort((p, q) => q.depth - p.depth); + // Painter's algorithm: `depth` (z2) increases TOWARD the camera (the top + // layer / front edge have the largest depth in the top-down + tilted-from- + // above views). So draw farthest (smallest depth) first, nearest last — + // ascending. This puts layer 0 on top in the default top-down view and + // makes the stack occlude correctly as you tilt back to see the side. + quads.sort((p, q) => p.depth - q.depth); for (const Q of quads) { ctx.fillStyle = `hsla(${Q.hue},80%,${(26 + Q.L * 44).toFixed(0)}%,0.66)`; ctx.strokeStyle = `hsla(${Q.hue},80%,82%,0.18)`; ctx.lineWidth = 0.6;