@oazmi/kitchensink - v0.9.13
    Preparing search index...

    Function throttle

    • a throttled function blocks the execution of fn, if less than delta_time_ms amount of time has passed since the previous non-rejected call. a rejected caller would receive the THROTTLE_REJECT symbol, instead of the fn function's evaluated value.

      the following visual illustration should give you an idea of how a throttled function with delta_time_ms = 1000 would behave.

      • the intersections in the call made axis specifies the time where a call is made to the throttled function.
      • successfully evaluated calls are labeled as resolved (with the legend marker o), and their caller will receive the evaluated value of fn()
      • unsuccessful calls (i.e. rejected) are labeled as rejected (with the legend marker x), and their caller will receive the symbol value THROTTLE_REJECT.
      │resolved │  o         o                  o                           
      │rejected │  │ x  x x  │ x                │ x x                       
      │call made├──┴─┴──┴─┴──┴─┴────────────────┴─┴─┴─────────────────► time
      │time     │  0         1         2         3         4         5      
      

      Type Parameters

      • T extends unknown
      • ARGS extends any[]

      Parameters

      • delta_time_ms: number

        the time interval in milliseconds for throttling

      • fn: (...args: ARGS) => T

        the function to be throttled

      Returns (...args: ARGS) => typeof THROTTLE_REJECT | T

      a function (that takes arguments intended for fn) that returns the value of fn if it was not throttled, otherwise a THROTTLE_REJECT symbol is returned.

      import {
      assertEquals as assertEq,
      assertLessOrEqual as assertLe,
      assertGreaterOrEqual as assertGe,
      } from "jsr:@std/assert"

      // a function that creates an asynchronous delay of the given number of milliseconds
      const sleep = (time_ms: number) => (new Promise((resolve) => (setTimeout(resolve, time_ms))))

      const
      log_history: Array<[time: number, value: number]> = [],
      t0 = performance.now(),
      current_time = () => (performance.now() - t0)

      // the function that we plan to apply throttling to
      const fn = (v: number) => {
      log_history.push([current_time(), v])
      return v + 100
      }

      // the throttled version of `fn`, that blocks subsequent calls when they are made under the `delta_time` interval (1000ms here).
      const throttled_fn = throttle(1000, fn)

      // first call to the `throttled_fn` will be evaluated successfully and immediately
      const a = throttled_fn(24)

      assertEq(a, 100 + 24)
      assertGe(log_history[0][0], 0)
      assertLe(log_history[0][0], 100)
      assertEq(log_history[0][1], 24)

      // subsequent calls to the `throttled_fn` that are made under 1000ms, will be immediately rejected with the symbol value `THROTTLE_REJECT`.
      await sleep(200)
      const b1 = throttled_fn(37)
      const b2 = throttled_fn(42)

      assertEq(b1, THROTTLE_REJECT)
      assertEq(b2, THROTTLE_REJECT)
      assertGe(current_time(), 199)
      assertLe(current_time(), 400)

      // finally, when 1000ms has passed, `throttled_fn` will permit another successful call
      await sleep(800)
      const c = throttled_fn(99)

      assertEq(c, 100 + 99)
      assertGe(log_history[1][0], 999)
      assertLe(log_history[1][0], 1300)
      assertEq(log_history[1][1], 99)