Three.js PointLight Performance Impact

In Three.js, lighting is crucial for creating realistic 3D environments, but overusing independent PointLight objects can severely degrade rendering performance. This article explains how too many point lights impact GPU performance, details the underlying technical limitations of WebGL shaders, and provides actionable optimization strategies to keep your 3D scenes running smoothly.

How WebGL Handles Lights

Standard Three.js uses a forward rendering pipeline. In forward rendering, the lighting calculations for every active light are computed for every single pixel (fragment) of an object during the draw phase.

When you add a PointLight to a scene, Three.js dynamically rebuilds and recompiles the materials’ fragment shaders to include the math for that light. If you have 20 point lights and 50 meshes, the GPU must calculate the math for all 20 lights for every pixel of those 50 meshes, regardless of whether the light actually reaches the mesh. This drastically increases the arithmetic load (ALU instructions) on the GPU, leading to a drop in frame rates.

The Impact of Shadow Maps

The performance penalty of point lights increases exponentially when shadows are enabled (light.castShadow = true).

Unlike directional lights, which use a single flat texture map for shadows, a PointLight shines in all directions. To calculate shadows, Three.js must render the scene six times per light—once for each face of a cube map. If you have five point lights casting shadows, your scene requires 30 additional render passes every frame just to update the shadow maps. This quickly bottlenecks the CPU with draw calls and overwhelms the GPU’s memory bandwidth.

Hardware and Shader Limits

Aside from slowing down the frame rate, there is a hard limit to how many lights WebGL can support simultaneously.

Shaders rely on “uniforms” to receive light data (such as position, color, and intensity) from the CPU. GPUs have a strict limit on the maximum number of uniform vectors allowed in a shader. If you exceed this limit by adding too many independent lights, the shader will fail to compile, and your materials will render completely black or fail to load entirely.

Best Practices for Optimization

To maintain a high frame rate while using point lights, consider the following optimization techniques: