CtrlK
BlogDocsLog inGet started
Tessl Logo

tessl/npm-stats-js

JavaScript Performance Monitor for real-time FPS and frame timing statistics

Pending
Quality

Pending

Does it follow best practices?

Impact

Pending

No eval scenarios have been run

SecuritybySnyk

Pending

The risk profile of this skill

Overview
Eval results
Files

stats.js

stats.js is a lightweight JavaScript performance monitoring library that provides a visual widget for displaying real-time FPS (frames per second) and frame render time statistics. It creates a compact DOM-based overlay that can be embedded in web applications for performance debugging and optimization.

Package Information

  • Package Name: stats.js
  • Package Type: npm
  • Language: JavaScript
  • Installation: npm install stats.js

Core Imports

// CommonJS
const Stats = require('stats.js');

// ES Modules (if using a bundler)
import Stats from 'stats.js';

Browser direct include:

<script src="path/to/stats.min.js"></script>
<!-- Stats constructor is available globally -->

Basic Usage

// Create a new performance monitor
const stats = new Stats();

// Position the widget (usually top-left corner)
stats.domElement.style.position = 'absolute';
stats.domElement.style.left = '0px';
stats.domElement.style.top = '0px';
document.body.appendChild(stats.domElement);

// Option 1: Manual measurement
function gameLoop() {
    stats.begin();
    
    // Your performance-critical code here
    // (game rendering, calculations, etc.)
    
    stats.end();
    requestAnimationFrame(gameLoop);
}

// Option 2: Convenience method
function gameLoop() {
    stats.update(); // Equivalent to calling end() then begin()
    
    // Your performance-critical code here
    
    requestAnimationFrame(gameLoop);
}

// Start the loop
requestAnimationFrame(gameLoop);

Architecture

stats.js is built around several key design patterns:

  • DOM Widget System: Creates a self-contained visual widget using dynamically generated DOM elements with inline styling
  • Dual Display Modes: Interactive toggle between FPS (frames per second) and MS (milliseconds per frame) measurement modes
  • Performance Timing: Uses high-precision timing APIs (performance.now() with Date.now() fallback) for accurate measurements
  • Real-time Visualization: Live-updating graph bars that show performance history over time
  • Event-driven Interaction: Mouse click handling for mode switching with visual feedback
  • Modular Measurement: Flexible begin/end pattern allows measurement of arbitrary code blocks

Capabilities

Stats Constructor

Creates a new performance monitoring widget instance with interactive display modes.

/**
 * Creates a new Stats performance monitor widget
 * @constructor
 * @returns {Object} Stats instance with methods and properties
 */
function Stats();

The widget automatically creates a visual display with:

  • FPS Mode (Mode 0): Shows frames per second with min/max tracking (blue/cyan theme)
  • MS Mode (Mode 1): Shows milliseconds per frame with min/max tracking (green theme)
  • Interactive Toggle: Click the widget to switch between modes

Instance Properties

interface StatsInstance {
  /** Library revision number (currently 13) */
  REVISION: number;
  
  /** The widget's container DOM element that can be appended to the document */
  domElement: HTMLDivElement;
}

Performance Measurement

Core methods for measuring code performance within a frame or time period.

/**
 * Marks the beginning of a performance measurement frame
 * Call before the code you want to measure
 */
begin(): void;

/**
 * Marks the end of a performance measurement frame and updates display
 * Call after the code you want to measure
 * @returns {number} Current timestamp (from performance.now() or Date.now())
 */
end(): number;

/**
 * Convenience method that calls end() then immediately begins a new measurement
 * Useful for continuous monitoring in animation loops
 */
update(): void;

Usage Examples:

const stats = new Stats();
document.body.appendChild(stats.domElement);

// Measuring a specific operation
stats.begin();
performExpensiveCalculation();
stats.end();

// Measuring in an animation loop
function animate() {
    stats.begin();
    
    // Render scene, update game logic, etc.
    renderScene();
    updatePhysics();
    
    stats.end();
    requestAnimationFrame(animate);
}

// Alternative using update() method
function animate() {
    stats.update();
    
    // Your code here runs after measurement ends and new one begins
    renderScene();
    updatePhysics();
    
    requestAnimationFrame(animate);
}

Display Mode Control

Control which performance metric is displayed in the widget.

/**
 * Sets the display mode of the performance monitor
 * @param {number} value - Display mode (0 = FPS mode, 1 = MS mode)
 */
setMode(value: number): void;

Usage Examples:

const stats = new Stats();

// Start in FPS mode (default)
stats.setMode(0);

// Switch to milliseconds mode
stats.setMode(1);

// Toggle between modes programmatically
let currentMode = 0;
function toggleMode() {
    currentMode = (currentMode + 1) % 2;
    stats.setMode(currentMode);
}

Display Modes

FPS Mode (Mode 0)

  • Purpose: Displays frames rendered per second with minimum and maximum tracking
  • Color Scheme: Blue/cyan background (#002, #0ff)
  • Interpretation: Higher numbers indicate better performance
  • Graph: Real-time histogram showing FPS variations over time

MS Mode (Mode 1)

  • Purpose: Displays milliseconds needed to render each frame with min/max tracking
  • Color Scheme: Green background (#020, #0f0)
  • Interpretation: Lower numbers indicate better performance
  • Graph: Real-time histogram showing frame time variations

Styling and Theming

The widget can be customized using CSS by targeting specific element IDs:

/* Main container */
#stats {
    width: 80px;
    opacity: 0.9;
    cursor: pointer;
}

/* FPS mode styling */
#fps { /* Container for FPS display */ }
#fpsText { /* FPS text label */ }
#fpsGraph { /* FPS graph container */ }

/* MS mode styling */
#ms { /* Container for MS display */ }
#msText { /* MS text label */ }
#msGraph { /* MS graph container */ }

Browser Compatibility

  • Timing API: Uses performance.now() when available, falls back to Date.now()
  • DOM Requirements: Requires document.createElement and basic DOM manipulation
  • Module Support: Works with CommonJS (module.exports) and global variable patterns
  • Zero Dependencies: No external libraries required

Integration Patterns

Game Development

const stats = new Stats();
stats.domElement.style.position = 'fixed';
stats.domElement.style.top = '0';
stats.domElement.style.right = '0';
stats.domElement.style.zIndex = '10000';
document.body.appendChild(stats.domElement);

function gameLoop(timestamp) {
    stats.begin();
    
    updateGame(timestamp);
    renderGame();
    
    stats.end();
    requestAnimationFrame(gameLoop);
}

Web Application Monitoring

// Monitor specific operations
function monitoredFunction() {
    stats.begin();
    try {
        // Heavy computation or rendering
        processLargeDataSet();
        updateUI();
    } finally {
        stats.end(); // Ensure measurement ends even if errors occur
    }
}

// Monitor animation performance
function smoothAnimation() {
    stats.update();
    // Animation code here
    animateElements();
    requestAnimationFrame(smoothAnimation);
}

Development Debug Tool

// Only show stats in development
if (process.env.NODE_ENV === 'development') {
    const stats = new Stats();
    stats.setMode(1); // Start with MS mode for development
    document.body.appendChild(stats.domElement);
    
    // Make it draggable or add toggle button
    stats.domElement.style.position = 'fixed';
    stats.domElement.style.top = '10px';
    stats.domElement.style.left = '10px';
    stats.domElement.style.zIndex = '9999';
}
Workspace
tessl
Visibility
Public
Created
Last updated
Describes
npmpkg:npm/stats.js@1.0.x
Publish Source
CLI
Badge
tessl/npm-stats-js badge