300ms delay removal: using fastclick.js vs using ontouchstart

ぃ、小莉子 提交于 2020-01-28 15:50:18

问题


I'm using regular jQuery and I have an event handler that looks like this:

$('#someID').on({

   click: SomeFunction

}, '.SomeClass');

This will produce a 300ms delay on the click event and I'm looking to remove this delay. What's the difference between rewriting this code like that:

$('#someID').on({

   'touchstart': SomeFunction

}, '.SomeClass');

and using an external library like Fastclick.js?


回答1:


I work for the Financial Times and head up the team that created Fastclick.js.

In principle, all Fastclick does is bind to the touchend event and fire a click event on the same element. However, there are many edge cases, traps and pitfalls, all of which we have discovered, worked around and baked into fastclick. For example:

  • If you move your finger during the touch, it's a swipe or other kind of gesture, so we should not react
  • If you touch with more than one finger at a time, we should not react
  • If you touch a text field, the control needs to gain focus as well as receive a click event
  • Some controls require a native click to operate (for security), so we should allow selective opting-out of Fastclick
  • Some browsers already support fast clicking when viewport sizing defaults to device-width. We should not activate Fastclick behaviour at all in these user agents.

Since Fastclick is 1% basic premise and 99% edge cases, there are lots of alternatives that are smaller, including probably one that you could write yourself. But many people prefer the reassurance that comes with using a well tested library.

Note that we use touchend and not touchstart because A) a click is not triggered until you lift your finger from the mouse button or trackpad, so touch should mirror that behaviour, and B) until you end the touch we don't yet know if you plan on moving your finger while it's in contact with the screen, which would be a gesture, swipe or scroll rather than a click.

Hope that helps.




回答2:


touchstart happens at the time your finger touches the element while click won't fire until you release your finger (touchend) on the same element. If you touch, move your finger out of the element, then release, no click event occurs. However, in that case, touchstart does occur.

Because you tag Cordova, I assume it is a Cordova hybrid app for mobile.
1. On Android since 2.3.x, 300ms is removed if you disable zoom:

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

2. On Android since 4.4.3 (whose webview is Chrome 33), 300ms is removed if you specify that the page is mobile-optimized:

<meta name="viewport" content="width=device-width" />
  1. On IE10+, use CSS to remove that delay:

    -ms-touch-action: manipulation; /* IE10 /
    touch-action: manipulation; /
    IE11+ */

  2. On iOS, you cannot use viewport to disable 300ms delay

Therefore, to make sure the 300ms is removed, I usually use a tap library for tap. For example: tappy (tap only), zepto touch (tap, swipe - good if your site already uses zepto), hammer.js (various gestures), depending on your needs. Those tap events do not suffer from the 300ms problem.

FastClick.js should be OK though I did not try it yet.




回答3:


Andrew gives the correct answer.

In general,

"touchstart" will be triggered when we perform "click","swipe","scroll" etc. However, as you know, what we want to capture is "click".

What FastClick.js does is to define a rule for "click". For example, we could set the condition below as a "click":

During time between "touchstart" and "touchend" is 200ms, in "touchmove", we find no distance has been moved.

The same, we could set the condition below as a "scroll":

During "touchstart" and "touchend", in "touchmove", we find distance has been moved on y axis but no x axis moving happens.




回答4:


To get rid of 300ms delay, here are two options:

Option 1:

By default, there will be about 300ms delay for the click event on webview, which results in a very slow response/performance when click on a button. You can try to override the click event with the ‘tap’ event in jQuery Mobile to remove the delay: (Source: IBM)

$('btnId').on('tap', function(e) {
     e.stopImmediatePropagation();
     e.preventDefault();
     ...
});

Option 2: Interesting one

By default JQuery Mobile CSS itself has introduced a long delay - I mean some places 300ms or 350ms or 225ms. These delays can be optimized. I too have modified the default CSS and reduced the long delay from 350ms to 100ms for page transition and it was really great.

Search in the Jquery Mobile CSS : animation-duration

JQuery Mobile 1.2.0

In some places delay is set to: -webkit-animation-duration:350ms;-moz-animation-duration:350ms while other places delay is: -webkit-animation-duration:225ms;-moz-animation-duration:225ms

The latest version on github:

.in {
    -webkit-animation-timing-function: ease-out;
    -webkit-animation-duration: 350ms;
    -moz-animation-timing-function: ease-out;
    -moz-animation-duration: 350ms;
    animation-timing-function: ease-out;
    animation-duration: 350ms;
}
.out {
    -webkit-animation-timing-function: ease-in;
    -webkit-animation-duration: 225ms;
    -moz-animation-timing-function: ease-in;
    -moz-animation-duration: 225ms;
    animation-timing-function: ease-in;
    animation-duration: 225ms;
}

Check this github code:

Now it's up to you which delay you want to optimize, like click, page transition, flip, slide etc. and accordingly just modify the default delay time with your own desired delay time.

In this way there is NO need of an extra library




回答5:


If you go to a site that isn't mobile optimised, it starts zoomed out so you can see the full width of the page. To read the content, you either pinch zoom, or double-tap some content to zoom it to full-width. This double-tap is the performance killer, because with every tap we have to wait to see if it might become a double-tap, and that wait is 300ms. Here's how it plays out:

  • touchstart
  • touchend
  • Wait 300ms in case of another tap
  • click

This pause applies to click events in JavaScript, but also other click-based interactions such as links and form controls.

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

Fastclick.js solve problem related if user didn't want to click on element and just decided to scroll.




回答6:


You may not use FastClick.js nowadays:

Note: As of late 2015 most mobile browsers - notably Chrome and Safari - no longer have a 300ms touch delay, so fastclick offers no benefit on newer browsers, and risks introducing bugs into your application. Consider carefully whether you really need to use it.

(Taken from: https://github.com/ftlabs/fastclick docs)



来源:https://stackoverflow.com/questions/27173272/300ms-delay-removal-using-fastclick-js-vs-using-ontouchstart

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!