From 34e46eefae04db261c9406630f5d0f4f496fe3f6 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?David=20N=C3=A9grier?= Date: Mon, 13 Jul 2026 19:39:06 +0200 Subject: [PATCH] Fix TilemapGPULayer empty cells rendering opaque Empty cells were not discarded in the fragment shader. getTileTexelCoord() returns (0, 0) for an empty tile, so it sampled the top-left texel of tile 0 - opaque for most tilesets - painting tile 0 over everything drawn beneath the layer. This also made stacked GPU layers hide one another: an upper layer's empty cells covered the layer below. Discard empty fragments in main() and regenerate the bundled shader. Co-Authored-By: Claude Opus 4.8 (1M context) --- src/renderer/webgl/shaders/TilemapGPULayer-frag.js | 4 ++++ src/renderer/webgl/shaders/src/TilemapGPULayer.frag | 9 +++++++++ 2 files changed, 13 insertions(+) diff --git a/src/renderer/webgl/shaders/TilemapGPULayer-frag.js b/src/renderer/webgl/shaders/TilemapGPULayer-frag.js index 862dfd8564..b592df4504 100644 --- a/src/renderer/webgl/shaders/TilemapGPULayer-frag.js +++ b/src/renderer/webgl/shaders/TilemapGPULayer-frag.js @@ -227,6 +227,10 @@ module.exports = [ '{', ' vec2 layerTexCoord = outTexCoord;', ' Tile tile = getLayerData(layerTexCoord);', + ' if (tile.empty)', + ' {', + ' discard;', + ' }', ' Samples samples = getFinalSamples(tile, layerTexCoord);', ' vec4 fragColor = samples.color;', ' #pragma phaserTemplate(declareSamples)', diff --git a/src/renderer/webgl/shaders/src/TilemapGPULayer.frag b/src/renderer/webgl/shaders/src/TilemapGPULayer.frag index 8430963a03..4c256c39f5 100644 --- a/src/renderer/webgl/shaders/src/TilemapGPULayer.frag +++ b/src/renderer/webgl/shaders/src/TilemapGPULayer.frag @@ -301,6 +301,15 @@ void main () vec2 layerTexCoord = outTexCoord; Tile tile = getLayerData(layerTexCoord); + // Empty cells must not draw anything. Without this, empty tiles sample the + // tileset at (0, 0) - the top-left texel of tile 0 - which is opaque for + // most tilesets, painting tile 0 over everything drawn beneath the layer + // (and causing stacked GPU layers to hide one another). + if (tile.empty) + { + discard; + } + Samples samples = getFinalSamples(tile, layerTexCoord); vec4 fragColor = samples.color;