Android手勢---GestureDetector


GestureDetector 可以使用 MotionEvents 檢測各種手勢和事件突想。

這個類只能用于檢測觸摸事件的 MotionEvent


GestureDetector有三個內(nèi)部接口鲁驶,兩個內(nèi)部類

三個核心接口

  • OnGestureListener

  • OnDoubleTapListener

  • OnContextClickListener

他們都是起到監(jiān)聽器的作用

兩個內(nèi)部類:

  • SimpleOnGestureListener

注意:SimpleOnGestureListener繼承了GestureDetector的三個內(nèi)部接口

  • GestureHandler
    處理GestureDetector類的數(shù)據(jù)

構(gòu)造方法

GestureDetector自帶了五個構(gòu)造方法,但是有兩個被廢棄了

public GestureDetector(Context context, OnGestureListener listener) 
public GestureDetector(Context context, OnGestureListener listener, Handler handler) 
public GestureDetector(Context context, OnGestureListener listener, Handler handler, boolean unused){this(context, listener, handler);} 

因為第三個調(diào)用第二個草描,所以只要關(guān)注前面兩個就行了

我們發(fā)現(xiàn)第二個構(gòu)造方法中多了一個Handler變量
一般來說,不會使用這個構(gòu)造方法

但是因為GestureDetector中的數(shù)據(jù)是給GestureHandler內(nèi)部類進行處理庸蔼,這個類會使用Handle糙臼,由Handler的知識知道,創(chuàng)建Handler必須有Looper禾怠,但是在一些新開的線程中沒有創(chuàng)建Looper,所以我們需要傳入一個帶了Looper的Handler變量贝搁,否則吗氏,GestureDetector對象會創(chuàng)建失敗

SimpleOnGestureListener類的方法:

//下面的6個方法繼承自OnGestureListener
public boolean onSingleTapUp( MotionEvent e)
當用戶單擊時觸發(fā)

public void onLongPress (MotionEvent e )
當用戶手指在長按屏幕時觸發(fā)

public boolean onScroll (MotionEvent e1 , MotionEvent e2 ,float distanceX , float distanceY)
當用戶手指在屏幕上拖動時觸發(fā)
后面兩個變量時在X,Y上移動的距離

public boolean onFling ( MotionEvent e1 ,MotionEvent e2 , float velocityX , float velocityY)
當用戶手指拖動后,手指離開屏幕時觸發(fā)
這個方法常用來使手指離開后頁面仍然可以滑動(速度慢慢變欣啄妗)
后兩個變量表示手指在X,Y兩個方向上的速度

public void onShowPress (MotionEvent  e)
當用戶手指按下弦讽,但沒有移動時觸發(fā)該方法

public boolean onDown ( MotionEvent e)  
當按下時觸發(fā)該方法,所有手勢第一個必定觸發(fā)該方法

//下面的三個方法繼承自OnDoubleTapListener
public boolean onDoubleTap (MotionEvent e)
當用戶雙擊時觸發(fā)

public boolean onDoubleTapEvent (MotionEvent e)
在雙擊事件確定發(fā)生時會對第二次按下產(chǎn)生的 MotionEvent 信息進行回調(diào)膀哲。

public boolean onSingleTapConfirmed ( MotionEvent e)
當單擊事件確定后進行回調(diào)

//下面的這個方法繼承自ContextClickListener
onContextClick ( MotionEvent e)
用于檢測外部設備上的按鈕是否按下的往产,例如藍牙觸控筆上的按鈕,一般情況下某宪,忽略即可仿村。

如果偵聽 onContextClick(MotionEvent),
則必須在 View 的onGenericMotionEvent(MotionEvent)中
調(diào)用 GestureDetector OnGenericMotionEvent(MotionEvent)兴喂。

手勢的常用事件

按下

public boolean onDown (MotionEvent e)

按下是所以手勢必定有的動作
所以無論什么手勢蔼囊,第一個調(diào)用的方法就是onDown

注意:
GestureDetector的點擊對圖片焚志,按鈕等無用

為了解決這個問題,我們可以

  • onDown返回true(根據(jù)響應中的先回調(diào)畏鼓,后監(jiān)聽)
  • 圖片等的xml文件中設置android:Clickable="true"

單擊:

public boolean onSingleTapUp( MotionEvent e)

public boolean onSingleTapConfirmed ( MotionEvent e)

這兩個方法都可以響應到單擊事件酱酬,但是他們之間還是有區(qū)別的

當我們同時在監(jiān)聽器中覆寫這兩個方法,并且進行單擊事件
我們會發(fā)現(xiàn)當進行單擊事件的時候云矫,這幾個方法響應的順序是這樣的

onDown() -> onSingleTapUp() -> onSingleCofirmed()

首先onDown()必定是第一個執(zhí)行的膳沽,但是會發(fā)現(xiàn)onSingleTapUp在onSingleComfirmed之前執(zhí)行
我查閱了相關(guān)文檔,發(fā)現(xiàn)他們雖然同樣響應的是當手指離開屏幕的活動让禀,但是onSingleTapUp是立即執(zhí)行挑社,而onSingleComfirmed卻要在離開后300ms后才執(zhí)行 ,這樣的目的是確認我們進行的是單擊事件(為了防止我們在300ms內(nèi)再次進行單擊事件)堆缘,所以他們的名字分別是Up和Comfirmed

所以滔灶,在設置雙擊事件時,最好使用onSingleComfirmed()吼肥,進行雙擊時不會回調(diào)單擊方法

雙擊

public boolean onDoubleTap (MotionEvent e)

public boolean onDoubleTapEvent (MotionEvent e)

