Interactive 3D Falling Leaves Shader
See the Pen Interactive 3D Falling Leaves Shader.
Tech & Dependencies
Features
- ✓ Instanced Rendering
- ✓ Custom GLSL Shaders
- ✓ Raycasted Interaction
- ✓ Dynamic Matrix Updates
Browser Support
Core
This Interactive 3D Falling Leaves Shader is a sophisticated WebGL demonstration built with Three.js that showcases efficient rendering of thousands of unique objects. By utilizing InstancedMesh and custom GLSL shaders, it creates a stylized autumn tree where leaves respond to wind, sway realistically, and “die” (fall off) either randomly or through user interaction via raycasting.
Core Technique: Instancing & Shader Logic
The project achieves high performance by offloading calculations to the GPU and using efficient data structures for thousands of leaf instances.
1. GPU-Accelerated Displacement
The vertex shader handles both the organic wind sway (via triplanar noise) and the physical interaction. When the mouse moves, the uRaycast uniform is updated. The shader calculates the distance between each leaf instance and the cursor, applying a displacement force if they are close.
// Offset calculation based on mouse position
float offset = clamp(0.8 - distance(uRaycast, instanceMatrix[3].xyz), 0., 999.);
offset = (pow(offset, 0.8) / 2.0) * vCloseToGround;
mouseDisplace[3].xyz = vec3(offset);
// Triplanar noise for wind effect
vec4 noiseOffset = getTriplanar(uNoiseMap) * vCloseToGround;
2. Instanced Mesh Management (Логика JavaScript)
Instead of creating thousands of individual Mesh objects, the code uses one THREE.InstancedMesh. The falling physics are handled in the animate loop by decomposing the transformation matrix of “dead” leaves, updating their position and rotation, and then recomposing them.
tree.deadID = tree.deadID.map(i => {
tree.leaves.getMatrixAt(i, matrix);
matrix.decompose(dummy.position, dummy.rotation, dummy.scale);
if (dummy.position.y > 0) {
dummy.position.y -= 0.04; // Gravity
dummy.position.x += Math.random()/5 - 0.11; // Flutter
dummy.updateMatrix();
tree.leaves.setMatrixAt(i, dummy.matrix);
return(i);
}
});
tree.leaves.instanceMatrix.needsUpdate = true;
Browser Support
This snippet requires modern browser support for WebGL and ES Modules. Only legacy browsers without WebGL or ES Module support (like IE11) will fail to render this scene.


