无法在被动事件侦听器中阻止默认值

Posted

技术标签:

【中文标题】无法在被动事件侦听器中阻止默认值【英文标题】:Unable to preventDefault inside passive event listener 【发布时间】:2017-06-25 09:33:15 【问题描述】:

我正在使用Framework7 sortable list,它运行良好,只是它不会在列表更改时触发事件。

所以我正在尝试一些内置事件:

$('.sortable-handler').on('touchstart', function (e) 
    e.preventDefault();
    alert('touchstart');
);

$('.sortable-handler').on('touchmove', function (e) 
    e.preventDefault();
    console.log('touchmove');
);

$('.sortable-handler').on('touchcancel', function (e) 
    e.preventDefault();
    console.log('touchcancel');
);

$('.sortable-handler').mouseleave(function (e) 
    e.preventDefault();
    console.log('mouseleave');
);

.. 但我得到的只是:

由于目标, 被视为被动。看 https://www.chromestatus.com/features/5093566007214080

我应该寻找哪个事件来获取每个排序的更新列表?

【问题讨论】:

【参考方案1】:

看到这个blog post。如果您在每个 touchstart 上调用 preventDefault,那么您还应该有一个 CSS 规则来禁用触摸滚动,例如

.sortable-handler 
  touch-action: none;

【讨论】:

@Rick Byers,我如何为wheel mousewheel DOMMouseScroll 添加preventDefault() @Rick Beyers。你能举个例子吗?我在使用 jquery mobile swipe 事件时遇到了同样的问题 来自开发文档 - 如果您有一个水平轮播,请考虑将touch-action: pan-y pinch-zoom 应用于它,以便用户仍然可以垂直滚动和正常缩放。【参考方案2】:

对我来说

document.addEventListener("mousewheel", this.mousewheel.bind(this),  passive: false );

成功了( passive: false 部分)。

【讨论】:

它在没有绑定 mouseweel 的情况下对我有用。我用它代替了 e.preventDefault。 window.addEventListener('wheel', passive: false ) 在伪函数为我解决了这个问题之后添加了被动:假。【参考方案3】:

在纯 JS 中添加 passive: false 作为第三个参数

document.addEventListener('wheel', function(e) 
    e.preventDefault();
    doStuff(e);
,  passive: false );

【讨论】:

如果您还需要使用捕获而不是冒泡(意味着第三个参数否则为true),则第三个参数应为capture: true, passive:false。有关第三个参数的完整选项列表,请参阅 developer.mozilla.org/en-US/docs/Web/API/EventTarget/…。 我怎样才能对听众做出反应【参考方案4】:

当用户在新位置释放当前排序元素时,要在 Framework7 中处理可排序列表,您可以使用以下代码:

  $$('li').on('sortable:sort',function(event)
    alert("From " + event.detail.startIndex + " to " + event.detail.newIndex);
  );

小提琴:https://jsfiddle.net/0zf5w4y7/

【讨论】:

天啊,你是怎么知道这个事件的?他们的文档中没有提到它。 他们有。他们在页面底部提到了它。请参阅文档framework7.io/docs/sortable-list.html#sortable-events 似乎可以使用App Instance EventsortableSort触发相同的行为【参考方案5】:

我在使用 owl carousal 和滚动图像时遇到了这个问题。

所以只需在页面中添加下面的 CSS 即可解决。

.owl-carousel 
-ms-touch-action: pan-y;
touch-action: pan-y;

.owl-carousel 
-ms-touch-action: none;
touch-action: none;

【讨论】:

感谢您的回答,我专门寻找 owl-carousal,这就像一个魅力 :) 很好的答案。猫头鹰旋转木马的东西 lmao【参考方案6】:

仍然可以滚动这对我有用

if (e.changedTouches.length > 1) e.preventDefault();

【讨论】:

【参考方案7】:

添加到 Rick Buyers 的答案

请参阅此博文。如果您在每个 touchstart 上调用 preventDefault 那么你还应该有一个 CSS 规则来禁用触摸滚动,比如

.sortable-handler 
  touch-action: none;

这里是如何在 javascript 中做到这一点:

handlerList = document.getElementsByClassName("sortable-handler");
for (var i=0, len=handlerList.length|0; i<len; i=i+1|0) 
    handlerList[i].style.style.touchAction = "none";

【讨论】:

【参考方案8】:

在致电preventDefault之前进行检查

event.cancelable && event.preventDefault()

就是这样!

更多:

touchstart & touchmove 默认被动true 由于性能原因,在大多数情况下,您不需要更改默认优化。

【讨论】:

【参考方案9】:

我为我的代码制定了不同的解决方案。我需要禁用 touchend 事件的被动属性。我使用的是 jquery 3.5。你可以试试下面的代码:

jQuery.event.special.touchstart = 
        setup: function (_, ns, handle) 
            this.addEventListener('touchend', handle,  passive: !ns.includes('noPreventDefault') );
        
    ;

【讨论】:

以上是关于无法在被动事件侦听器中阻止默认值的主要内容,如果未能解决你的问题,请参考以下文章

无法在被动事件侦听器 jQuery Mobile 中阻止默认值

Skrollr 手机坏了。无法在被动事件侦听器中阻止默认值

react-datepicker“无法阻止被动事件侦听器调用中的默认值”

无法阻止被动事件监听器jQuery Mobile中的默认

owl-carousel 无法阻止默认

在 onWheel 事件中使用 event.preventDefault 时,如何规避 reactjs 中的“被动事件监听器”