diff --git a/src/AcDream.App/Rendering/IndoorCellStencilPipeline.cs b/src/AcDream.App/Rendering/IndoorCellStencilPipeline.cs index a887c87..9911a90 100644 --- a/src/AcDream.App/Rendering/IndoorCellStencilPipeline.cs +++ b/src/AcDream.App/Rendering/IndoorCellStencilPipeline.cs @@ -369,6 +369,11 @@ public sealed unsafe class IndoorCellStencilPipeline : IDisposable _gl.StencilFunc(StencilFunction.Equal, 0x02, 0x02u); // bit 2 set _gl.StencilMask(0x00u); // read-only — do not touch bit 1 or bit 2 _gl.StencilOp(StencilOp.Keep, StencilOp.Keep, StencilOp.Keep); + // Make the per-cell transparent render state explicit (don't inherit DrawRegionBit2's + // DepthFunc.Always): depth-test Less, depth-write off (translucent). Self-describing so + // the clip pass can't silently regress if a sibling helper's exit state changes. + _gl.DepthFunc(DepthFunction.Less); + _gl.DepthMask(false); } // Triangulate the NDC region (fan, z=0) and draw it writing only bit 2 (set or clear). @@ -415,7 +420,10 @@ public sealed unsafe class IndoorCellStencilPipeline : IDisposable _gl.DrawArrays(PrimitiveType.Triangles, 0, (uint)triVerts); _gl.BindVertexArray(0); _gl.Enable(EnableCap.CullFace); - _gl.ColorMask(true, true, true, true); + _gl.ColorMask(true, true, true, false); // match the indoor pass convention (alpha-write off) + // Restore the loop's depth-test: do NOT leak DepthFunc.Always into the cell render, the + // unclipped else-branch, the IndoorPass shells, or Step 4. (Opus review C1/C2.) + _gl.DepthFunc(DepthFunction.Less); } ///