Monitoring Performance with Stats.js in Three.js
Stats.js is a lightweight performance monitoring utility integrated into the Three.js ecosystem, deisgned to measure frame rates (FPS), rendering time (ms), and memory usage (mb) for WebGL aplpications. It provides real-time visual feedback to optimize animation smoothness.
Importing Stats.js
When installing Three.js via npm (npm install three), Stats.js is included in the examples directory. Import it using ES modules:
import Stats from 'three/examples/jsm/libs/stats.module.js';
Basic Usage
To implement performance monitoring, follow these steps:
- Instantiate the monitor
- Configure the display panel (FPS: 0, ms: 1, mb: 2)
- Position the UI element
- Append to the DOM
- Update metrics during rendering
Example implementation:
// Initialize performance monitor
const perfMonitor = new Stats();
// Set initial panel (0: FPS, 1: ms, 2: mb)
perfMonitor.showPanel(0);
// Style and position the monitor
Object.assign(perfMonitor.domElement.style, {
position: 'absolute',
left: '0',
top: '0',
zIndex: '100'
});
document.body.appendChild(perfMonitor.domElement);
// Animation loop with monitoring
function animate() {
perfMonitor.update(); // Refresh metrics
// Application rendering logic
boxMesh.rotation.x += 0.01;
rndr.render(sce, cam);
requestAnimationFrame(animate);
}
animate();
Alternative Configuration Methods
- Panel selection: Use
showPanel(panelId)instead of deprecatedsetMode(). For example,perfMonitor.showPanel(1)displays rendering time in milliseconds. - Metric collection: Wrap critical code sections with
begin()andend()for granular timing analysis:
function criticalSection() {
perfMonitor.begin();
// Code to profile (e.g., complex geometry updates)
updateHeavyCalculations();
perfMonitor.end();
}
Complete Integration Example
<script type="module">
import * as THREE from 'three';
import Stats from 'three/examples/jsm/libs/stats.module.js';
// Scene setup
const sce = new THREE.Scene();
const cam = new THREE.PerspectiveCamera(
75, window.innerWidth/window.innerHeight, 0.1, 1000
);
cam.position.set(10, 10, 10);
cam.lookAt(sce.position);
sce.add(cam);
// Object creation
const boxGeom = new THREE.BoxGeometry(1, 1, 1);
const boxMat = new THREE.MeshBasicMaterial({ color: 0xffff00 });
const boxMesh = new THREE.Mesh(boxGeom, boxMat);
sce.add(boxMesh);
// Renderer initialization
const rndr = new THREE.WebGLRenderer();
rndr.setSize(window.innerWidth, window.innerHeight);
document.body.appendChild(rndr.domElement);
// Performance monitoring
const perfMonitor = new Stats();
perfMonitor.showPanel(0); // Show FPS
Object.assign(perfMonitor.domElement.style, {
position: 'absolute', left: '0', top: '0'
});
document.body.appendChild(perfMonitor.domElement);
// Animation loop
function animate() {
perfMonitor.update();
boxMesh.rotation.x += 0.01;
boxMesh.rotation.y += 0.01;
rndr.render(sce, cam);
requestAnimationFrame(animate);
}
animate();
</script>
Clicking the monitor UI toggles between FPS, ms, and mb panels dynamically.