【问题标题】:jQuery click event triggered multiple times off one clickjQuery单击事件多次触发一次单击
【发布时间】:2017-07-11 22:17:58
【问题描述】:

当仅单击一个元素时,我在 jQuery 中注册了多次单击时遇到问题。我已经阅读了Stack Overflow 上的一些其他线程来尝试解决它,但我认为这是我编写的代码。 HTML 代码无效,但这是由某些 HTML 5 和使用 YouTube 嵌入代码引起的。不会影响点击。

jQuery,在 document.ready 上触发

function setupHorzNav(portalWidth) {
    $('.next, .prev').each(function() {
        $(this).click(function(e) {
            var target = $(this).attr('href');
            initiateScroll(target);
            console.log("click!");
            e.stopPropagation();
            e.preventDefault();
            return false;
        });
    });

    function initiateScroll(target) {
        var position = $(target).offset();
        $('html, body').animate({
            scrollLeft: position.left
        }, 500);
    }
}

示例 HTML

<nav class="prev-next">
    <a href="#countdown-wrapper" class="prev">Prev</a>
    <a href="#signup-wrapper" class="next">Next</a>
</nav>

在 Firefox 中,单击即可记录“单击!” 16次! Chrome 只看到一个,但两种浏览器都显示上述代码存在问题。

是我写错了代码还是有错误?

-- 一些额外的信息 ------------------------------------------

setupHorzNav 由我的代码中的另一个函数调用。我已经对此进行了测试并确认它仅在初始加载时被调用一次。

if ( portalWidth >= 1248 ) {
    wrapperWidth = newWidth * 4;
    setupHorzNav(newWidth);
}
else
{
    wrapperWidth = '100%';
}

nav 'prev-next' 有多个实例。所有目标都是不同的锚点。都在同一个html页面中。

<nav class="prev-next">
    <a href="#video-wrapper" class="prev">Prev</a>
</nav>

【问题讨论】:

  • 你能发布你打电话给setupHorzNav的地方和&lt;nav class="prev-next"&gt;周围的代码吗?
  • 只是一些建议。在这种情况下您不需要使用each,只需使用:$('.next, .prev').click(function (e) { //... });。而且您不需要使用所有三个e.stopPropagation();e.preventDefault();return false;return false; 自动执行 preventDefaultstopPropagation。如果您想要执行其中一项,或者由于代码中可能存在问题而想要比return false 更早地执行它,那么这些非常有用
  • 另外,最好在循环之外定义你的事件处理函数(比如你的情况下的每个),以确保你没有多个相同的实例在内存中起作用。
  • 我相信 chrome 也会显示 16 条日志,但在行前显示为一个数字。
  • setupHorzNav 函数的开头放置一个 console.log 并检查它被调用了多少次。

标签: javascript jquery html


【解决方案1】:

尝试像这样解除点击事件的绑定

$(this).unbind('click').click(function (e) {    
});

【讨论】:

    【解决方案2】:

    您不需要.each() 来绑定事件处理程序。试试这个:

    $('.next, .prev').click(function(e){
            var target = $(this).attr('href');
            initiateScroll(target);
            console.log("click!");
            e.stopPropagation();
            e.preventDefault();
            return false;
    });
    

    编辑: 我认为这是您从导致它的setupHorzNav 函数中附加事件处理程序的方式。将其更改为仅附加一次,例如 $(document).ready() 或其他内容。

    我已经设法通过从事件处理程序调用的函数中附加事件处理程序来了解多个事件处理程序的情况。其效果是点击事件处理程序的数量随着每次点击而呈几何级数增长。

    这是代码:(和jsfiddle 演示)

    function setupNav() {
        $('.next, .prev').each(function () {
            $(this).click(function (e) {
                setupNav();
                var target = $(this).attr('href');
                console.log("click!");
                e.stopPropagation();
                e.preventDefault();
                return false;
            });
        });
    }
    
    setupNav();
    

    查看从点击事件处理程序调用setupNav() 函数如何在连续点击时添加多个事件处理程序(以及click 日志消息)

    【讨论】:

    • 不会改变/帮助/修复任何东西,这与使用each 相同。正如您所指出的,each 在这种情况下是不必要的,但如果更改也无济于事
    • 我使用了您添加的第一个示例代码。现在可以了。我可以在 FF 和 Chrome 中确认点击是按预期触发的。现在没有奇怪的滚动问题。杰出的!谢谢。
    【解决方案3】:

    由于您的问题并不清楚您是否多次调用绑定函数,因此快速而肮脏的修复方法是:

    $('.next, .prev').unbind('click').click(function() {
        ...
    });
    

    您在这里所做的是取消绑定任何以前绑定的 click 事件处理程序并重新绑定。

    【讨论】:

      【解决方案4】:

      其他地方没有其他点击绑定吗?

      您是否使用 ajax 加载页面?

      你也可以试试这个:

      $('.next, .prev').click(function (e) {
          var target = $(this).attr('href');
          initiateScroll(target);
          console.log("click!");
          e.stopPropagation();
          e.preventDefault();
          return false;
      });
      

      【讨论】:

      • 在其他地方有点击绑定,但在不相关的项目上,由单独的函数触发。页面不是通过 ajax 加载的。
      猜你喜欢
      • 2013-02-04
      • 2011-01-08
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2017-12-19
      • 2018-09-13
      • 2012-02-26
      • 1970-01-01
      相关资源
      最近更新 更多