Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Debounce actions from multiple events

How do I debounce an action that can be kicked off from multiple events? Here's an example just to demonstrate the behavior: http://jsfiddle.net/eXart/2/

<input type="text" id="t">

<div id="x"></div>

<script>
function debounce(fn, delay) {
    var timer = null;
    return function () {
        var context = this, args = arguments;
        clearTimeout(timer);
        timer = setTimeout(function () {
            fn.apply(context, args);
        }, delay);
    };
}

function doStuff(){
    document.getElementById("x").innerHTML +="<br>stuff";
}

    var t = document.getElementById("t");
    t.onchange = debounce(function(){ doStuff() }, 500);
    t.onblur = debounce(function(){ doStuff() }, 500);
</script>

If you enter some text in the textbox and click out of it, you see "stuff" appears twice instead of once because each event is getting it's own debounce instance. How do you share debounce instances across events?

like image 762
adam0101 Avatar asked Oct 17 '13 18:10

adam0101


1 Answers

You must attach the same debounced handler, like this

var debouncedFunc = debounce(function(){ doStuff(); }, 500);

t.onchange = debouncedFunc;
t.onblur = debouncedFunc;

if you want to share the timer.

But I think you should only use one of the onchange or onblur events if you want to avoid duplicate invocations once the input loses focus.

like image 169
tobi Avatar answered Sep 30 '22 15:09

tobi