移動端300ms點擊延遲和點擊穿透問題

一般情況下,如果沒有經(jīng)過特殊處理持舆,移動端瀏覽器在派發(fā)點擊事件的時候,通常會出現(xiàn)300ms左右的延遲伪窖。也就是說逸寓,當我們點擊頁面的時候移動端瀏覽器并不是立即作出反應,而是會等上一小會兒才會出現(xiàn)點擊的效果覆山。在移動WEB興起的初期竹伸,用戶對300ms的延遲感覺不明顯。但是簇宽,隨著用戶對交互體驗的要求越來越高勋篓,現(xiàn)今吧享,移動端300ms的點擊延遲逐漸變得明顯而無法忍受。

那么譬嚣,移動端300ms的點擊延遲是怎么來的呢耙蔑?

問題由來
這要追溯至 2007 年初。蘋果公司在發(fā)布首款 iPhone 前夕孤荣,遇到一個問題:當時的網(wǎng)站都是為大屏幕設備所設計的甸陌。于是蘋果的工程師們做了一些約定,應對 iPhone 這種小屏幕瀏覽桌面端站點的問題盐股。

這當中最出名的钱豁,當屬雙擊縮放(double tap to zoom),這也是會有上述 300 毫秒延遲的主要原因疯汁。

雙擊縮放牲尺,顧名思義,即用手指在屏幕上快速點擊兩次幌蚊,iOS 自帶的 Safari 瀏覽器會將網(wǎng)頁縮放至原始比例谤碳。 那么這和 300 毫秒延遲有什么聯(lián)系呢? 假定這么一個場景溢豆。用戶在 iOS Safari 里邊點擊了一個鏈接蜒简。由于用戶可以進行雙擊縮放或者雙擊滾動的操作,當用戶一次點擊屏幕之后漩仙,瀏覽器并不能立刻判斷用戶是確實要打開這個鏈接搓茬,還是想要進行雙擊操作。因此队他,iOS Safari 就等待 300 毫秒卷仑,以判斷用戶是否再次點擊了屏幕。 鑒于iPhone的成功麸折,其他移動瀏覽器都復制了 iPhone Safari 瀏覽器的多數(shù)約定锡凝,包括雙擊縮放,幾乎現(xiàn)在所有的移動端瀏覽器都有這個功能垢啼。之前人們剛剛接觸移動端的頁面窜锯,在欣喜的時候往往不會care這個300ms的延時問題,可是如今touch端界面如雨后春筍膊夹,用戶對體驗的要求也更高衬浑,這300ms帶來的卡頓慢慢變得讓人難以接受。

也就是說放刨,移動端瀏覽器會有一些默認的行為,比如雙擊縮放尸饺、雙擊滾動进统。這些行為助币,尤其是雙擊縮放,主要是為桌面網(wǎng)站在移動端的瀏覽體驗設計的螟碎。而在用戶對頁面進行操作的時候眉菱,移動端瀏覽器會優(yōu)先判斷用戶是否要觸發(fā)默認的行為。

那有什么辦法可以解決這個問題呢掉分?

瀏覽器開發(fā)商的解決方案

瀏覽器開發(fā)商要對移動端瀏覽器本身的設計進行改善俭缓,以提供長遠的解決方案。

目前酥郭,瀏覽器開發(fā)商的解決方案主要有一下三種方案:
方案一:禁用縮放
當HTML文檔頭部包含如下meta標簽時:

<meta name="viewport" content="user-scalable=no">
<meta name="viewport" content="initial-scale=1,maximum-scale=1">

表明這個頁面是不可縮放的华坦,那雙擊縮放的功能就沒有意義了,此時瀏覽器可以禁用默認的雙擊縮放行為并且去掉300ms的點擊延遲不从。
這個方案有一個缺點惜姐,就是必須通過完全禁用縮放來達到去掉點擊延遲的目的,然而完全禁用縮放并不是我們的初衷椿息,我們只是想禁掉默認的雙擊縮放行為歹袁,這樣就不用等待300ms來判斷當前操作是否是雙擊。但是通常情況下寝优,我們還是希望頁面能通過雙指縮放來進行縮放操作条舔,比如放大一張圖片,放大一段很小的文字乏矾。

方案二:更改默認的視口寬度
一開始逞刷,為了讓桌面站點能在移動端瀏覽器正常顯示,移動端瀏覽器默認的視口寬度并不等于設備瀏覽器視窗寬度妻熊,而是要比設備瀏覽器視窗寬度大夸浅,通常是980px。我們可以通過以下標簽來設置視口寬度為設備寬度扔役。

<meta name="viewport" content="width=device-width">

