Android Touch事件分發機制學習

来源:http://www.cnblogs.com/liunanjava/archive/2016/08/28/5815615.html
-Advertisement-
Play Games

Android 事件分發機制 ViewGroup dispatchTouchEvent 返回true ViewGroup自己在dispatchTouchEvent中消費這個事件 dispatchTouchEvent 返回false 回傳到Activity中onTouchEvent消費事件 dispa ...


Android  事件分發機制

 

ViewGroup

dispatchTouchEvent 返回true

dispatchTouchEvent: Activity    ACTION_DOWN
    MyrelativeLayout  dispatchTouchEvent:   ACTION_DOWN
    dispatchTouchEvent: Activity    ACTION_UP
    MyrelativeLayout  dispatchTouchEvent:   ACTION_UP

ViewGroup自己在dispatchTouchEvent中消費這個事件

dispatchTouchEvent 返回false

  dispatchTouchEvent: Activity    ACTION_DOWN
        MyrelativeLayout  dispatchTouchEvent:   ACTION_DOWN
        onTouchEvent: Activity    ACTION_DOWN
        dispatchTouchEvent: Activity    ACTION_UP
        onTouchEvent: Activity    ACTION_UP

回傳到Activity中onTouchEvent消費事件

 

dispatchTouchEvent 返回 super.dispatchTouchEvent(ev)子View也都返回super

            dispatchTouchEvent: Activity    ACTION_DOWN
        MyrelativeLayout  dispatchTouchEvent:   ACTION_DOW
         MyrelativeLayout onInterceptTouchEvent  ACTION_DO
         MyImageView dispatchTouchEvent:   ACTION_DOWN
          MyImageView     onTouchEvent:   ACTION_DOWN
        MyrelativeLayout: onTouchEvent  ACTION_DOWN
        onTouchEvent: Activity    ACTION_DOWN
        dispatchTouchEvent: Activity    ACTION_UP
        onTouchEvent: Activity    ACTION_UP        

 ViewGroup返回dispatchTouchEvent,會調用ViewGroup中的onInterceptTouchEvent方法,
如果onInterceptTouchEvent返回super.onInterceptTouchEvent(ev)
就迴向下傳到子View
子View中調用dispatchTouchEvent與onTouchEvent方法
如果都返回的是super().再向上傳到ViewGroup,
這時調用ViewGroup的onTouchEvent,如果返回為super,
剛再向上返回給Activity,調用Activity的onTouchEvent消費

 

ViewGroup中的onInterceptTouchEvent返回true,onTouchEvent返回super

    dispatchTouchEvent: Activity    ACTION_DOWN
        MyrelativeLayout  dispatchTouchEvent:   ACTION_DOWN
         MyrelativeLayout onInterceptTouchEvent  ACTION_DOWN
        MyrelativeLayout: onTouchEvent  ACTION_DOWN
        onTouchEvent: Activity    ACTION_DOWN
        dispatchTouchEvent: Activity    ACTION_UP
        onTouchEvent: Activity    ACTION_UP

 事件從Activty的dispatchTouchEvent開始
調用ViewGroup的dispatchTouchEvent,此時這裡返回super
會調用ViewGroup中的onInterceptTouchEvent攔截事件
onInterceptTouchEvent這裡返回true,說明攔截
就會交給ViewGroup的onTouchEvent
onTouchEvent這裡返回Suepr,不消費,就再向上傳給Activity
最後由Activty中的onTouchEvent來消費

 

ViewGroup中的onInterceptTouchEvent返回true,onTouchEvent返回true(和上面相同最後由ViewGroup來消費)

            dispatchTouchEvent: Activity    ACTION_DOWN
        MyrelativeLayout  dispatchTouchEvent:   ACTION_DO
         MyrelativeLayout onInterceptTouchEvent  ACTION_D
        MyrelativeLayout: onTouchEvent  ACTION_DOWN
        dispatchTouchEvent: Activity    ACTION_UP
        MyrelativeLayout  dispatchTouchEvent:   ACTION_UP
        MyrelativeLayout: onTouchEvent  ACTION_UP

 事件從Activty的dispatchTouchEvent開始
調用ViewGroup的dispatchTouchEvent,此時這裡返回super
會調用ViewGroup中的onInterceptTouchEvent攔截事件
onInterceptTouchEvent這裡返回true,說明攔截
就會交給ViewGroup的onTouchEvent
這裡onTouchEvent 返回 true表明,消費,事件到此結束不再傳遞

 

ViewGroup中的onInterceptTouchEvent返回true,onTouchEvent返回false(最後由Activty來消費)

