Backed out changeset b71c8c052463 (bug 1943846) for causing mass failures. CLOSED...
[gecko.git] / devtools / shared / throttle.js
blob51aca6fa3669c28c3c4f6cdf85e5c8cade558c3c
1 /* This Source Code Form is subject to the terms of the Mozilla Public
2 * License, v. 2.0. If a copy of the MPL was not distributed with this
3 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
5 "use strict";
7 // setImmediate is only defined when running in the worker thread
8 /* globals setImmediate */
10 /**
11 * From underscore's `_.throttle`
12 * http://underscorejs.org
13 * (c) 2009-2014 Jeremy Ashkenas, DocumentCloud and Investigative Reporters & Editors
14 * Underscore may be freely distributed under the MIT license.
16 * Returns a function, that, when invoked, will only be triggered at most once during a
17 * given window of time. The throttled function will run as much as it can, without ever
18 * going more than once per wait duration.
20 * @param {Function} func
21 * The function to throttle
22 * @param {number} wait
23 * The wait period
24 * @param {Object} scope
25 * The scope to use for func
26 * @return {Function} The throttled function
28 function throttle(func, wait, scope) {
29 let args, result;
30 let timeout = null;
31 let previous = 0;
33 const later = function () {
34 previous = Date.now();
35 timeout = null;
36 result = func.apply(scope, args);
37 args = null;
40 const throttledFunction = function () {
41 const now = Date.now();
42 const remaining = wait - (now - previous);
43 args = arguments;
44 if (remaining <= 0) {
45 if (!isWorker) {
46 clearTimeout(timeout);
48 timeout = null;
49 previous = now;
50 result = func.apply(scope, args);
51 args = null;
52 } else if (!timeout) {
53 // On worker thread, we don't have access to privileged setTimeout/clearTimeout
54 // API which wouldn't be frozen when the worker is paused. So rely on the privileged
55 // setImmediate function which executes on the next event loop.
56 if (isWorker) {
57 setImmediate(later);
58 timeout = true;
59 } else {
60 timeout = setTimeout(later, remaining);
63 return result;
66 function cancel() {
67 if (timeout) {
68 if (!isWorker) {
69 clearTimeout(timeout);
71 timeout = null;
73 previous = 0;
74 args = undefined;
75 result = undefined;
78 function flush() {
79 if (!timeout) {
80 return result;
82 previous = 0;
83 return throttledFunction();
86 throttledFunction.cancel = cancel;
87 throttledFunction.flush = flush;
89 return throttledFunction;
92 exports.throttle = throttle;