fill-extrusion polygons occluded by underlying raster layer with raster-elevation at low pitch, depth-test appears to collapse
Author: Siraj-zakiCreated Aug 26, 2026Updated Aug 27, 2026
Labelsbug :lady_beetle:auto-triaged
mapbox-gl-js version
3.25.x
Browser and version
Chrome 130 / Safari 17 / Firefox 131 — reproduces in all three
Expected behavior
A fill-extrusion polygon whose fill-extrusion-base sits above a raster layer's raster-elevation should paint on top of the raster at every pitch and
zoom. The raster's sub-1 raster-opacity (254/255) forces the alpha-blend path and should skip depth-write, so the elevated polygon always wins the
depth test.
Actual behavior
- At pitch >= ~30°: polygon renders correctly on top of the raster.
- At pitch < ~15° (near top-down): the polygon becomes invisible; the raster paints where the polygon should be. The effect gets 100% reproducible past ~zoom 20.5 on zoom-out and near-orthographic views. At the transition zooms the polygon flickers in and out as depth values quantize.
- map.queryRenderedFeatures() still returns the polygon at the missing pixels — it's in the scene, just not drawn. A line layer on the same geometry
(which doesn't depth-test) stays visible; only the fill-extrusion top face is occluded. - Removing raster-elevation from the raster paint restores the polygon at all pitches, but breaks multi-floor raster stacking.
Link to the demonstration
No response
Steps to trigger the unexpected behavior
- new mapboxgl.Map({ style: 'mapbox://styles/mapbox/standard', center: [-74.0, 40.7], zoom: 20, pitch: 0 }).
- Add an image source and a raster layer with raster-opacity: 254/255 and raster-elevation: 0.1.
- Add a fill-extrusion layer whose polygon overlaps the raster, with fill-extrusion-base: 0.15 and fill-extrusion-height: 0.5 (top clearly above the
raster in world Z). - View at pitch: 0 — polygon is missing; the raster paints through where it should be.
- map.easeTo({ pitch: 45 }) — polygon reappears.
- map.easeTo({ pitch: 0 }) — polygon disappears again.
- Alternate: keep pitch 0 and zoom from 22 → 18 — polygon vanishes below ~zoom 20.5.
Relevant log output
No warnings or errors are emitted by Mapbox GL JS. The console stays clean throughout.
map.queryRenderedFeatures(centerPixel, { layers: ['poly'] }) at pitch 0, zoom 19:
[{ layer: { id: 'poly', type: 'fill-extrusion' }, properties: {...}, geometry: {...} }]
(polygon is found in the scene but not visible on screen.)
map.getStyle().layers.map(l => ({ id: l.id, type: l.type, slot: l.slot })) — confirms raster sits before poly in the style layer order.
WebGL: WEBGL_debug_renderer_info reports ANGLE (…) / Apple M-series GPU / … on affected machines; the same repro fails identically on Intel integrated,
Apple Silicon, and discrete NVIDIA, so it's not driver-specific.Source: mapbox/mapbox-gl-js