Performance Optimization for 3D Background
Performance was critical: this needs to run smoothly in a variety of environments, from high-end desktops to mobile devices. This article covers the key optimizations implemented.
Overview
The animated background uses multiple optimization strategies to ensure smooth performance across different devices and browsers.
Chunk Management
Only 8-15 terrain chunks exist at once, with old chunks disposed when out of view. Chunks are generated lazily (only 3 initially) to improve load time.
-
Lazy Loading: Only generate chunks as needed
-
Disposal: Properly dispose of chunks when out of view
-
Memory Efficiency: Keep active chunk count low
Level of Detail (LOD)
Terrain grid size adapts based on distance from camera:
-
Close: 120×30 grid (high detail)
-
Medium: 160×30 grid (medium detail)
-
Far: 160×5 grid (low detail)
This reduces polygon count for distant terrain while maintaining detail up close.
Reduced Complexity
-
Terrain grid size optimized for performance
-
Tree count limited (4-7 per chunk)
-
Reduced star count (400 instead of 800)
-
Simplified geometry where possible
Memory Management
All geometries and materials properly disposed when chunks are removed, preventing memory leaks:
// Proper cleanup
chunk.geometry.dispose();
if (Array.isArray(chunk.material)) {
chunk.material.forEach(m => m.dispose());
} else {
chunk.material.dispose();
}
Efficient Height Lookups
Terrain height sampling:
-
Skips distant chunks (only checks within 8 units)
-
Samples every 3rd point for performance
-
Uses cached edge heights when available
Simplified Shaders
Cell shading uses simple if/else chains, not complex calculations. Alpha fade at edges uses separate attribute for efficiency.
IntersectionObserver
Visualizations pause rendering when not visible, saving CPU/GPU resources:
const observer = new IntersectionObserver((entries) => {
isVisible = entries[0].isIntersecting;
if (!isVisible) {
// Pause animation
}
}, {threshold: 0.1});
Throttled FPS
Animations run at 15-20 FPS instead of 60 FPS for lower compute requirements:
const targetFPS = 15;
const frameInterval = 1000 / targetFPS;
const animate = (currentTime: number) => {
const deltaTime = currentTime - lastTime;
if (deltaTime < frameInterval) return;
// Render frame
};
GPU-Based Animation
Fog particles animate in vertex shader, not CPU. This moves all animation calculations to the GPU, eliminating CPU overhead.
References
For more on performance optimization in Three.js:
Related Articles
-
An adventure with 3js 3d Backgrounds - Overview of the animated background system
-
Terrain Generation - Terrain generation optimizations including LOD and chunk management
-
L-System 3D Tree Generation - Performance considerations for tree generation and rendering
-
3d Background - Atmospheric Effects - GPU-based fog animation that leverages GPU computation for efficiency
