您的位置:首页 > 移动开发 > Android开发

[图解]Android View的事件分发机制

2019-05-10 18:52 447 查看
版权声明:本文为博主原创文章,遵循 CC 4.0 by-sa 版权协议,转载请附上原文出处链接和本声明。 本文链接:https://blog.csdn.net/LeeDuoZuiShuai/article/details/90082214

[图解]Android View的事件分发机制


图中箭头蓝色代表事件向下传递的方向
橙色代表事件回传的方向
绿色代表事件的处理方向
黄色代表类的关系
连线代表同一个对象

点击事件的产生和事件序列

分析最普通最常用的一种情况,用户点击手机屏幕,会产生一个ACTION_DOWN事件,代表屏幕被摁下。同时,若手指移动,则会产生ACTION_MOVE事件,代表手指移动。最后,用户手指离开屏幕,产生ACTION_UP事件,代表用户手指离开屏幕。这就是点击事件的产生。由于用户在操作手机时,手指点击后,一定会抬起。所以我们通常用ACTION_DOWN代表一个事件序列的开始,ACTION_UP代表一个事件序列的结束。在DOWN和UP之间,可以存在其他的不同点击事件,而由这一系列点击事件构成的有序事件组,叫做事件序列。

与事件分发有关的方法

1.onTouchEvent()和onTouch()

这两个方法负责对拦截下来的事件进行处理。onTouchEvent()方法来自于View类中我们重写的方法。onTouch()方法来自于我们在View类外部设置的触摸监听器(setOnTouchListener)中的接口onTouchListener中的方法。Android的事件分发的处理存在两套事件处理过程,一个是内部的onTouchEvent()方法,一个是外部的onTouch()方法。且外部的方法优先级高于内部的方法,这样设计的目的是方便开发者在类的外部对事件进行处理,以免类的内部过于臃肿。

2.onInterceptTouchEvent()

该方法负责对父级传递过来的事件进行拦截。若返回true,则拦截。若返回false,则不拦截。

3.dispatchTouchEvent()

该方法负责对事件进行向下分发,内部会调用onInterceptTouchEvent()方法,onTouchEvent()方法和onTouch()方法。若返回true,代表事件由自己处理。若返回false,代表向下分发。

事件分发流程

首先,用户点击屏幕产生点击事件序列,每个点击事件依次向下传递。
最开始会传给Activity。一般情况下,Activity不会对事件进行拦截,而是直接传给最顶级的view。
Activity内部的事件传递过程:最先传给Window类的实现类PhoneWindow类,然后传给DecorView类,最后传给最顶级的View。
最顶级的View一般为ViewGroup(内部有多个View),它首先会调用dispatchTouchEvent()方法对事件进行分发,内部会调用onInterceptTouchEvent()方法对事件进行拦截,若返回false,则不拦截并把事件传给下一层的View。
最后,事件会被传给最底层的View,它不需要对事件进行分发,只需要判断是否处理事件。首先会判断View是否在外部设置了TouchListener,若设置了,则执行接口onTouchListener中的onTouch()方法。若没有设置,则会执行View类中的onTouchEvent()方法。同时,若onTouch()方法的返回值为true,代表事件被消耗,若返回false,代表事件处理失败,onTouch()方法对事件处理失败时会调用onTouchEvent()方法进行处理。若onTouchEvent()方法也无法处理,则返回false。此时,代表当前的View无法处理该点击事件,而由于当前的View为最底层的view,事件无法向下分发,所以只能向上一层回传。若在回传过程中仍没有被处理最后会被传到最顶级的View。然后,最顶级的View将事件交给Activity来处理,通过调用Activity的onTouchEvent()方法来处理,最后完成事件的处理流程。

注意

一个事件序列由DOWN开始,UP结束。若一个View拦截了DOWN事件,则该事件序列中的其他事件都会交给该View来处理,直到事件序列结束。

内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: