UNPKG

@nesvet/n

Version:
102 lines 3.13 kB
import { noop } from "./noop.js"; export function debounce(callback, limit = 0, options = {}) { let { leading = false, trailing = true } = options; const { maxWait = Infinity } = options; let timeout; let maxWaitTimeout; let end; let context; let args; let initial; let final; let result; const expired = async () => { const n = Date.now(); if (n >= end) { timeout = undefined; end = undefined; clearTimeout(maxWaitTimeout); if (typeof final == "function") await final(); debounced.resolve(result); debounced.promise.isResolved = true; initial = leading; } else { clearTimeout(timeout); timeout = setTimeout(expired, end - n); } }; const maxWaitExpired = Number.isFinite(maxWait) ? () => { if (final === run) final = false; run(); maxWaitTimeout = setTimeout(maxWaitExpired, maxWait); } : null; async function run() { return (result = await callback.apply(context, args)); } if (leading && typeof leading == "boolean") leading = run; initial = leading; if (trailing && typeof trailing == "boolean") trailing = run; final = trailing; const debounced = Object.assign(function (..._args) { args = _args; context = this; // eslint-disable-line no-invalid-this end = Date.now() + limit; final = trailing; if (debounced.promise.isResolved) debounced.promise = Object.assign(new Promise(resolve => { debounced.resolve = resolve; if (typeof initial == "function") { initial(); initial = false; if (final === run) final = false; } if (!timeout) { timeout = setTimeout(expired, limit); if (maxWaitExpired) maxWaitTimeout = setTimeout(maxWaitExpired, maxWait); } }), { isResolved: false }); return debounced.promise; }, { callback, promise: Object.assign(Promise.resolve(), { isResolved: true }), resolve: noop, run, clear: async (shouldRun) => { clearTimeout(timeout); timeout = undefined; clearTimeout(maxWaitTimeout); debounced.promise.isResolved = true; debounced.resolve(shouldRun ? await run() : result); } }); return debounced; } debounce.noop = Object.assign(() => { }, { callback: noop, promise: Object.assign(Promise.resolve(), { isResolved: true }), resolve: noop, run: noop, clear: noop }); export function throttle(callback, limit, options) { return debounce(callback, limit, { maxWait: limit, leading: true, trailing: true, ...options }); } //# sourceMappingURL=debounce.js.map