Android中的事件分发总结
2017-05-10 14:06
337 查看
Android中的事件分发机制测试:
对于布局:
其布局为
<RelativeLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context="com.example.test_event_dispatch_oninterccept_ontouch.MainActivity">
<com.example.test_event_dispatch_oninterccept_ontouch.ViewgroupFather
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="@android:color/holo_blue_light"
>
<com.example.test_event_dispatch_oninterccept_ontouch.ViewGroupChild
android:layout_width="200dp"
android:layout_height="200dp"
android:background="@android:color/holo_red_light"
>
<com.example.test_event_dispatch_oninterccept_ontouch.MyTextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_vertical"
android:text="事件分发测试"
android:background="@android:color/holo_orange_dark">
</com.example.test_event_dispatch_oninterccept_ontouch.MyTextView>
</com.example.test_event_dispatch_oninterccept_ontouch.ViewGroupChild>
</com.example.test_event_dispatch_oninterccept_ontouch.ViewgroupFather>
</RelativeLayout>
测试一:
控件名称 dispatch intercept touch
Ativity super super
Father super super super
Child super super super
MyTextView super super
测试结果:
总结:
当dispatch返回值为super的时候:
当dispatch返回值为super时,则自动将事件分发给当前view的intercept方法,以确定是否拦截事件;如果该dispatch所在的控件为最小单元时,则将事件传递给touch;如果该dispatch所在为Activity时,则将事件分发其下最外层布局,由该布局进行事件分发。
当dispatch返回值为true的时候:
事件将会在当前View的dispatch方法中被消费,不在向下级传递。
当dispatch返回值为false的时候:
如果该dispatch方法接收的事件是由外层容器(父级容器)传进来的,则将该事件交给外层容器的touch方法处理。
如果该dispatch方法在Acticity中,则直接由activity中的touch方法消费该事件。
当intercept返回值为super的时候:
事件将不会被拦截,而且经过该intercept方法传递到子View或子ViewGroup的dispatch方法上,与该dispatch方法进行事件分发。
当intercept返回值为true的时候:
事件将被拦截,而后交由当前ViewGroup的touch事件进行消费。
当intercept返回值为false的时候:
事件将不会被拦截,而且该事件将由该方法传递给子view或子Viewgroup的dispatch方法从新分发。
当touch返回值为super的时候:
事件将会由该touch所在容器向父级容器的touch传递,若父级容器也返回super或者false,则继续向父级容器传递直至传递到Acticity的touch方法中。
当touch返回值为true的时候:
事件将在该touch方法中被消费。
当touch返回值为false的时候:
与返回super相同。
事件分发调用的方法可以分为两步
第一步为试探性分发,例如上面的demo,假如在child的dispatch中返回true,则其分发可以理解为:从acticity试探性的将事件正常分发到father,从father正常分发到child中的dispatch中,发现dispatch返回值为true;
则Android事件分发机制可以确定事件分发到此处为止,于是开始正式分发事件,从activity的dispatch开始,逐级分发一直分发到child的dispatch方法中。
对于touch方法而言,如果在试探性事件分发中,事件没有被消费掉,则会逐级向父级touch方法传递,直至传递到acticity的touch方法为止,此时,事件分发机制认为,该事件将会由acticity的touch事件消费,于是,直接将事件分发给acticity的touch方法,
4000
则会出现以下结果:
举例:
测试二:
控件名称 dispatch intercept touch
Ativity super super
Father super super super
Child super super
true
MyTextView super super
结果:
结果解释:
当点击事件发生后,activity的dispatch方法将开始分发事件,由于该方法的返回值是super,所以原本应该会被传到当前dispatch所在位置的intercept方法中进行判断是否拦截,但是由于当前dispatch所在的位置是acticity,没有intercepter方法,所以,默认事件向下级传递。其过程:(MainActicity的dispatchTouchEvent—>Father的dispatchTouchEvent),该过程后,于是事件从acticity中被传递到了father的dispatch方法中。由于father的dispatch方法的返回值也是super。则事件被传递到intercepter中判断是否需要拦截,而该intercepter的返回值也是super,默认表示不拦截,于是,事件将继续想下级传递。其过程:(Father的dispatchTouchEvent—>Father的onInterceptTouchEvent—>Child的dispatchTouchEvent),该过程后,事件被传递到了Child的dispatchTouchEvent中,由于Child的dispatchTouchEvent方法返回值也是super,则该事件被交由Child的onInterceptTouchEvent方法判断是否拦截,该方法返回值依旧为super,表示不拦截,则事假继续想下级传递到MyTextView的dispatchTouchEvent方法中,其过程:(Child的dispatchTouchEvent—>Child的onInterceptTouchEvent—>MyTextView的dispatchTouchEvent),该过程后,事件被传递到了MyTextView的dispatchTouchEvent中,由于MyTextView的dispatchTouchEvent返回值是super,原本该将该事件分发该onInterceptTouchEvent方法进行判断是否拦截,但是由于MyTextView已经是最小单元,不在有下级,于是该事件被分发给了最小单元的onTouchEvent方法。由于MyTextView的onTouchEvent方法返回值为super,表示向上级传递,则该事件由当前onTouchEvent方法传递给了父级Child的onTouchEvent方法,其过程:(MyTextView的dispatchTouchEvent—>MyTextView的onTouchEvent—>Child的onTouchEvent),该过程后,事件被传递到了Child的onTouchEvent方法中,由于该方法的返回值为true,表示事件在此方法中被消费掉,于是,整个试探性事件分发完成。事件的试探性分发完成之后,将进行事件分发,采用的是事件的逐级分发,事件由Activity的dispatchTouchEvent方法开始分发到Father的dispatchTouchEvent,由于Child不在当前级,则在Father层使用onInterceptTouchEvent来判断事件是否拦截,确认不拦截后,事件从Father的onInterceptTouchEvent下发到Child的dispatchTouchEvent中,由于Child中的onTouchEvent方法就在当前层,不用再判是否进行事件拦截,于是,Child的dispatchTouchEvent方法直接将事件发给Child的onTouchEvent方法,其过程:(Activity的dispatchTouchEvent—>Father的dispatchTouchEvent—>Father的onInterceptTouchEvent—>Child的dispatchTouchEvent—>Child的onTouchEvent)至此,整个事件分发结束。
对于布局:
其布局为
<RelativeLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context="com.example.test_event_dispatch_oninterccept_ontouch.MainActivity">
<com.example.test_event_dispatch_oninterccept_ontouch.ViewgroupFather
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="@android:color/holo_blue_light"
>
<com.example.test_event_dispatch_oninterccept_ontouch.ViewGroupChild
android:layout_width="200dp"
android:layout_height="200dp"
android:background="@android:color/holo_red_light"
>
<com.example.test_event_dispatch_oninterccept_ontouch.MyTextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_vertical"
android:text="事件分发测试"
android:background="@android:color/holo_orange_dark">
</com.example.test_event_dispatch_oninterccept_ontouch.MyTextView>
</com.example.test_event_dispatch_oninterccept_ontouch.ViewGroupChild>
</com.example.test_event_dispatch_oninterccept_ontouch.ViewgroupFather>
</RelativeLayout>
测试一:
控件名称 dispatch intercept touch
Ativity super super
Father super super super
Child super super super
MyTextView super super
测试结果:
总结:
当dispatch返回值为super的时候:
当dispatch返回值为super时,则自动将事件分发给当前view的intercept方法,以确定是否拦截事件;如果该dispatch所在的控件为最小单元时,则将事件传递给touch;如果该dispatch所在为Activity时,则将事件分发其下最外层布局,由该布局进行事件分发。
当dispatch返回值为true的时候:
事件将会在当前View的dispatch方法中被消费,不在向下级传递。
当dispatch返回值为false的时候:
如果该dispatch方法接收的事件是由外层容器(父级容器)传进来的,则将该事件交给外层容器的touch方法处理。
如果该dispatch方法在Acticity中,则直接由activity中的touch方法消费该事件。
当intercept返回值为super的时候:
事件将不会被拦截,而且经过该intercept方法传递到子View或子ViewGroup的dispatch方法上,与该dispatch方法进行事件分发。
当intercept返回值为true的时候:
事件将被拦截,而后交由当前ViewGroup的touch事件进行消费。
当intercept返回值为false的时候:
事件将不会被拦截,而且该事件将由该方法传递给子view或子Viewgroup的dispatch方法从新分发。
当touch返回值为super的时候:
事件将会由该touch所在容器向父级容器的touch传递,若父级容器也返回super或者false,则继续向父级容器传递直至传递到Acticity的touch方法中。
当touch返回值为true的时候:
事件将在该touch方法中被消费。
当touch返回值为false的时候:
与返回super相同。
事件分发调用的方法可以分为两步
第一步为试探性分发,例如上面的demo,假如在child的dispatch中返回true,则其分发可以理解为:从acticity试探性的将事件正常分发到father,从father正常分发到child中的dispatch中,发现dispatch返回值为true;
则Android事件分发机制可以确定事件分发到此处为止,于是开始正式分发事件,从activity的dispatch开始,逐级分发一直分发到child的dispatch方法中。
对于touch方法而言,如果在试探性事件分发中,事件没有被消费掉,则会逐级向父级touch方法传递,直至传递到acticity的touch方法为止,此时,事件分发机制认为,该事件将会由acticity的touch事件消费,于是,直接将事件分发给acticity的touch方法,
4000
则会出现以下结果:
举例:
测试二:
控件名称 dispatch intercept touch
Ativity super super
Father super super super
Child super super
true
MyTextView super super
结果:
结果解释:
当点击事件发生后,activity的dispatch方法将开始分发事件,由于该方法的返回值是super,所以原本应该会被传到当前dispatch所在位置的intercept方法中进行判断是否拦截,但是由于当前dispatch所在的位置是acticity,没有intercepter方法,所以,默认事件向下级传递。其过程:(MainActicity的dispatchTouchEvent—>Father的dispatchTouchEvent),该过程后,于是事件从acticity中被传递到了father的dispatch方法中。由于father的dispatch方法的返回值也是super。则事件被传递到intercepter中判断是否需要拦截,而该intercepter的返回值也是super,默认表示不拦截,于是,事件将继续想下级传递。其过程:(Father的dispatchTouchEvent—>Father的onInterceptTouchEvent—>Child的dispatchTouchEvent),该过程后,事件被传递到了Child的dispatchTouchEvent中,由于Child的dispatchTouchEvent方法返回值也是super,则该事件被交由Child的onInterceptTouchEvent方法判断是否拦截,该方法返回值依旧为super,表示不拦截,则事假继续想下级传递到MyTextView的dispatchTouchEvent方法中,其过程:(Child的dispatchTouchEvent—>Child的onInterceptTouchEvent—>MyTextView的dispatchTouchEvent),该过程后,事件被传递到了MyTextView的dispatchTouchEvent中,由于MyTextView的dispatchTouchEvent返回值是super,原本该将该事件分发该onInterceptTouchEvent方法进行判断是否拦截,但是由于MyTextView已经是最小单元,不在有下级,于是该事件被分发给了最小单元的onTouchEvent方法。由于MyTextView的onTouchEvent方法返回值为super,表示向上级传递,则该事件由当前onTouchEvent方法传递给了父级Child的onTouchEvent方法,其过程:(MyTextView的dispatchTouchEvent—>MyTextView的onTouchEvent—>Child的onTouchEvent),该过程后,事件被传递到了Child的onTouchEvent方法中,由于该方法的返回值为true,表示事件在此方法中被消费掉,于是,整个试探性事件分发完成。事件的试探性分发完成之后,将进行事件分发,采用的是事件的逐级分发,事件由Activity的dispatchTouchEvent方法开始分发到Father的dispatchTouchEvent,由于Child不在当前级,则在Father层使用onInterceptTouchEvent来判断事件是否拦截,确认不拦截后,事件从Father的onInterceptTouchEvent下发到Child的dispatchTouchEvent中,由于Child中的onTouchEvent方法就在当前层,不用再判是否进行事件拦截,于是,Child的dispatchTouchEvent方法直接将事件发给Child的onTouchEvent方法,其过程:(Activity的dispatchTouchEvent—>Father的dispatchTouchEvent—>Father的onInterceptTouchEvent—>Child的dispatchTouchEvent—>Child的onTouchEvent)至此,整个事件分发结束。
相关文章推荐
- Android事件分发总结
- Android中的事件分发机制总结
- Android ViewGroup事件分发机制总结
- Android的事件分发总结
- Android事件分发机制总结
- 总结的不错的Android事件分发介绍
- android菜鸟之路-事件分发机制总结(二)
- Android View 与 ViewGroup 事件分发总结
- Android事件分发机制学习和总结
- 对Android中Touch事件分发机制的理解和总结
- Android 事件分发总结
- Android开发总结笔记 ViewGroup的事件分发机制 3-10
- Android View 事件分发机制 && Android ViewGroup 事件分发机制 源码解析 --总结
- Android总结02_Touch事件的分发与消费机制
- 【转】Android笔记:触摸事件的分析与总结----Touch事件分发方法dispatchTouchEvent()源码分析
- android事件分发总结
- android开发游记:从viewpager禁用滚动 总结android事件分发机制
- Android开发总结笔记 View的事件分发机制 3-9
- Android触摸事件分发机制总结
- android 点击事件分发总结