javascript - 为什么在某些情况下单击鼠标中键不会触发 'click'?

标签 javascript jquery google-chrome firefox mouseevent

这是一个 JSFiddle我所看到的行为,与 Chrome 和 FF 中的中键点击和 click 事件有关。

“点击”有点管用

方法 1:将 click 处理程序直接绑定(bind)到 a 元素,中间单击将在 Chrome 中触发处理程序,但在FF.

$('div a').on('click', function(ev) {
    // middle click triggers this handler
});

方法 2:将委托(delegate)的 click 处理程序绑定(bind)到包含一个或多个 adiv。在 Chrome 或 FF 中单击鼠标中键不会触发此处理程序。

$('div').on('click', 'a', function(ev) {
    // middle click doesn't trigger this handler
});

如果 div 开始时为空,而 a 元素稍后通过 AJAX 调用或作为某些用户输入的结果填充,则此方法非常有值(value)。

'mouseup' 有效

使用 mouseup 而不是 click 会导致方法 1 和 2 在两种浏览器中都有效。

// Approach 1 w/ mouseup
$('div a').on('mouseup', function(ev) {
    // middle click **does** trigger this handler in Chrome and FF
});

// Approach 2 w/ mouseup
$('div').on('mouseup', 'a', function(ev) {
    // middle click **does** trigger this handler in Chrome and FF
});

这是 JSFiddle使用 mouseup

这很有趣,在某些情况下可能会有用,因为 mouseup 几乎是 click。但是 mouseup 不是 click,我是在追求 click 的行为。我不想创建一个 hacky mousedown;设置超时; mouseup 模拟 click

我很确定答案是“不”,但是是否有一种跨浏览器的方法可以使中间点击触发 click 处理程序?如果不是,原因是什么?

最佳答案

点击事件通常是针对鼠标左键触发的,但是,根据浏览器的不同,点击事件可能会也可能不会针对鼠标右键和/或中键触发。

在 Internet Explorer 和 Firefox 中,不会为右侧或中间按钮触发点击事件。

因此,我们不能可靠地将点击事件用于中间按钮或右键的事件处理程序。

相反,为了区分鼠标按钮,我们必须使用 mousedown 和 mouseup 事件,因为大多数浏览器都会为任何鼠标按钮触发 mousedown 和 mouseup 事件。

在 Firefox 和 Chrome 中,event.which 应该包含一个数字,指示按下了哪个鼠标按钮(1 是左边,2 是中间,3 是右边)。

另一方面,在 Internet Explorer 中,event.button 表示单击了哪个鼠标按钮(1 为左,4 为中,2 为右);

event.button 应该也适用于 Firefox 和其他浏览器,但数字可能略有不同(0 为左,1 为中,2 为右)。

所以为了把它们放在一起,我们通常会做这样的事情:

document.onmousedown = function(e) {
    var evt = e==null ? event : e;

    if (evt.which) { // if e.which, use 2 for middle button
        if (evt.which === 2) {
            // middle button clicked
        }
    } else if (evt.button) { // and if e.button, use 4
        if (evt.button === 4) {
            // middle button clicked
        }
    }
}

由于 jQuery 规范化了 event.which,您应该只需要在 jQuery 事件处理程序中使用它,并且这样做:

$('div a').on('mousedown', function(e) {
    if (e.which === 2) {
        // middle button clicked           
    }
});

换句话说,您不能使用 onclick 事件,因此您可以同时使用 mousedown 和 mouseup 来模拟它。

您可以添加一个计时器来限制 mousedown 和 mouseup 事件之间允许的时间,甚至可以添加 mousemove 处理程序来限制 mousedown 和 mouseup 事件之间的移动,并使事件处理程序在鼠标指针移动时不触发超过十个像素等。可能性几乎是无穷无尽的,所以这应该不是问题。

$('#test').on({
    mousedown: function(e) {
        if (e.which === 2) {
            $(this).data('down', true);
        }
    },
    mouseup: function(e) {
        if (e.which === 2 && $(this).data('down')) {
            alert('middle button clicked');
            $(this).data('down', false);
        }
    }
});

关于javascript - 为什么在某些情况下单击鼠标中键不会触发 'click'?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/20154901/

相关文章:

jquery - 隐藏导航栏直到鼠标悬停

脚本 : Line is executing even after return false

jQuery 悬停和 IE

html - 本地(文件 ://) website favicon works in Firefox, 不在 Chrome 或 Safari 中 - 为什么?

javascript - Codepen 六边形菜单故障排除帮助 : is my html file not properly linking to my javascript file?

javascript - 如何从chrome扩展的后台js访问页面元素

javascript - 如何使用 jQuery 选择单个子元素?

ajax - 按后退按钮时 Chrome 显示 ajax 响应

javascript - "The iterator is bound to the context object."

javascript - Webpack 和 TypeScript : module resolution error