這兩個方法都可以響應雙擊事件录平,為了驗證他們的區(qū)別,我們同樣在一個響應器中覆寫這兩個方法缀皱,并且進行雙擊事件(我們這里單擊事件使用onSingleComfirmed)

我們使用Log.e()把方法響應的順序弄出來斗这,發(fā)現(xiàn)他們規(guī)律很神奇

onDown() -> onDoubleTap() -> onDoubleTapEvent() -> onDown()-> onDoubleTapEvent() ->onDoubleTapEvent()(不定數(shù)目個)

然后我在onDoubleTapEvent()中吧MotionEvent e 輸出,
然后方法響應的順序變成:

onDown() -> onDoubleTap() -> onDoubleTapEvent() -> onDown()-> onDoubleTapEvent() Down -> onDoubleTapEvent()Move(不定數(shù)目個) ->onDoubleTapEvent() Up

我們對以上信息進行分析:
DoubleTap在DoubleTapEvent前面執(zhí)行,但是根據(jù)DoubleTapEvent的第一個MotionEvent是Down啤斗,所以判斷雙擊的響應條件是在第一次單擊后的300ms內(nèi)按下手指

我們又嘗試在雙擊后手指不離開屏幕表箭,可見隨時間的延長,Move也變得更多钮莲,
由此判斷免钻,onDoubleTapEvent是實時回調(diào)的,并且是用來檢測MotionEvent

長按

public void onShowPress (MotionEvent e)

public void onLongPress (MotionEvent e)

這次我們在響應器中覆寫所有方法崔拥,進行長按操作
發(fā)現(xiàn)方法響應的順序為:

onDown -> onShowPress -> onLongPress

也就是說极舔,在長按時,onShowPress在onLongPress前面執(zhí)行

滑動/拖動

public void onScroll (MotionEvent e)

public void onFling (MotionEvent e)

同樣链瓦,我們覆寫所有方法拆魏,進行滑動操作,
發(fā)現(xiàn)方法的響應順序為

onDown -> onScroll -> 不定量個onScroll ->onScroll -> onFiling

由此可見,在滑動/拖動過程中慈俯,不斷調(diào)用onScroll渤刃,最后調(diào)用onFiling

當然,Android自帶的手勢不能完全滿足我們的需求贴膘,于是Android提供了自建手勢的方法卖子,這些內(nèi)容將在下一篇博客中陳述

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個濱河市刑峡,隨后出現(xiàn)的幾起案子揪胃,更是在濱河造成了極大的恐慌璃哟,老刑警劉巖,帶你破解...
    沈念sama閱讀 211,348評論 6 491
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件喊递,死亡現(xiàn)場離奇詭異随闪,居然都是意外死亡,警方通過查閱死者的電腦和手機骚勘,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 90,122評論 2 385
  • 文/潘曉璐 我一進店門铐伴,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人俏讹,你說我怎么就攤上這事当宴。” “怎么了泽疆?”我有些...
    開封第一講書人閱讀 156,936評論 0 347
  • 文/不壞的土叔 我叫張陵户矢,是天一觀的道長。 經(jīng)常有香客問我殉疼,道長梯浪,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 56,427評論 1 283
  • 正文 為了忘掉前任瓢娜,我火速辦了婚禮挂洛,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘眠砾。我一直安慰自己虏劲,他們只是感情好,可當我...
    茶點故事閱讀 65,467評論 6 385
  • 文/花漫 我一把揭開白布褒颈。 她就那樣靜靜地躺著柒巫,像睡著了一般。 火紅的嫁衣襯著肌膚如雪谷丸。 梳的紋絲不亂的頭發(fā)上堡掏,一...
    開封第一講書人閱讀 49,785評論 1 290
  • 那天,我揣著相機與錄音淤井,去河邊找鬼布疼。 笑死摊趾,一個胖子當著我的面吹牛币狠,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播砾层,決...
    沈念sama閱讀 38,931評論 3 406
  • 文/蒼蘭香墨 我猛地睜開眼漩绵,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了肛炮?” 一聲冷哼從身側(cè)響起止吐,我...
    開封第一講書人閱讀 37,696評論 0 266
  • 序言:老撾萬榮一對情侶失蹤宝踪,失蹤者是張志新(化名)和其女友劉穎,沒想到半個月后碍扔,有當?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體瘩燥,經(jīng)...
    沈念sama閱讀 44,141評論 1 303
  • 正文 獨居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 36,483評論 2 327
  • 正文 我和宋清朗相戀三年不同,在試婚紗的時候發(fā)現(xiàn)自己被綠了厉膀。 大學時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點故事閱讀 38,625評論 1 340
  • 序言:一個原本活蹦亂跳的男人離奇死亡二拐,死狀恐怖服鹅,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情百新,我是刑警寧澤企软,帶...
    沈念sama閱讀 34,291評論 4 329
  • 正文 年R本政府宣布,位于F島的核電站饭望,受9級特大地震影響仗哨,放射性物質(zhì)發(fā)生泄漏。R本人自食惡果不足惜杰妓,卻給世界環(huán)境...
    茶點故事閱讀 39,892評論 3 312
  • 文/蒙蒙 一藻治、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧巷挥,春花似錦桩卵、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,741評論 0 21
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至高职,卻和暖如春钩乍,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背怔锌。 一陣腳步聲響...
    開封第一講書人閱讀 31,977評論 1 265
  • 我被黑心中介騙來泰國打工寥粹, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留,地道東北人埃元。 一個月前我還...
    沈念sama閱讀 46,324評論 2 360
  • 正文 我出身青樓涝涤,卻偏偏與公主長得像,于是被迫代替她去往敵國和親岛杀。 傳聞我的和親對象是個殘疾皇子阔拳,可洞房花燭夜當晚...
    茶點故事閱讀 43,492評論 2 348

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