debounce and throttle

Delay or rate-limit the on… handlers of an element, or its request when the element has fetch attributes. Used in component markup.

<input oninput="search(this.value)" debounce="300ms">
<div onpointermove="track(event)" throttle="100ms"></div>
<input name="q" fetch="/api/search" trigger="input" debounce="250ms" into="#results.items">

Attributes

Attribute Type Meaning
debounce duration Run once the events stop for this long, with the last event
throttle duration Run at most once per period, on the leading edge. Events in between are dropped

If both are present, debounce is used.

What is timed

Element Timed
Element without fetch attributes Every on… handler on it
Element with fetch attributes Requests started by event-name and reference triggers. Its own on… handlers run immediately. load, visible and poll are not timed

A pending debounced call is cancelled when the element is removed. An invalid duration logs a warning and counts as 0.

Example

Previewindex.htmltyping-echo.html

Copied 500ms after you stop typing:

Handler runs:

<!doctype html>
<html lang="en">
<head>
  <meta charset="utf-8">
  <meta name="viewport" content="width=device-width, initial-scale=1">
  <title>debounce and throttle demo</title>
  <link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/@realmorg/realm@alpha/dist/realm.css">
  <link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/@realmorg/ui@alpha/dist/theme.css">
  <script type="module" src="https://cdn.jsdelivr.net/npm/@realmorg/realm@alpha/dist/realm.js"></script>
</head>
<body>
  <import-element from="./typing-echo.html"></import-element>

  <typing-echo></typing-echo>
</body>
</html>
<custom-element name="typing-echo">
  <script>
    const echo = useState({ text: "", runs: 0 });

    function copy(field) {
      echo.text = field.value;
      echo.runs++;
    }
  </script>

  <style>
    :host {
      display: grid;
      gap: calc(var(--spacing) * 2);
      width: min(calc(var(--spacing) * 80), 100%);
    }
  </style>

  <input aria-label="Type here" placeholder="Type here" oninput="copy(this)" debounce="500ms">
  <p>Copied 500ms after you stop typing: <slot name="#echo.text"></slot></p>
  <p>Handler runs: <slot name="#echo.runs"></slot></p>
</custom-element>

Edit this page on GitHub · View as Markdown