因為雙擊縮放主要是用來改善桌面站點在移動端瀏覽體驗的帆喇,而隨著響應式設計的普及,很多站點都已經(jīng)對移動端坐過適配和優(yōu)化了亿胸,這個時候就不需要雙擊縮放了坯钦,如果能夠識別出一個網(wǎng)站是響應式的網(wǎng)站,那么移動端瀏覽器就可以自動禁掉默認的雙擊縮放行為并且去掉300ms的點擊延遲侈玄。如果設置了上述meta標簽婉刀,那瀏覽器就可以認為該網(wǎng)站已經(jīng)對移動端做過了適配和優(yōu)化,就無需雙擊縮放操作了序仙。
這個方案相比方案一的好處在于突颊,它沒有完全禁用縮放,而只是禁用了瀏覽器默認的雙擊縮放行為,但用戶仍然可以通過雙指縮放操作來縮放頁面律秃。

方案三:CSS touch-action
網(wǎng)上很多文章把這個方案歸結為指針事件爬橡,這令我很疑惑。

以我的理解來看棒动,指針事件的提出并不是為了解決300ms點擊延遲的糙申,而是為了使用一個單獨的事件模型,對鼠標船惨、觸摸柜裸、觸控等多種輸入類型進行統(tǒng)一的處理。也就是說粱锐,移動瀏覽器不用再為不同的輸入設備設計不同的事件疙挺,網(wǎng)頁的開發(fā)者也不用再為不同輸入類型的設備寫不同的事件響應代碼,而是通過統(tǒng)一的指針事件就可以開發(fā)出跨不同輸入類型終端的應用卜范。

跟300ms點擊延遲相關的衔统,是touch-action這個CSS屬性。這個屬性指定了相應元素上能夠觸發(fā)的用戶代理(也就是瀏覽器)的默認行為海雪。如果將該屬性值設置為touch-action: none锦爵,那么表示在該元素上的操作不會觸發(fā)用戶代理的任何默認行為,就無需進行300ms的延遲判斷奥裸。

而設置這個CSS屬性與否险掀,指針事件應該都是可以工作的。所以湾宙,網(wǎng)上的文章令我很疑惑樟氢,希望有大神能給我指示~ 。侠鳄。~

現(xiàn)有的解決方案

要解決300ms點擊延遲的問題埠啃,從長遠來說,自然還是得瀏覽器開發(fā)商提供統(tǒng)一的最終的解決方案伟恶。但是碴开,到目前為止,以上三種方案并不能提供很好的兼容性博秫,對于方案一和方案二潦牛,Chrome是率先支持的,F(xiàn)irefox緊隨其后挡育,然而令Safari頭疼的是巴碗,它除了雙擊縮放還有雙擊滾動操作,如果采用這種兩種方案即寒,那勢必連雙擊滾動也要一起禁用橡淆;對于方案三召噩,IE是支持的,但是其他瀏覽器支持不完善明垢。具體請看這篇文章:移動端Click300毫秒點擊延遲的來龍去脈(轉)蚣常。

所以市咽,在瀏覽器開發(fā)商最終統(tǒng)一的解決方案出來之前痊银,我們還有一些基于Javascript的現(xiàn)成的解決方案可以用。

方案一:指針事件的polyfill
現(xiàn)在除了IE施绎,其他大部分瀏覽器都還不支持指針事件溯革。有一些JS庫,可以讓我們提前使用指針事件谷醉,比如

然而致稀,我們現(xiàn)在關心的不是指針事件,而是與300ms延遲相關的CSS屬性touch-action俱尼。由于除了IE之外的大部分瀏覽器都不支持這個新的CSS屬性抖单,所以這些指針事件的polyfill必須通過某種方式去模擬支持這個屬性。一種方案是JS去請求解析所有的樣式表遇八,另一種方案是將touch-action作為html標簽的屬性矛绘。

方案二:FastClick
FastClickFT Labs 專門為解決移動端瀏覽器 300 毫秒點擊延遲問題所開發(fā)的一個輕量級的庫。FastClick的實現(xiàn)原理是在檢測到touchend事件的時候刃永,會通過DOM自定義事件立即出發(fā)模擬一個click事件货矮,并把瀏覽器在300ms之后的click事件阻止掉。

二斯够、點擊穿透問題

說完移動端點擊300ms延遲的問題囚玫,還不得不提一下移動端點擊穿透的問題《凉妫可能有人會想抓督,既然click點擊有300ms的延遲,那對于觸摸屏束亏,我們直接監(jiān)聽touchstart事件不就好了嗎铃在?
使用touchstart去代替click事件有兩個不好的地方。
第一:touchstart是手指觸摸屏幕就觸發(fā)枪汪,有時候用戶只是想滑動屏幕涌穆,卻觸發(fā)了touchstart事件,這不是我們想要的結果雀久;
第二:使用touchstart事件在某些場景下可能會出現(xiàn)點擊穿透的現(xiàn)象宿稀。

