remotion-dev/remotion · error · Error

Failed to create WebGL vertex array

Error message

Failed to create WebGL vertex array

What it means

Thrown in the setup() of the halftone-linear-gradient WebGL2 effect when gl.createVertexArray() returns null. WebGL2 returns null from resource-creation calls only when the implementation has run out of addressable GL objects or the context is lost; the library treats a null VAO as fatal because the effect cannot bind vertex attributes without it.

Solutions

  1. Reduce the number of simultaneous WebGL2 effects in the composition, or ensure effects are reused via the effect-state cache rather than re-created each frame.
  2. Check for WebGL context-loss: if gl.isContextLost() is true before setup, the GPU process is gone — restart the render.
  3. Render on a machine with a healthier GPU/driver (hardware acceleration on, or a newer headless Chromium).
  4. Update the GPU driver; very old OpenGL drivers misreport VAO limits.
Defensive patterns

Strategy: try-catch

Validate before calling

// Best-effort pre-check: probe whether the context can still hand out a VAO before relying on the effect.
function canCreateVao(canvas: HTMLCanvasElement): boolean {
  const gl = canvas.getContext('webgl2');
  if (!gl) return false;
  const vao = gl.createVertexArray();
  const ok = vao !== null;
  if (vao) gl.deleteVertexArray(vao);
  gl.deleteProgram(gl.createProgram()); // touch
  return ok;
}

Try / catch

try {
  // ...use halftoneLinearGradient()
} catch (e) {
  if (e instanceof Error && /Failed to create WebGL vertex array/.test(e.message)) {
    // most likely context loss; restart the render process
  } else throw e;
}

Prevention

When it happens

Trigger: Instantiating many halftone-linear-gradient effect instances (or other WebGL2 effects) in one render session until the context's object budget is exhausted; rendering while the GL context is in the process of being lost; rendering on a GPU whose driver caps vertex-array objects very low.

Common situations: Long render jobs with hundreds of frames each allocating fresh effect state; combining several WebGL2-backed effects per composition on low-resource GPUs; GPU process crash in Chrome leaving the context zombie.

Related errors


AI-assisted analysis of remotion-dev/remotion@78fe4bb3fd (2026-08-12). Data as JSON: /api/errors/f577e375863d7e12. Report an issue: GitHub.

Appendix: source

Thrown at packages/effects/src/halftone-linear-gradient.ts:454

		if (!gl) {
			throw createWebGL2ContextError('halftone linear gradient effect');
		}

		gl.pixelStorei(gl.UNPACK_PREMULTIPLY_ALPHA_WEBGL, true);

		const vs = compileShader(gl, gl.VERTEX_SHADER, HALFTONE_LINEAR_GRADIENT_VS);
		const fs = compileShader(
			gl,
			gl.FRAGMENT_SHADER,
			HALFTONE_LINEAR_GRADIENT_FS,
		);
		const program = linkProgram(gl, vs, fs);
		gl.deleteShader(vs);
		gl.deleteShader(fs);

		const vao = gl.createVertexArray();
		if (!vao) {
			throw new Error('Failed to create WebGL vertex array');
		}

		gl.bindVertexArray(vao);

		const data = new Float32Array([
			-1, -1, 0, 0, 1, -1, 1, 0, -1, 1, 0, 1, 1, 1, 1, 1,
		]);

		const vbo = gl.createBuffer();
		if (!vbo) {
			throw new Error('Failed to create WebGL buffer');
		}

		gl.bindBuffer(gl.ARRAY_BUFFER, vbo);
		gl.bufferData(gl.ARRAY_BUFFER, data, gl.STATIC_DRAW);

		const aPos = gl.getAttribLocation(program, 'aPos');
		const aUv = gl.getAttribLocation(program, 'aUv');

View on GitHub (pinned to 78fe4bb3fd)