Android事件的分发和消费机制

Android 中与 Touch 事件相关的方法包括:dispatchTouchEvent(MotionEvent ev)onInterceptTouchEvent(MotionEvent ev)onTouchEvent(MotionEvent ev);可以响应这些方法的控件包括:ViewGroupViewActivity。方法与控件的对应关系以下表所示:
测试

Touch 事件相关方法   方法功能 
  ViewGroup   
       View       
     Activity     
  public boolean dispatchTouchEvent(MotionEvent ev) 事件分发 
 Yes  Yes  Yes
  public boolean onInterceptTouchEvent(MotionEvent ev) 
事件拦截 
 Yes  Yes  No
  public boolean onTouchEvent(MotionEvent ev) 事件响应 
 Yes  Yes  Yes

从这张表中咱们能够看到 ViewGroup 和 View 对与 Touch 事件相关的三个方法均能响应,而 Activity 对 onInterceptTouchEvent(MotionEvent ev) 也就是事件拦截不进行响应。另外须要注意的是 View 对 dispatchTouchEvent(MotionEvent ev) 和 onInterceptTouchEvent(MotionEvent ev) 的响应的前提是能够向该 View 中添加子 View,若是当前的 View 已是一个最小的单元 View(好比 TextView),那么就没法向这个最小 View 中添加子 View,也就没法向子 View 进行事件的分发和拦截,因此它没有dispatchTouchEvent(MotionEvent ev) 和 onInterceptTouchEvent(MotionEvent ev),只有 onTouchEvent(MotionEvent ev) spa

1、Touch 事件分析 事件

▐ 事件分发:public boolean dispatchTouchEvent(MotionEvent ev) it

Touch 事件发生时 Activity 的 dispatchTouchEvent(MotionEvent ev) 方法会以隧道方式(从根元素依次往下传递直到最内层子元素或在中间某一元素中因为某一条件中止传递)将事件传递给最外层 View 的 dispatchTouchEvent(MotionEvent ev) 方法,并由该 View 的 dispatchTouchEvent(MotionEvent ev) 方法对事件进行分发。dispatchTouchEvent 的事件分发逻辑以下: io

  • 若是 return true,事件会分发给当前 View 并由 dispatchTouchEvent 方法进行消费,同时事件会中止向下传递;
  • 若是 return false,事件分发分为两种状况:
  1. 若是当前 View 获取的事件直接来自 Activity,则会将事件返回给 Activity 的 onTouchEvent 进行消费;
  2. 若是当前 View 获取的事件来自外层父控件,则会将事件返回给父 View 的  onTouchEvent 进行消费。
  • 若是返回系统默认的 super.dispatchTouchEvent(ev),事件会自动的分发给当前 View 的 onInterceptTouchEvent 方法。

▐ 事件拦截:public boolean onInterceptTouchEvent(MotionEvent ev) 
table

外层 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 的 onTouchEvent 进行处理。

▐ 事件响应:public boolean onTouchEvent(MotionEvent ev) margin

在 dispatchTouchEvent 返回 super.dispatchTouchEvent(ev) 而且 onInterceptTouchEvent 返回 true 或返回 super.onInterceptTouchEvent(ev) 的状况下 onTouchEvent 会被调用。onTouchEvent 的事件响应逻辑以下: tab

  • 若是事件传递到当前 View 的 onTouchEvent 方法,而该方法返回了 false,那么这个事件会从当前 View 向上传递,而且都是由上层 View 的 onTouchEvent 来接收,若是传递到上面的 onTouchEvent 也返回 false,这个事件就会“消失”,并且接收不到下一次事件。
  • 若是返回了 true 则会接收并消费该事件。
  • 若是返回 super.onTouchEvent(ev) 默认处理事件的逻辑和返回 false 时相同。

到这里,与 Touch 事件相关的三个方法就分析完毕了。下面的内容会经过各类不一样的的测试案例来验证上文中三个方法对事件的处理逻辑。 di

相关文章
相关标签/搜索