pixijs/pixijs · error · Error
[RenderTargetSystem] layer must be 0 when rendering to 2D te
Error message
[RenderTargetSystem] layer must be 0 when rendering to 2D textures in WebGL.
What it means
Inside the per-attachment bind loop, when a color attachment's GL source target is TEXTURE_2D, the layer parameter must be 0 (2D textures have no slices). If a non-zero layer is requested against a 2D texture, framebufferTexture2D cannot honor it, so the adaptor throws. This catches mismatched render-target configs where a layer is set but the texture is not a 2D array / cube map.
Source
Thrown at src/rendering/renderers/gl/renderTarget/GlRenderTargetAdaptor.ts:188
this.bindFramebuffer(gpuRenderTarget.framebuffer);
if (
!renderTarget.isRoot
&& renderTarget.colorAttachments.length > 0
&& (gpuRenderTarget._attachedMipLevel !== mipLevel
|| gpuRenderTarget._attachedLayer !== layer)
)
{
renderTarget.colorAttachments.forEach((attachment, i) =>
{
const colorTexture = attachment.texture;
const glSource = this._renderer.texture.getGlSource(colorTexture);
if (glSource.target === gl.TEXTURE_2D)
{
if (layer !== 0)
{
throw new Error('[RenderTargetSystem] layer must be 0 when rendering to 2D textures in WebGL.');
}
gl.framebufferTexture2D(
gl.FRAMEBUFFER,
gl.COLOR_ATTACHMENT0 + i,
gl.TEXTURE_2D,
glSource.texture,
mipLevel
);
}
else if (glSource.target === (gl as any).TEXTURE_2D_ARRAY)
{
if (this._renderer.context.webGLVersion < 2)
{
throw new Error('[RenderTargetSystem] Rendering to 2D array textures requires WebGL2.');
}
gl.framebufferTextureLayer(View on GitHub (pinned to 4b141e3ced)
Solutions
- Pass layer=0 (or omit it) when the render target's color attachment is a 2D texture.
- If layered rendering is intended, back the render target with a 2D array or cube texture, not a 2D texture.
- Inspect each attachment's GL source target before deciding whether to pass a non-zero layer.
- Centralize layer/texture-type validation in your render-pass builder.
Example fix
// before
const rt = new RenderTarget({ colorTextures: [tex2d] });
renderTargetSystem.bind(rt, undefined, 0, 1); // layer 1 on 2D
// after
const rt = new RenderTarget({ colorTextures: [tex2d] });
renderTargetSystem.bind(rt, undefined, 0, 0); Defensive patterns
Strategy: validation
Validate before calling
if (layer !== 0 && glSource.target === gl.TEXTURE_2D) {
throw new Error('layer must be 0 for TEXTURE_2D attachments');
} Type guard
function isTexture2DTarget(target: number, gl: WebGL2RenderingContext): boolean {
return target === gl.TEXTURE_2D;
} Prevention
- Pass layer=0 for 2D-texture-backed render targets.
- Use 2D-array or cube textures when non-zero layers are needed.
- Validate attachment target before applying a layer argument.
When it happens
Trigger: Binding a RenderTarget whose color texture is a plain 2D texture but passing layer !== 0; reusing a render pass that specifies a layer with a 2D-texture-backed target.
Common situations: Generic layer-handling code that applies a non-zero layer uniformly without checking the texture type; migrating a cube-map render path to a 2D texture but leaving the layer argument in place.
Related errors
- [RenderTargetSystem] Rendering to array layers requires WebG
- [RenderTargetSystem] Cube map layer must be between 0 and 5.
- Invalid KTX identifier in header
- WebGL does not support array textures
- [RenderTargetSystem] Rendering to mip levels is not supporte
AI-assisted analysis of pixijs/pixijs@4b141e3ced (2026-08-12).
Data as JSON: /api/errors/f09281e5ee21aba4.
Report an issue: GitHub.