dispatchTouchEvent: Activity    ACTION_DOWN
        MyrelativeLayout  dispatchTouchEvent:   ACTION_DOWN
         MyrelativeLayout onInterceptTouchEvent  ACTION_DOWN
        MyrelativeLayout: onTouchEvent  ACTION_DOWN
        onTouchEvent: Activity    ACTION_DOWN
        dispatchTouchEvent: Activity    ACTION_UP
        onTouchEvent: Activity    ACTION_UP

 

 事件從Activty的dispatchTouchEvent開始
調用ViewGroup的dispatchTouchEvent,此時這裡返回super
會調用ViewGroup中的onInterceptTouchEvent攔截事件
onInterceptTouchEvent這裡返回true,說明攔截
就會交給ViewGroup的onTouchEvent
這裡onTouchEvent 返回 false表明,不消費,
事件會向上傳遞給Activity來調用onTouchEvent來消費

 

ViewGroup中的onInterceptTouchEvent返回super

        dispatchTouchEvent: Activity    ACTION_DOWN
        MyrelativeLayout  dispatchTouchEvent:   ACTION_DOWN
         MyrelativeLayout onInterceptTouchEvent  ACTION_DOWN
         MyImageView dispatchTouchEvent:   ACTION_DOWN
          MyImageView     onTouchEvent:   ACTION_DOWN
        MyrelativeLayout: onTouchEvent  ACTION_DOWN
        onTouchEvent: Activity    ACTION_DOWN
        dispatchTouchEvent: Activity    ACTION_UP
        onTouchEvent: Activity    ACTION_UP

 

 從上到下
Activity dispatchTouchEvent

ViewGroup  dispatchTouchEvent

ViewGroup  onInterceptTouchEvent

子View的 dispatchTouchEvent

子View的 onTouchEvent

ViewGroud的 onTouchEvent
Acitivty 的 onTouchEvent

 

View

子View的dispatchTouchEvent返回false

 

        dispatchTouchEvent: Activity    ACTION_DOWN
        MyrelativeLayout  dispatchTouchEvent:   ACTION_DOWN
         MyrelativeLayout onInterceptTouchEvent  ACTION_DOWN
         MyImageView dispatchTouchEvent:   ACTION_DOWN
        MyrelativeLayout: onTouchEvent  ACTION_DOWN
        onTouchEvent: Activity    ACTION_DOWN
        dispatchTouchEvent: Activity    ACTION_UP
        onTouchEvent: Activity    ACTION_UP

 前提ViewGroup的3個方法都返回super

從上到下
Activity dispatchTouchEvent

ViewGroup  dispatchTouchEvent

ViewGroup  onInterceptTouchEvent

子View dispatchTouchEvent(返回false直接回返到ViewGroup的onTouchEvent方法)
ViewGroup  onTouchEvent

Activity onTouchEvent

子View的dispatchTouchEvent返回true

dispatchTouchEvent: Activity    ACTION_DOWN
        MyrelativeLayout  dispatchTouchEvent:   ACTION_DOWN
         MyrelativeLayout onInterceptTouchEvent  ACTION_DOWN
         MyImageView dispatchTouchEvent:   ACTION_DOWN
        dispatchTouchEvent: Activity    ACTION_UP
        MyrelativeLayout  dispatchTouchEvent:   ACTION_UP
         MyrelativeLayout onInterceptTouchEvent  ACTION_UP
         MyImageView dispatchTouchEvent:   ACTION_UP

 從上到下
Activity dispatchTouchEvent

ViewGroup  dispatchTouchEvent

ViewGroup  onInterceptTouchEvent

子View dispatchTouchEvent(返回true直接消費此事件)

 

子View的 onTouchEvent 返回true

前提
子類的dispatchTouchEvent返回super

        dispatchTouchEvent: Activity    ACTION_DOWN
        MyrelativeLayout  dispatchTouchEvent:   ACTION_DOWN
         MyrelativeLayout onInterceptTouchEvent  ACTION_DOWN
         MyImageView dispatchTouchEvent:   ACTION_DOWN
          MyImageView     onTouchEvent:   ACTION_DOWN
        dispatchTouchEvent: Activity    ACTION_UP
        MyrelativeLayout  dispatchTouchEvent:   ACTION_UP
         MyrelativeLayout onInterceptTouchEvent  ACTION_UP
         MyImageView dispatchTouchEvent:   ACTION_UP
          MyImageView     onTouchEvent:   ACTION_UP

 

 從上到下
Activity dispatchTouchEvent

ViewGroup  dispatchTouchEvent

ViewGroup  onInterceptTouchEvent

子View dispatchTouchEvent(super)

子View的onTouchEvent返回true消費這個事件,不再向上傳遞

子View的 onTouchEvent 返回false

