Android中父View和子view的點擊事件的執行過程

Android中的事件類型分爲按鍵事件和屏幕觸摸事件,Touch事件是屏幕觸摸事件的基礎事件,有必要對它進行深刻的瞭解。 
一個最簡單的屏幕觸摸動做觸發了一系列Touch事件:ACTION_DOWN->ACTION_MOVE->ACTION_MOVE->ACTION_MOVE...->ACTION_MOVE->ACTION_UP

當屏幕中包含一個ViewGroup,而這個ViewGroup又包含一個子view,這個時候android系統如何處理Touch事件呢?究竟是
ViewGroup來處理Touch事件,仍是子view來處理Touch事件呢?我只能很確定的對你說不必定。呵呵,爲何呢?看看下面個人調查結果你
就明白了。

android系統中的每一個View的子類都具備下面三個和TouchEvent處理密切相關的方法:

1)public boolean dispatchTouchEvent(MotionEvent ev)   這個方法用來分發TouchEvent
html

2)public boolean onInterceptTouchEvent(MotionEvent ev) 這個方法用來攔截TouchEvent
3)public boolean onTouchEvent(MotionEvent ev)      這個方法用來處理TouchEvent

當TouchEvent發生時,首先Activity將TouchEvent傳遞給最頂層的View, 
TouchEvent最早到達最頂層 view的 dispatchTouchEvent,而後由  dispatchTouchEvent方法進行分發,
android

若是dispatchTouchEvent返回true,則交給這個view的onTouchEvent處理,app

若是 dispatchTouchEvent返回 false,則交給這個 view的 interceptTouchEvent方法來決定是否要攔截這個事件,
若是 interceptTouchEvent返回 true,也就是攔截掉了,則交給它的onTouchEvent來處理,
若是 interceptTouchEvent返回 false,那麼就傳遞給子 view,由子 view 的dispatchTouchEvent再來開始這個事件的分發。
函數

若是事件傳遞到某一層的子 view的 onTouchEvent上了,這個方法返回了 false,那麼這個事件會從這個 view往上傳遞,都是onTouchEvent來接收。
若是事件傳遞到某一層的子view的onTouchEvent上了,這個方法返回false,那麼這個事件將不會向上傳遞了,又這個view攔截處理.
而若是傳遞到最上面的 onTouchEvent也返回 false的話,這個事件就會「消失」,並且接收不到下一次事件
佈局

onInterceptTouchEvent()用於處理事件並改變事件的傳遞方向。處理事件這個不用說了,你在函數內部編寫代碼處理就能夠了。而決定傳遞方向的是返回值,返回爲false時事件會傳遞給子控件的onInterceptTouchEvent();返回值爲true時事件會傳遞給當前控件的onTouchEvent(),而不在傳遞給子控件,這就是所謂的Intercept(截斷)。this

onTouchEvent() 用於處理事件,返回值決定當前控件是否消費(consume)了這個事件。可能你要問是否消費了又區別嗎,反正我已經針對事件編寫了處理代碼?答案是有區別!好比ACTION_MOVE或者ACTION_UP發生的前提是必定曾經發生了ACTION_DOWN,若是你沒有消費ACTION_DOWN,那麼系統會認爲ACTION_DOWN沒有發生過,因此ACTION_MOVE或者ACTION_UP就不能被捕獲。spa

本文源地址:http://www.cnblogs.com/rocky_yi/archive/2011/01/21/1941522.html# ,轉載請註明出處!rest

複製代碼

<?xml version="1.0" encoding="utf-8"?>
<com.touchstudy.LayoutView1 xmlns:android="http://schemas.android.com/apk/res/android"
    android:orientation
="vertical"
    android:layout_width
="fill_parent"
    android:layout_height
="fill_parent" >
    
<com.touchstudy.LayoutView2
        
android:orientation="vertical"
        android:layout_width
="fill_parent"
        android:layout_height
="fill_parent"
        android:gravity
="center">
       
<com.touchstudy.MyTextView 
            
android:layout_width="wrap_content"
            android:layout_height
="wrap_content"
            android:id
="@+id/tv"
            android:text
="AB"
            android:textSize
="40sp"
            android:textStyle
="bold"
            android:background
="#FFFFFF"
            android:textColor
="#0000FF"/>
   
</com.touchstudy.LayoutView2>
</com.touchstudy.LayoutView1>
orm

複製代碼

 

 

在沒有重寫onInterceptTouchEvent()和onTouchEvent()的狀況下(他們的返回值都是false), 對上面這個佈局,MotionEvent事件的傳遞順序以下:xml

 

當某個控件的onInterceptTouchEvent()返回值爲true時,就會發生截斷,事件被傳到當前控件的onTouchEvent()。如咱們將LayoutView2的onInterceptTouchEvent()返回值爲true,則傳遞流程變成:

 

 若是咱們同時將LayoutView2的onInterceptTouchEvent()和onTouchEvent()設置成true,那麼LayoutView2將消費被傳遞的事件,同時後續事件(如跟着ACTION_DOWN的ACTION_MOVE或者ACTION_UP)會直接傳給LayoutView2的onTouchEvent(),不傳給其餘任何控件的任何函數。同時傳遞給子空間一個ACTION_CANCEL事件。傳遞流程變成(圖中沒有畫出ACTION_CANCEL事件):

          

附SDK給出的說明:

·  You will receive the down event here.

·  The down event will be handled either by a child of this view group, or given to your own onTouchEvent() method to handle; this means you should implement onTouchEvent() to return true, so you will continue to see the rest of the gesture (instead of looking for a parent view to handle it). Also, by returning true from onTouchEvent(), you will not receive any following events in onInterceptTouchEvent() and all touch processing must happen in onTouchEvent() like normal.

·  For as long as you return false from this function, each following event (up to and including the final up) will be delivered first here and then to the target's onTouchEvent().

·  If you return true from here, you will not receive any following events: the target view will receive the same event but with the action ACTION_CANCEL, and all further events will be delivered to your onTouchEvent() method and no longer appear here.

相關文章
相關標籤/搜索