意外と情報がなかったので。
ES6版
tap_es6.js
element.addEventListener("touchstart", function(...args) {
const [element, event] = args;
let isTouchMove = false;
element.addEventListener("touchend", (e) => {
if (!isTouchMove) {
/* logic */
}
}, {once: true})
element.addEventListener("touchmove", (e) => {
isTouchMove = true;
}, {once: true})
}.bind(null, element))
normal版
tap.js
element.addEventListener("touchstart", function(...args) {
const [element, event] = args;
let isTouchMove = false;
element.addEventListener("touchend", (e) => {
if (!isTouchMove) {
/* logic */
}
}, {once: true})
element.addEventListener("touchmove", (e) => {
isTouchMove = true;
}, {once: true})
}.bind(null, element))
解説
touchendの中にタップしたときのロジックを載せてしまうと、要素を触りながら要素外へ移動して離したときもタップしたことになってしまう。
つまりユーザが一度要素を触ってしまったらキャンセル不可能になってしまう。
それを防ぐためにtouchstartを拾ったらその中でtouchendとtouchmoveを拾うようにした。
もしtouchendよりまえにtouchmoveを検知したらタップをキャンセルしたとみなして、タップされたときのロジックを実行しない。