什么是點擊穿透
假如頁面上有兩個元素A和B赖捌。B元素在A元素之上祝沸。我們在B元素的touchstart事件上注冊了一個回調函數(shù)矮烹,該回調函數(shù)的作用是隱藏B元素。我們發(fā)現(xiàn)罩锐,當我們點擊B元素奉狈,B元素被隱藏了,隨后涩惑,A元素觸發(fā)了click事件仁期。

這是因為在移動端瀏覽器,事件執(zhí)行的順序是touchstart > touchend > click竭恬。而click事件有300ms的延遲跛蛋,當touchstart事件把B元素隱藏之后,隔了300ms痊硕,瀏覽器觸發(fā)了click事件赊级,但是此時B元素不見了,所以該事件被派發(fā)到了A元素身上岔绸。如果A元素是一個鏈接理逊,那此時頁面就會意外地跳轉。

參考文章鏈接

移動端Click300毫秒點擊延遲的來龍去脈(轉)
移動端click事件延遲300ms到底是怎么回事盒揉,該如何解決晋被?
詳細解析-移動H5點擊穿透現(xiàn)象

作者:tsyeyuanfeng
鏈接:http://www.reibang.com/p/6e2b68a93c88
來源:簡書
簡書著作權歸作者所有,任何形式的轉載都請聯(lián)系作者獲得授權并注明出處预烙。

最后編輯于
?著作權歸作者所有,轉載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末墨微,一起剝皮案震驚了整個濱河市,隨后出現(xiàn)的幾起案子扁掸,更是在濱河造成了極大的恐慌翘县,老刑警劉巖,帶你破解...
    沈念sama閱讀 217,542評論 6 504
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件谴分,死亡現(xiàn)場離奇詭異锈麸,居然都是意外死亡,警方通過查閱死者的電腦和手機牺蹄,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 92,822評論 3 394
  • 文/潘曉璐 我一進店門忘伞,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人沙兰,你說我怎么就攤上這事氓奈。” “怎么了鼎天?”我有些...
    開封第一講書人閱讀 163,912評論 0 354
  • 文/不壞的土叔 我叫張陵舀奶,是天一觀的道長。 經(jīng)常有香客問我斋射,道長育勺,這世上最難降的妖魔是什么但荤? 我笑而不...
    開封第一講書人閱讀 58,449評論 1 293
  • 正文 為了忘掉前任,我火速辦了婚禮涧至,結果婚禮上腹躁,老公的妹妹穿的比我還像新娘。我一直安慰自己南蓬,他們只是感情好纺非,可當我...
    茶點故事閱讀 67,500評論 6 392
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著蓖康,像睡著了一般铐炫。 火紅的嫁衣襯著肌膚如雪垒手。 梳的紋絲不亂的頭發(fā)上蒜焊,一...
    開封第一講書人閱讀 51,370評論 1 302
  • 那天,我揣著相機與錄音科贬,去河邊找鬼泳梆。 笑死,一個胖子當著我的面吹牛榜掌,可吹牛的內(nèi)容都是我干的陕靠。 我是一名探鬼主播狼犯,決...
    沈念sama閱讀 40,193評論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了弄息?” 一聲冷哼從身側響起,我...
    開封第一講書人閱讀 39,074評論 0 276
  • 序言:老撾萬榮一對情侶失蹤舌界,失蹤者是張志新(化名)和其女友劉穎综芥,沒想到半個月后,有當?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體反砌,經(jīng)...
    沈念sama閱讀 45,505評論 1 314
  • 正文 獨居荒郊野嶺守林人離奇死亡雾鬼,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 37,722評論 3 335
  • 正文 我和宋清朗相戀三年,在試婚紗的時候發(fā)現(xiàn)自己被綠了宴树。 大學時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片策菜。...
    茶點故事閱讀 39,841評論 1 348
  • 序言:一個原本活蹦亂跳的男人離奇死亡,死狀恐怖酒贬,靈堂內(nèi)的尸體忽然破棺而出又憨,到底是詐尸還是另有隱情,我是刑警寧澤锭吨,帶...
    沈念sama閱讀 35,569評論 5 345
  • 正文 年R本政府宣布蠢莺,位于F島的核電站,受9級特大地震影響耐齐,放射性物質發(fā)生泄漏浪秘。R本人自食惡果不足惜蒋情,卻給世界環(huán)境...
    茶點故事閱讀 41,168評論 3 328
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望耸携。 院中可真熱鬧棵癣,春花似錦、人聲如沸夺衍。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,783評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽沟沙。三九已至河劝,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間矛紫,已是汗流浹背赎瞎。 一陣腳步聲響...
    開封第一講書人閱讀 32,918評論 1 269
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留颊咬,地道東北人务甥。 一個月前我還...
    沈念sama閱讀 47,962評論 2 370
  • 正文 我出身青樓,卻偏偏與公主長得像喳篇,于是被迫代替她去往敵國和親敞临。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當晚...
    茶點故事閱讀 44,781評論 2 354

推薦閱讀更多精彩內(nèi)容