Ajax调用后,jQuery事件绑定了两次

时间:2018-08-21 07:33:47

标签: javascript jquery ajax jquery-events

我想将事件绑定到由ajax调用动态创建的元素上。 某些元素已经存在,并且在页面加载时将绑定一个事件。但是,当在ajax调用之后创建新元素时,新元素将失去其绑定。

我搜索了一个非常好的解决方案。 Jquery Event won't fire after ajax call

在这个问题上,“杰森·芬加”提出了两种解决方案

  • 第二种解决方案是使用on方法,但对我不起作用
  • 第一种方法可行,但存在一些问题

这是他提出的第一个解决方案

  

“ 1)封装您的”绑定“代码,并在页面加载时以及在有问题的元素添加回页面后立即调用它。例如:”

$(document).ready(function(){
// bind event handlers when the page loads.
bindButtonClick();
});

function bindButtonClick(){
$('.myClickableElement').click(function(){
    ... event handler code ...
});
}

function updateContent(){
$.ajax({
    url : '/ajax-endpoint.php',
    data : {'onMyWay' : 'toServer'},
    dataType : 'html',
    type : 'post',
    success : function(responseHtml){
        // .myClickableElement is replaced with new (unbound) html 
     element(s)
        $('#container').html(responseHtml);

        // re-bind event handlers to '.myClickableElement'
        bindButtonClick();  
    }
});
}

我面临什么问题? 该事件已成功与新元素绑定,但是对于旧元素或页面加载时加载的元素,该事件绑定了两次。 这是什么问题?

3 个答案:

答案 0 :(得分:2)

jQuery在绑定同一事件的侦听器之前不会检查事件侦听器是否已绑定到元素。在您的代码中,.myClickableElement选择所有此类元素,对于现有元素,将添加重复的侦听器。

通过首先解除绑定事件监听器

解决此问题的一种方法是先删除侦听器,然后再次绑定它。这样,每个目标元素将只存在一次。

function bindButtonClick(){
  $('.myClickableElement').off('click').on('click', function(){
    ... event handler code ...
  });
}

通过在父元素上使用事件委托

另一种(但有效的)方法是将事件委托用于子元素。我对您的HTML不太了解,但是您可以在父元素上执行此操作(.parent是所有.myClickableElement元素的父元素):

$('.parent').on('click', '.myClickableElement', function() {
  ... event handler code ...
});

这还将为这些元素启用事件绑定,这些元素在执行此代码时不存在于DOM中。因此,这将是解决您问题的通用解决方案,并且在AJAX完成后,您无需绑定侦听器。

答案 1 :(得分:0)

您可以使用document.on或父容器委派cilck事件,该事件将适用于现有以及动态创建的元素,而无需从ajax调用中一次又一次地绑定它

$(document).ready(function(){
   // If you know that elements for which click handler required can be anywhere in the document
   /*$(document).on('click', '.myClickableElement', function(){
    ... event handler code ...
   });*/

   //If you are sure that elements to which click event handler required is belongs to container elements
   $('#container').on('click', '.myClickableElement', function(){
    ... event handler code ...
   });
});

function updateContent(){
$.ajax({
    url : '/ajax-endpoint.php',
    data : {'onMyWay' : 'toServer'},
    dataType : 'html',
    type : 'post',
    success : function(responseHtml){
        // .myClickableElement is replaced with new (unbound) html 
     element(s)
        $('#container').html(responseHtml);

        // re-bind event handlers to '.myClickableElement'
        //bindButtonClick();   -- not required to bind again
    }
});
}

答案 2 :(得分:0)

您必须使用unbind方法取消绑定给元素的事件,然后重新绑定。

$('.myClickableElement').unbind('click').bind('click', function(){
    // action goes here
});

如果您的.myClickableElement已经有一个附加事件,则可以通过取消绑定将其删除。

要获得更好的批准,请选中此documentation