欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

JS中touchstart事件與click事件沖突的解決方法

 更新時(shí)間:2018年03月12日 08:36:04   作者:<_/>  
這篇文章主要給大家介紹了關(guān)于JS中touchstart事件與click事件沖突的解決方法,文中通過(guò)示例代碼將解決的方法介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧。

前言

移動(dòng)互聯(lián)網(wǎng)是未來(lái)的發(fā)展趨勢(shì),現(xiàn)在國(guó)內(nèi)很多互聯(lián)網(wǎng)大佬都在爭(zhēng)取移動(dòng)這一塊大餅,如微信及支付寶是目前比較成功的例子,當(dāng)然還有各種APP和web運(yùn)用。

下面這篇文章主要介紹了關(guān)于JS中touchstart事件與click事件沖突解決的相關(guān)內(nèi)容,下面話不多說(shuō)了,來(lái)一起看看詳細(xì)的介紹吧。

一 · 業(yè)務(wù)場(chǎng)景的描述

在對(duì)已完成的PC站點(diǎn)進(jìn)行移動(dòng)端適配時(shí),我們想要站點(diǎn)在移動(dòng)設(shè)備上有更快的響應(yīng)速度,以帶給用戶更好的體驗(yàn),此時(shí),我們應(yīng)該使用移動(dòng)設(shè)備專用的事件系統(tǒng),例如,使用 touchstart 事件代替 click 事件。

為什么這樣效果會(huì)更好呢?根據(jù)Google開發(fā)者文檔中的描述:

移動(dòng)設(shè)備上的瀏覽器將會(huì)在 click 事件觸發(fā)時(shí)延遲 300ms ,以確保這是一個(gè)“單擊”事件而非“雙擊”事件。
而對(duì)于 touchstart 事件而言,則會(huì)在用戶手指觸碰屏幕的一瞬間觸發(fā)所綁定的事件。所以,使用 touchstart 替換 click 事件的意義在于,幫助用戶在每次點(diǎn)擊時(shí)節(jié)省 300ms 的時(shí)間。在頁(yè)面頻繁需要點(diǎn)擊,或者點(diǎn)擊發(fā)生在動(dòng)畫中,對(duì)動(dòng)畫流暢度有較高要求的情境下,使用這種技術(shù)是非常必要的。

但是,讓我們回到我們的初始場(chǎng)景,在 PC端站點(diǎn)適配移動(dòng)端時(shí) 我們不能簡(jiǎn)單的進(jìn)行 touchstart和 click 事件的替換,因?yàn)镻C并不能識(shí)別 touchstart 事件。

二 · 產(chǎn)生沖突的原因

當(dāng)然,我們可以給某個(gè)元素同時(shí)綁定 touchstart 和 click 事件,但這將會(huì)導(dǎo)致本篇文章解決的問(wèn)題 -- 這兩個(gè)事件在移動(dòng)設(shè)備上會(huì)發(fā)生沖突。

由于移動(dòng)設(shè)備能夠同時(shí)識(shí)別 touchstart 和 click 事件,因此當(dāng)用戶點(diǎn)擊目標(biāo)元素時(shí),綁定在目標(biāo)元素上的 touchstart 事件與 click 事件(約300ms后)會(huì)依次被觸發(fā),也就是說(shuō),我們所綁定的回調(diào)函數(shù)會(huì)被執(zhí)行兩次!。這顯然不是我們想要的結(jié)果。

三 · 解決方案

針對(duì)這樣的情境,有以下兩種解決方案:

(一)使用 preventDefault

第一種解決方案是使用事件對(duì)象中的 preventDefault 方法,preventDefault 方法的作用在于:阻止元素默認(rèn)事件行為的發(fā)生,但有意思的是,當(dāng)我們?cè)谀繕?biāo)元素同時(shí)綁定 touchstart 和 click 事件時(shí),在 touchstart 事件回調(diào)函數(shù)中使用該方法,可以阻止后續(xù) click 事件的發(fā)生。

這從道理上是講不通的,畢竟,我們添加的 click 事件并不是元素的“默認(rèn)事件”,但它確實(shí)奏效了,或者說(shuō),被瀏覽器實(shí)現(xiàn)了,因此我們可以使用該方法解決移動(dòng)設(shè)備上 touchstart 事件與 click 事件的沖突問(wèn)題,具體代碼如下:

const Button = document.getElementById("targetButton")
Button.addEventListener("touchstart", e => {
 e.preventDefault()
 console.log("touchstart event!")
})
 
Button.addEventListener("click", e => {
 e.preventDefault()
 console.log("click event!")
})

當(dāng)你在瀏覽器上模擬移動(dòng)設(shè)備后點(diǎn)擊目標(biāo)元素,只會(huì)在控制臺(tái)看到 touchstart event! 字段,很顯然,click 事件被成功阻止了。

總結(jié)

使用該方法的優(yōu)點(diǎn)在于簡(jiǎn)單粗暴,直接有效,能夠很好的實(shí)現(xiàn)我們的目標(biāo),但缺點(diǎn)在于, preventDefault 方法為阻止 click 事件的方式是瀏覽器實(shí)現(xiàn)上的,而不是 preventDefault 原理上的,這會(huì)帶來(lái)一些不確定性,雖然我暫時(shí)尚未發(fā)現(xiàn)該方法失效的具體場(chǎng)景。

(二)基于功能檢測(cè)綁定事件

我們可以通過(guò)判斷瀏覽器是否支持 touchstart 事件來(lái)封裝元素的點(diǎn)擊事件,這樣客戶端會(huì)根據(jù)當(dāng)前環(huán)境判定元素應(yīng)該綁定的事件類型,代碼如下:

const Button = document.getElementById("targetButton")
const clickEvent = (function() {
 if ('ontouchstart' in document.documentElement === true)
 return 'touchstart';
 else
 return 'click';
})();
 
Button.addEventListener(clickEvent, e => {
 console.log("things happened!")
})

總結(jié)

該方法的優(yōu)點(diǎn)在于,我們通過(guò)增加一次判斷,為元素減少了一個(gè)不必要的事件綁定,從而避免了 touchstart 與 click 事件的沖突問(wèn)題。這種方法避免了我們書寫兩次同樣的代碼,并且相較于第一種方法更加符合邏輯,因此是我所推薦的。

好了,以上就是這篇文章的全部?jī)?nèi)容了,希望本文的內(nèi)容對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,如果有疑問(wèn)大家可以留言交流,謝謝大家對(duì)腳本之家的支持。

相關(guān)文章

最新評(píng)論