Is 1000Hz possible in Chrome? Bypassing the Event Loop to test Mouse Polling Rate

Published: (December 24, 2025 at 09:01 PM EST)
2 min read
Source: Dev.to

Source: Dev.to

Cover image for Is 1000Hz possible in Chrome? Bypassing the Event Loop to test Mouse Polling Rate

The Problem: Visuals vs. Inputs

Most web animations rely on requestAnimationFrame (rAF). If your monitor is 60 Hz, rAF fires every ~16.6 ms. Measuring a 1000 Hz mouse (which sends data every 1 ms) inside an rAF loop will miss ~94 % of the data.

We need to decouple the Input Thread from the Render Thread.

The Solution: pointermove + performance.now()

  • Listen to the raw pointermove event, which fires more frequently than screen updates (Chrome/Edge expose “Coalesced Events”).
  • Use the High Resolution Time API (performance.now()) for microsecond precision—Date.now() is only millisecond‑accurate.

The Code

let lastEventTime = 0;
let pollingRateSamples = [];

window.addEventListener('pointermove', (event) => {
  // 1. Get the microsecond‑precise timestamp
  const currentEventTime = performance.now();

  // 2. Calculate the delta (time between two events)
  const timeDelta = currentEventTime - lastEventTime;

  // 3. Convert to Frequency (Hz)
  // Hz = 1000 ms / delta
  const instantaneousHz = 1000 / timeDelta;

  // 4. Filter out noise (idle or super slow movements)
  if (instantaneousHz > 10 && instantaneousHz < 8000) {
    pollingRateSamples.push(instantaneousHz);
  }

  lastEventTime = currentEventTime;

  // NOTE: Do NOT update the DOM here!
  // Updating the UI every 1 ms will kill browser performance.
  // Store the data, and visualize it in a separate requestAnimationFrame loop.
});

The “Event Loop” Trap

Browsers group events to save battery. A heavy operation inside the pointermove listener causes throttling to match the frame rate.

How to avoid it

  • Keep the listener lightweight (only math and array push).
  • De‑couple visualization: use a separate requestAnimationFrame loop to read from pollingRateSamples and draw the graph.

The Result

By separating input capture from rendering, consistent readings matching native software are achieved.

Demo GIF

You can try the live demo here: Mouse Polling Rate Test

The suite also includes a Gamepad Tester (for stick drift) and a Dead Pixel test, all running locally in the browser.

Discussion

I built this to prove that modern Web APIs are powerful enough to replace many “utility” desktop tools.

What do you think? Are we at a point where we can finally uninstall those 500 MB driver suites, or will native apps always be king for hardware interaction?

Let me know in the comments!

Back to Blog

Related posts

Read more »