I watched this video on https://www.youtube.com/watch?v=cjIswDCKgu0&t=429s YouTube;
I just wanted to make a simple debounce function. but this code does not work on my device as intended. Please help.
let debounceTimes = 0;
// this code does not work as intended
let timeout; // if I make it global it works just fine
// but I don't want to do that for obvious reasons
function debounce(cb, delay = 100) {
// let timeout; // this is being reinitialized
// only if I could do something like this
// static timeout;
// to avoid re-initializing the variable
// return (...args) => {
clearTimeout(timeout);
timeout = setTimeout(() => {
cb();
}, delay);
// }
}
window.addEventListener("mousemove", () => {
// console.log("hello");
// document.getElementById("debounce").innerText ;
debounce(
() => {
debounceTimes ;
document.getElementById("debounce").innerText = String(debounceTimes);
}, 100);
});
CodePudding user response:
In this example, it is not possible, since when the event is triggered it just runs the debounce
function which creates the variable inside. To avoid re-initializing the variable you can:
Create variable in the global scope
Create another function that returns the debounce function(so the timeout is hidden in function scope)
let debounceTimes = 0;
function getDebounce() {
let timeout;
function debounce(cb, delay = 100) {
clearTimeout(timeout);
timeout = setTimeout(() => {
cb();
}, delay);
}
return debounce;
}
const debounce = getDebounce();
window.addEventListener('mousemove', () => {
debounce(() => {
debounceTimes ;
document.getElementById('debounce').innerText = String(debounceTimes);
}, 100);
});
CodePudding user response:
A good pattern in JS when you want a variable to be private to a function, but yet outside its scope, is to use closures and IIFE:
const debounce = (function() {
let debounceTimes = 0;
let timeout; // if I make it global it works just fine
// but I don't want to do that for obvious reasons
return (cb, delay = 100) => {
clearTimeout(timeout);
timeout = setTimeout(() => {
cb();
console.log("Count:", debounceTimes)
debounceTimes
}, delay);
}
})()
window.onmousemove = () => debounce(() => console.log("Debounced"),200)
CodePudding user response:
I ended up making a class with static method and varibles since it was simillar to the c ways of doing things. but i like @Tomasz Staszkiewicz 's answer better. He made another function inside the function to achive this.
class ignoreInput {
static #timeout;
static debounce (cb, delay = 100) {
clearTimeout(this.timeout);
this.timeout = setTimeout(() => {
cb();
}
, delay);
}
static throttle (cb, delay = 100) {
// some code
}
};
CodePudding user response:
As i see you dont use timeout variable out of debounce function, then try it as parameter of debounce function...
let debounceTimes = 0;
// this code does not work as intended
// if I make it global it works just fine
// but I don't want to do that for obvious reasons
function debounce(timeout, cb, delay = 100) {
// let timeout; // this is being reinitialized
// only if I could do something like this
// static timeout;
// to avoid re-initializing the variable
// return (...args) => {
clearTimeout(timeout);
timeout = setTimeout(() => {
cb();
}, delay);
// }
}
window.addEventListener("mousemove", () => {
// console.log("hello");
// document.getElementById("debounce").innerText ;
debounce(
() => {
debounceTimes ;
document.getElementById("debounce").innerText = String(debounceTimes);
}, 100);
});
Run code snippetHide resultsExpand snippet