快速通话后仅调用一次功能

时间:2015-04-17 10:09:49

标签: javascript jquery settimeout

我有一个用户可以点击的搜索按钮。

此搜索按钮调用一个函数。我想避免在用户点击两次或更多次搜索按钮时多次执行该功能(因为他认为没有发生任何事情)。

我正在考虑以某种方式使用setTimeout(function(){}),并且如果点击按钮距离最后一次点击至少3秒,则最终只会再次调用搜索功能。

示例:https://jsfiddle.net/n1rcre75/ - 我希望能够连续两次单击该按钮(1秒后),但执行功能只运行一次

有什么想法吗?

9 个答案:

答案 0 :(得分:2)

保护搜索:

var button = document.getElementById('search');
var runSearch = true;

button.addEventListener('click', function(evt) {
        evt.preventDefault();

        if(!runSearch){
                return;
        }

        console.log('do search');

        runSearch = false;          
        setTimeout(function(){
                runSearch = true;
        }, 3000);
});

或者,如果您不想在范围中引入另一个变量:

document.getElementById('search').addEventListener('click', (function() {
        var runSearch = true;

        return function(evt)  {
                evt.preventDefault();

                if(!runSearch){
                        return;
                }

                runSearch = false;
                console.log('do search');

                setTimeout(function(){
                        runSearch = true;
                }, 3000);
        }
})());

答案 1 :(得分:1)

我创建了一个构造函数来以可重用的方式处理它。您可以在创建对象时或在调用对象时提供延迟。它的默认值为300毫秒。

function FunctionInvoker(waitTime) {
    this.timerIdentifier = null;
    this.waitTime = waitTime || 300;

    var self = this;

    this.invoke = function (callback, waitTime) {

        self.cancel();

        self.timerIdentifier = setTimeout(function () {
            self.cancel();
            callback();
        }, waitTime || self.waitTime);
    };

    this.cancel = function () {
        if (self.timerIdentifier != null) {
            clearTimeout(self.timerIdentifier);
            self.timerIdentifier = null;
        }
    }
}

使用它:

var functionInvoker = new FunctionInvoker();

functionInvoker.invoke(function () {
     // whatever you want to do (callback function)
     saveMyData(); // for ex: save data
});

我在处理滑块时使用了这段代码。滑块正在进行多次AJAX调用。通过使用functionInvoker,我只能在滑块为Xms保持相同的值时才进行AJAX调用。

答案 2 :(得分:0)

使按钮处于非活动状态,直到搜索功能返回成功或错误,或直到用户更改搜索字符串。

答案 3 :(得分:0)

当你从按下事件中调用我们的函数时,禁用函数运行时的原始按钮,例如使用Id元素的get元素:

function(foo){
document.getElementById("yourButtonId").disabled = true;

//do your function

document.getElementById("btnPlaceOrder").disabled = false;  
}

当然这个用例并不适用于所有情况,例如你想在函数内部甚至xhr进行额外的调用。如果你有回调,你应该重新启用那些按钮。

答案 4 :(得分:0)

试试这段代码:

<html>
    <head>
        <script type="text/javascript" src="http://code.jquery.com/jquery-2.1.3.min.js"></script>
        <script>
            $(document).ready(function() {
                $('button').click(function() {
                    $('button').prop('disabled', true);
                    setTimeout(function() {
                        $('button').prop('disabled', false);
                    }, 3000);
                });

            });
        </script>
    </head>
    <body>
        <button>Click me</button>
    </body>
</html>

答案 5 :(得分:0)

只是另一种解决方案:

<button onclick="buttonClick()">Click</button>

<script>
  var running = false;
  function buttonClick(){
        if(running == false){
          running = true;
          //your code
          setTimeout(function(){running = false}, 3000);
        }
  }
</script>

答案 6 :(得分:0)

通用代码。您可以将 avoid_double_click 类添加到您希望避免多次点击的链接/按钮

jQuery('.avoid_double_click').on('click', function(e) {
    var onclick_event = jQuery(this).attr('onclick');
    jQuery(this).removeAttr("onclick");
    var that = this;
    setTimeout(function(){
      jQuery(that).attr('onclick', onclick_event);
    },2000);
  });

答案 7 :(得分:0)

拿走你的小提琴并做了一些改动,

setTimeout(function(){
//stuff
},3000);

仅用于模拟实际搜索

https://jsfiddle.net/n4fhaqad/

答案 8 :(得分:0)

此功能可用于使其无需任何其他必须遵守的状态或参数

function debounce(func, wait, immediate) {
    var timeout;
    return function() {
        var context = this, args = arguments;
        var later = function() {
            timeout = null;
            if (!immediate) func.apply(context, args);
        };
        var callNow = immediate && !timeout;
        clearTimeout(timeout);
        timeout = setTimeout(later, wait);
        if (callNow) func.apply(context, args);
    };
};

https://jsfiddle.net/cpg584pp/