如何检查click事件是否已绑定 - JQuery

Dus*_*sty 127 jquery

我用按钮绑定了一个click事件:

$('#myButton').bind('click',  onButtonClicked);
Run Code Online (Sandbox Code Playgroud)

在一个场景中,这被多次调用,所以当我这样做时,我会trigger看到多个我想要阻止的ajax调用.

bind如果之前没有约束,我该怎么办?

Kon*_*rus 177

还有一种方法 - 用CSS类和过滤器标记这样的按钮:

$('#myButton:not(.bound)').addClass('bound').bind('click',  onButtonClicked);
Run Code Online (Sandbox Code Playgroud)

在最近的jQuery版本中替换bindon:

$('#myButton:not(.bound)').addClass('bound').on('click',  onButtonClicked);
Run Code Online (Sandbox Code Playgroud)

  • 优秀!感谢康拉德,这点击了甜蜜点.我喜欢这样优雅而简单的方法.我很确定它的性能也更高,因为每个元素(已经附加了点击事件处理程序)都不需要在比较每个元素的大型事件桶中进行完整搜索.在我的实现中,我将添加的辅助类命名为"click-bound",我认为这是一个更易于维护的选项:$(".list-item:not(.click-bound)").addClass("click-bound") ; (4认同)
  • 井井有条.应该是IMO接受的答案! (3认同)
  • 这是更好的性能解决方案,因为代码可以检查CSS类的存在和已存在的滑动绑定。其他解决方案会执行更多的开销(至少我能说的是fr4om),然后执行解除绑定然后重新绑定的过程。 (2认同)

lon*_*day 115

更新于2012 年8月24日:在jQuery 1.8中,不再可以使用访问元素的事件.data('events').(有关详细信息,请参阅此错误.)可以使用jQuery._data(elem, 'events')内部数据结构访问相同的数据,该数据结构未记录,因此不能100%保证保持稳定.但是,这不应该是一个问题,上面插件代码的相关行可以更改为以下内容:

var data = jQuery._data(this[0], 'events')[type];
Run Code Online (Sandbox Code Playgroud)

jQuery事件存储在一个被调用的数据对象中events,因此您可以在此搜索:

var button = $('#myButton');
if (-1 !== $.inArray(onButtonClicked, button.data('events').click)) {
    button.click(onButtonClicked);
}
Run Code Online (Sandbox Code Playgroud)

当然,如果您可以构建应用程序,那么最好只调用一次此代码.


这可以封装到一个插件中:

$.fn.isBound = function(type, fn) {
    var data = this.data('events')[type];

    if (data === undefined || data.length === 0) {
        return false;
    }

    return (-1 !== $.inArray(fn, data));
};
Run Code Online (Sandbox Code Playgroud)

然后你可以打电话:

var button = $('#myButton');
if (!button.isBound('click', onButtonClicked)) {
    button.click(onButtonClicked);
}
Run Code Online (Sandbox Code Playgroud)

  • 编辑+1.今天读这篇文章我正在使用1.8.谢谢. (10认同)
  • 谢谢你的编辑.这仅适用于按钮还是我也可以用于`<a>`?因为当我尝试它时,在`jQuery._data()`上面会出现以下错误:TypeError:a is undefined` (2认同)

Nea*_*eal 59

如果使用jQuery 1.7+:

您可以off在之前致电on:

$('#myButton').off('click', onButtonClicked) // remove handler
              .on('click', onButtonClicked); // add handler
Run Code Online (Sandbox Code Playgroud)

如果不:

你可以先取消绑定它的第一个事件:

$('#myButton').unbind('click', onButtonClicked) //remove handler
              .bind('click', onButtonClicked);  //add handler
Run Code Online (Sandbox Code Playgroud)

  • 实际上,您可以在添加处理程序时命名它们,然后取消绑定变得非常简单.`$(SEL).unbind( "click.myNamespace");` (16认同)

小智 8

我看到的最好的方法是使用live()或delegate()来捕获父级中的事件而不是每个子元素中的事件.

如果您的按钮位于#parent元素内,则可以替换:

$('#myButton').bind('click', onButtonClicked);

通过

$('#parent').delegate('#myButton', 'click', onButtonClicked);

即使执行此代码时#myButton尚不存在.

  • 不推荐的方法 (2认同)

Rod*_*ira 8

我写了一个名为"once"的非常小的插件.在元素中执行off和on.

$.fn.once = function(a, b) {
    return this.each(function() {
        $(this).off(a).on(a,b);
    });
};
Run Code Online (Sandbox Code Playgroud)

简单地说:

$(element).once('click', function(){
});
Run Code Online (Sandbox Code Playgroud)

  • .one()将在第一次执行后删除处理程序. (9认同)
  • 这里"曾经"用于附加一次处理程序.jquery中的"one"用于运行一次不附加一次. (3认同)

Kri*_*hbg 6

为什么不使用这个

unbind()bind()

$('#myButton').unbind().bind('click',  onButtonClicked);
Run Code Online (Sandbox Code Playgroud)

  • `$('#myButton').off().on('click', onButtonClicked);` 也适用于我。 (3认同)