前提
子類的dispatchTouchEvent返回super

        dispatchTouchEvent: Activity    ACTION_DOWN
        MyrelativeLayout  dispatchTouchEvent:   ACTION_DOWN
         MyrelativeLayout onInterceptTouchEvent  ACTION_DOWN
         MyImageView dispatchTouchEvent:   ACTION_DOWN
          MyImageView     onTouchEvent:   ACTION_DOWN
        MyrelativeLayout: onTouchEvent  ACTION_DOWN
        onTouchEvent: Activity    ACTION_DOWN
        dispatchTouchEvent: Activity    ACTION_UP
        onTouchEvent: Activity    ACTION_UP

 

 從上到下
Activity dispatchTouchEvent

ViewGroup  dispatchTouchEvent

ViewGroup  onInterceptTouchEvent

子View dispatchTouchEvent(super)

子View的onTouchEvent返回false

ViewGroud的onTouchEvent

Acitivty的onTouchEvent

 

 

事件分發:dispatchTouchEvent

 

 如果 return true,事件會分發給當前 View 並由 dispatchTouchEvent 方法進行消費,同時事件會停止向下傳遞;
如果 return false,事件分發分為兩種情況:


如果當前 View 獲取的事件直接來自 Activity,則會將事件返回給 Activity 的 onTouchEvent 進行消費;
如果當前 View 獲取的事件來自外層父控制項,則會將事件返回給父 View 的  onTouchEvent 進行消費。
如果返回系統預設的 super.dispatchTouchEvent(ev),事件會自動的分發給當前 View 的 onInterceptTouchEvent 方法。

 

事件攔截:public boolean onInterceptTouchEvent(MotionEvent ev)

 

 在外層 View 的 dispatchTouchEvent(MotionEvent ev) 方法返回系統預設的 super.dispatchTouchEvent(ev) 情況下,事件會自動的分發給當前 View 的 onInterceptTouchEvent 方法。onInterceptTouchEvent 的事件攔截邏輯如下:


如果 onInterceptTouchEvent 返回 true,則表示將事件進行攔截,並將攔截到的事件交由當前 View 的 onTouchEvent 進行處理;
如果 onInterceptTouchEvent 返回 false,則表示將事件放行,當前 View 上的事件會被傳遞到子 View 上,再由子 View 的 dispatchTouchEvent 來開始這個事件的分發;
如果 onInterceptTouchEvent 返回 super.onInterceptTouchEvent(ev),事件預設會被攔截,

如果有子View將事件傳給子View由子View的dispatchTouchEvent來處理
如果沒有子View並將攔截到的事件交由當前 View 的 onTouchEvent 進行處理。

事件響應:public boolean onTouchEvent(MotionEvent ev)

 在 dispatchTouchEvent 返回 super.dispatchTouchEvent(ev) 並且 onInterceptTouchEvent 返回 true 或返回 super.onInterceptTouchEvent(ev) 的情況下 onTouchEvent 會被調用。onTouchEvent 的事件響應邏輯如下:

如果事件傳遞到當前 View 的 onTouchEvent 方法,而該方法返回了 false,那麼這個事件會從當前 View 向上傳遞,並且都是由上層 View 的 onTouchEvent 來接收,如果傳遞到上面的 onTouchEvent 也返回 false,這個事件就會“消失”,而且接收不到下一次事件。
如果返回了 true 則會接收並消費該事件。
如果返回 super.onTouchEvent(ev) 預設處理事件的邏輯和返回 false 時相同

 

源碼

https://github.com/ln0491/AndroidTouchDemo

 


您的分享是我們最大的動力!

-Advertisement-
Play Games
更多相關文章
  • 函數的一些理論知識 1. 函數: 執行一個明確的動作並提供一個返回值的獨立代碼塊。同時函數也是javascript中的一級公民(就是函數和其它變數一樣)。 2.函數的聲明方式: 1> 函數聲明:在函數里,必須手動去聲明函數的返回值,如果返回值沒有申明,則此函數返回值為undefined,,retur ...
  • 我們不要去糾結神馬是內建對象,神馬是內建構造器。到後來你們便會發現其實她們都是對象。 Array()是一個構建數組的內建構造器函數: 與下麵的是等效的: 無論數組是以神馬方式創建的,我們都可以照常向裡面添加元素。 當我們使用構造器函數Array()創建數組時,也可以通過傳值的方式為其添加元素: 如果 ...
  • 除了使用new操作符調用構造函數以外,我們也可以拋開new操作符,只用一般函數來創建對象,這樣就能執行某些預備工作,並已對象為返回值的函數。、 然後我們調用her()來生成對象: 實際上構造函數也是可以返回對象的,只不過this的值使用上將會有所不同。 在這裡,構造其函數不是返回包含屬性name的t ...
  • 我們可以通過構造器函數(簡稱構造函數)來創建對象: 為了使用該函數來創建對象,我們需要使用new操作符,例如: 使用構造函數創建對象的好處就是她可以接受一些參數,下麵我們就來修改一下上面的例子: 現在,我們就能利用同一個構造函數創建不同的對象了: 按照慣例,我們應該將構造函數的首字母大寫,以便區分一 ...
  • 版權聲明:作者原創,轉載請註明出處! 編寫插件的兩種方式: 1.類級別開發插件(1%) 2.對象級別開發(99%) 類級別的靜態開發就是給jquery添加靜態方法,三種方式 1.添加新的全局函數 2.使用$.extend(obj) 3.使用命名空間 類級別開發插件(用的非常少,1%) 分別舉例: 調 ...
  • 或者 ...
  • 本篇主要探討的是iOS應用中各種狀態的躍遷過程,建議大家通過修改AppDelegate.swift,在每個過程中添加日誌輸出代碼,從而觀察其變化。 ...
  • 一、PackageManager的resolveActivity 返回能夠匹配的Intent,如果不能匹配就返回NULL, 二、PackageManager的queryIntentActivities 返回所有成功匹配的Activity信息 三、Intent的resolveActivity 第一個參 ...
