【问题标题】:Eliminate 300ms delay on click events in mobile Safari消除移动 Safari 中点击事件的 300 毫秒延迟
【发布时间】:2012-08-27 15:26:42
【问题描述】:

从点击链接/按钮到事件触发时,我已经读过 mobile Safari has a 300ms delay on click events。延迟的原因是等待查看用户是否打算双击,但从用户体验的角度来看,等待 300 毫秒通常是不可取的。

One solution 要消除这 300 毫秒的延迟,是使用 jQuery Mobile 的“tap”处理。不幸的是,我不熟悉这个框架,如果我只需要一两行代码以正确的方式应用touchend,我不想加载一些大框架。

像许多网站一样,我的网站有很多这样的点击事件:

$("button.submitBtn").on('click', function (e) {   
  $.ajaxSubmit({... //ajax form submisssion
});

$("a.ajax").on('click', function (e) {   
  $.ajax({... //ajax page loading
});

$("button.modal").on('click', function (e) {   
      //show/hide modal dialog
});

而我想做的是使用这样的单个代码 sn-p 来消除 ALL 那些点击事件的 300 毫秒延迟:

$("a, button").on('tap', function (e) {
 $(this).trigger('click');
 e.preventDefault();
});

这是一个坏/好主意吗?

【问题讨论】:

标签: javascript jquery jquery-mobile safari touch


【解决方案1】:

现在,如果您设置视口,一些移动浏览器会消除 300 毫秒的点击延迟。您不再需要使用解决方法。

<meta name="viewport" content="width=device-width, user-scalable=no">

目前支持 Android 版 ChromeAndroid 版 FirefoxiOS 版 Safari

但在 iOS Safari 上,双击是不可缩放页面上的滚动手势。因此,他们无法消除 300 毫秒的延迟。如果他们无法消除不可缩放页面上的延迟,他们就不太可能在可缩放页面上消除它。

Windows Phones 在不可缩放页面上也保留了 300 毫秒的延迟,但它们没有像 iOS 那样的替代手势,因此它们可以像 Chrome 那样消除这种延迟。 您可以使用以下方法消除 Windows Phone 上的延迟:

html {
-ms-touch-action: manipulation;
touch-action: manipulation;
}

来源:http://updates.html5rocks.com/2013/12/300ms-tap-delay-gone-away

2015 年 12 月更新

到目前为止,iOS 上的 WebKit 和 Safari 在单击激活链接或按钮之前有 350 毫秒的延迟,以便人们通过双击来放大页面。几个月前,Chrome 已经通过使用更智能的算法来检测这一点和WebKit will follow with a similar approach,从而改变了这一点。这篇文章提供了一些很好的见解,浏览器如何使用触摸手势,以及浏览器如何仍然比现在更智能。

2016 年 3 月更新

在 iOS 版 Safari 上,检测第二次点击的 350 毫秒等待时间已被移除,以创建“快速点击”响应。这对于声明具有 width=device-width 或 user-scalable=no 的视口的页面启用。作者还可以通过使用 CSS touch-action: manipulation(如文档中的 here(向下滚动到“样式化快速点击行为”标题)和 here)来选择对特定元素进行快速点击行为。

【讨论】:

  • 其实WP有触摸事件:stackoverflow.com/questions/13396297/…
  • 是的,正如我在帖子中所写,它由 -ms-touch-action 控制。
  • 从主页(独立)运行应用程序时,iOS 上仍然存在问题。如果有人找到了一个不错的解决方法,那将非常受欢迎
  • 将触摸动作值设置为操作最接近所需的性能,但正如@MiguelGuardo 之前所说,一旦您将网页作为独立应用程序添加到 iOS 的主屏幕,效果就会丢失。
  • 可能有人可以破解 UIWebView - stackoverflow.com/questions/55155560/…
【解决方案2】:

This plugin -FastClick developed by Financial Times 非常适合您!

确保在点击函数之后直接添加event.stopPropagation(); 和/或event.preventDefault();,否则它可能会像我一样运行两次,即:

$("#buttonId").on('click',function(event){
    event.stopPropagation(); event.preventDefault();
   //do your magic

});

【讨论】:

  • 如果您使用的是 jquery mobile(无论如何是 1.3.2 版),这并不完美,它会破坏面板小部件 github.com/jquery/jquery-mobile/issues/6440 的关闭
  • 那个 event.stopPropagation() 正是我首先来到这个页面的原因。完美运行,谢谢!
  • @Jonathan fastclick 仅在有延迟问题的触摸设备上发挥作用(否则为 automatically bypassed )。但是,在每次点击事件后简单地添加 stopPropagationpreventDefault 可能会对所有浏览器中的所有事件处理程序产生不必要的副作用。
【解决方案3】:

我知道这是旧的,但你不能测试一下浏览器是否支持“触摸”吗?然后创建一个“touchend”或“click”变量,并将该变量用作绑定到您的元素的事件?

var clickOrTouch = (('ontouchend' in window)) ? 'touchend' : 'click';
$('#element').on(clickOrTouch, function() {
    // do something
});

因此代码示例检查浏览器是否支持“touchend”事件,如果不支持,则使用“click”事件。

(编辑:将“touchend”更改为“ontouchend”)

【讨论】:

  • 谢谢,我喜欢它的简单性。我希望其他人能够指出它可能存在的陷阱。
  • touchend 事件不能替换点击事件,因为@Andreas Köberle 在他的回复中解释了。例如,如果您滚动并且手指停在按钮上,它将触发链接...
  • 这是一个非常棒的轻量级解决方案,无需为了消除延迟而包含大量额外的东西库。希望我能在这个上投票 5 次! (只要你不担心滚动场景!)
  • 对于支持触摸和点击事件的计算机/浏览器,这是一个糟糕的解决方案。
  • 有些设备同时支持触摸和点击事件,您希望它们都在不同的情况下触发。我们曾经遇到过这样的情况:一些带有鼠标的 Windows 或 android 平板电脑在您点击某物时显然会触发点击事件,但当您点击时它也会触发触摸事件。这意味着你必须听这两个事件。作为一个额外的复杂因素,一些设备会在您点击时合成一个点击事件,因此在这些设备上同时监听可能会导致您的事件处理程序触发两次,除非您小心。
【解决方案4】:

我遇到了hugely popular alternative called Hammer.js(Github page),我认为这是最好的方法。

Hammer.js 是一个比 Fastclick.js(最受好评的答案)功能更全面的触摸库(有许多滑动命令)。

但请注意: 当您使用 Hammer.js 或 Fastclick.js 时,在移动设备上快速滚动往往会真正锁定 UI。如果您的网站有一个新闻源或用户会经常滚动的界面(看起来像大多数网络应用程序),这将是一个主要问题。出于这个原因,我目前没有使用这些插件。

【讨论】:

【解决方案5】:

不知何故,禁用缩放似乎禁用了这个小延迟。有道理,因为那时不再需要双击。

How can I "disable" zoom on a mobile web page?

但请注意这将产生的可用性影响。它可能对设计为应用程序的网页有用,但不应该用于更通用的“静态”页面恕我直言。我将它用于需要低延迟的宠物项目。

【讨论】:

    【解决方案6】:

    不幸的是,没有简单的方法可以做到这一点。因此,仅使用touchstarttouchend 会给您带来其他问题,例如有人在单击按钮时开始滚动。我们使用zepto 有一段时间了,即使有了这个非常好的框架,随着时间的推移也出现了一些问题。很多都是closed,不过好像不是一个简单解决的领域。

    我们有这个解决方案来全局处理链接点击:

       $(document.body).
        on('tap', 'a',function (e) {
          var href = this.getAttribute('href');
          if (e.defaultPrevented || !href) { return; }
          e.preventDefault();
          location.href= href;
        }).
        on('click', 'a', function (e) {
          e.preventDefault();
        });
    

    【讨论】:

    • -@Andreas,谢谢,所以您建议不要使用我发布的一般 tap 解决方案,并逐个元素地考虑 tap 事件?
    • 不,这不是重点。关键是不要尝试自己构建tapsolution。我会更新我的答案。
    • -@Andreas,感谢您的回答,许多点击事件都是 AJAX,因此默认事件已被阻止。你介意更新你的答案来处理这个问题吗?在这种情况下,我的一般tap 解决方案似乎与您的解决方案相同?
    【解决方案7】:

    我搜索了一种没有 jquery 和 fastclick 库的简单方法。这对我有用:

    var keyboard = document.getElementById("keyboard");
    var buttons = keyboard.children;
    var isTouch = ("ontouchstart" in window);
    for (var i=0;i<buttons.length;i++) {
        if ( isTouch ) {
            buttons[i].addEventListener('touchstart', clickHandler, false);         
        } else {
            buttons[i].addEventListener('click', clickHandler, false);          
        }
    }
    

    【讨论】:

      【解决方案8】:

      在 jQuery 中,你可以绑定“touchend”事件,在点击后立即触发代码(就像键盘中的按键)。在当前的 Chrome 和 Firefox 平板电脑版本上测试。对于您的触摸屏笔记本电脑和台式设备,也不要忘记“点击”。

      jQuery('.yourElements').bind('click touchend',function(event){
      
          event.stopPropagation();
          event.preventDefault();
      
      	// everything else
      });

      【讨论】:

        【解决方案9】:

        只是为了提供一些额外的信息。

        在 iOS 10 上,我页面上的&lt;button&gt;s 无法连续触发。总是有延迟。

        我试过fastclick/Hammer/tapjs/用touchstart替换click,都失败了。

        更新:原因似乎是按钮离边缘太近了!将它移到中心附近并滞后消失!

        【讨论】:

          【解决方案10】:

          你应该明确声明被动模式

          window.addEventListener('touchstart', (e) => {
          
              alert('fast touch');
          
          }, { passive : true});
          

          【讨论】:

            猜你喜欢
            • 1970-01-01
            • 2017-07-31
            • 2013-08-08
            • 1970-01-01
            • 2022-12-15
            • 1970-01-01
            • 1970-01-01
            • 2021-05-04
            • 1970-01-01
            相关资源
            最近更新 更多