一周排行
    -Advertisement-
    Play Games
  • 移動開發(一):使用.NET MAUI開發第一個安卓APP 對於工作多年的C#程式員來說,近來想嘗試開發一款安卓APP,考慮了很久最終選擇使用.NET MAUI這個微軟官方的框架來嘗試體驗開發安卓APP,畢竟是使用Visual Studio開發工具,使用起來也比較的順手,結合微軟官方的教程進行了安卓 ...
  • 前言 QuestPDF 是一個開源 .NET 庫,用於生成 PDF 文檔。使用了C# Fluent API方式可簡化開發、減少錯誤並提高工作效率。利用它可以輕鬆生成 PDF 報告、發票、導出文件等。 項目介紹 QuestPDF 是一個革命性的開源 .NET 庫,它徹底改變了我們生成 PDF 文檔的方 ...
  • 項目地址 項目後端地址: https://github.com/ZyPLJ/ZYTteeHole 項目前端頁面地址: ZyPLJ/TreeHoleVue (github.com) https://github.com/ZyPLJ/TreeHoleVue 目前項目測試訪問地址: http://tree ...
  • 話不多說,直接開乾 一.下載 1.官方鏈接下載: https://www.microsoft.com/zh-cn/sql-server/sql-server-downloads 2.在下載目錄中找到下麵這個小的安裝包 SQL2022-SSEI-Dev.exe,運行開始下載SQL server; 二. ...
  • 前言 隨著物聯網(IoT)技術的迅猛發展,MQTT(消息隊列遙測傳輸)協議憑藉其輕量級和高效性,已成為眾多物聯網應用的首選通信標準。 MQTTnet 作為一個高性能的 .NET 開源庫,為 .NET 平臺上的 MQTT 客戶端與伺服器開發提供了強大的支持。 本文將全面介紹 MQTTnet 的核心功能 ...
  • Serilog支持多種接收器用於日誌存儲,增強器用於添加屬性,LogContext管理動態屬性,支持多種輸出格式包括純文本、JSON及ExpressionTemplate。還提供了自定義格式化選項,適用於不同需求。 ...
  • 目錄簡介獲取 HTML 文檔解析 HTML 文檔測試參考文章 簡介 動態內容網站使用 JavaScript 腳本動態檢索和渲染數據,爬取信息時需要模擬瀏覽器行為,否則獲取到的源碼基本是空的。 本文使用的爬取步驟如下: 使用 Selenium 獲取渲染後的 HTML 文檔 使用 HtmlAgility ...
  • 1.前言 什麼是熱更新 游戲或者軟體更新時,無需重新下載客戶端進行安裝,而是在應用程式啟動的情況下,在內部進行資源或者代碼更新 Unity目前常用熱更新解決方案 HybridCLR,Xlua,ILRuntime等 Unity目前常用資源管理解決方案 AssetBundles,Addressable, ...
  • 本文章主要是在C# ASP.NET Core Web API框架實現向手機發送驗證碼簡訊功能。這裡我選擇是一個互億無線簡訊驗證碼平臺,其實像阿裡雲,騰訊雲上面也可以。 首先我們先去 互億無線 https://www.ihuyi.com/api/sms.html 去註冊一個賬號 註冊完成賬號後,它會送 ...
  • 通過以下方式可以高效,並保證數據同步的可靠性 1.API設計 使用RESTful設計,確保API端點明確,並使用適當的HTTP方法(如POST用於創建,PUT用於更新)。 設計清晰的請求和響應模型,以確保客戶端能夠理解預期格式。 2.數據驗證 在伺服器端進行嚴格的數據驗證,確保接收到的數據符合預期格 ...