You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
|
|
|
---
|
|
|
|
事件分发机制
|
|
|
|
---
|
|
|
|
|
|
|
|
#### 目录
|
|
|
|
|
|
|
|
1. 概述
|
|
|
|
2. 核心方法
|
|
|
|
3. 关于 ACTION_MOVE 和 ACTION_UP
|
|
|
|
4. 参考
|
|
|
|
|
|
|
|
#### 概述
|
|
|
|
|
|
|
|
事件分发中的事件即指 MotionEvent,传递方向是 Activity -> ViewGroup -> View,然后在回溯。事件分发包含三个核心方法:dispatchTouchEvent、onInterceptTouchEvent、onTouchEvent。
|
|
|
|
|
|
|
|
#### 核心方法
|
|
|
|
|
|
|
|
##### dispatchTouchEvent
|
|
|
|
|
|
|
|
用于事件分发,返回结果表示是否消耗了当前事件。它和 onInterceptTouchEvent 和 onTouchEvent 的关系可以表示为:
|
|
|
|
|
|
|
|
```java
|
|
|
|
public boolean dispatchTouchEvent(MotionEvent ev){
|
|
|
|
boolean consume = false;
|
|
|
|
if(onInterceptTouchEvent(ev)){
|
|
|
|
consume = onTouchEvent(ev);
|
|
|
|
}else{
|
|
|
|
consume = child.dispatchTouchEvent(ev);
|
|
|
|
}
|
|
|
|
return consume;
|
|
|
|
}
|
|
|
|
```
|
|
|
|
|
|
|
|
##### onInterceptTouchEvent
|
|
|
|
|
|
|
|
只存在于 ViewGroup 中,只有 ViewGroup 才会决定是否需要拦截事件自己处理。默认是不会拦截的,交给子 View 处理。
|
|
|
|
|
|
|
|
##### onTouchEvent
|
|
|
|
|
|
|
|
用于事件处理,我们平时设置的 onTouchEventListener 和 onClickListener 都是在其内。
|
|
|
|
|
|
|
|
##### 总结
|
|
|
|
|
|
|
|
1. 对于 dispatchTouchEvent 和 onTouchEvent ,return true 代表终止时间传递,return false 则是回溯到父 View 的 onTouchEvent 方法。
|
|
|
|
2. ViewGroup 想把事件分发给自己的 onTouchEvent,需要 onInterceptTouchEvent return true 把事件拦截下来,默认是不拦截的,所以 return super.onInterceptTouchEvent == return false 到 View.dispatchTouchEvent。
|
|
|
|
3. View 没有拦截器,为了让 View 可以把事件分发给自己的 onTouchEvent,View 的 dispatchTouchEvent 默认实现(super)就是把事件分发给自己的 onTouchEvent。
|
|
|
|
|
|
|
|
#### 关于 ACTION_MOVE 和 ACTION_UP
|
|
|
|
|
|
|
|
上面都是针对 ACTION_DOWN 的时间传递,ACTION_MOVE 和 ACTION_UP 在传递的过程中并不是和 ACTION_DOWN 一样。如果在执行 ACTION_DOWN 的时候返回了 false,后面一系列其他的 action 就不会再得到执行了。简单来说,就是当 dispatchTouchEvent 在进行事件分发的时候,只有前一个事件(如 ACTION_DOWN)返回 true,才会收到 ACTION_MOVE 和 ACTION_UP 的事件。
|
|
|
|
|
|
|
|
ACTION_DOWN 一旦在 onTouchEvent 被消费,那么之后的 ACTION_MOVE 和 ACTION_UP 就都会由其处理,结束时间传递。
|
|
|
|
|
|
|
|
比如我们在 Activity 的 onTouchEvent 返回 true:
|
|
|
|
|
|
|
|
![](https://i.loli.net/2019/02/11/5c60d51909117.png)
|
|
|
|
|
|
|
|
红线代表 ACTION_DOWN 事件流向,蓝线代表 ACTION_MOVE 和 ACTION_UP 事件流向。
|
|
|
|
|
|
|
|
#### 参考
|
|
|
|
|
|
|
|
[图解 Android 事件分发机制](https://www.jianshu.com/p/e99b5e8bd67b)
|
|
|
|
|
|
|
|
[Android 事件分发机制详解与实战剖析 | 开发者说·DTalk](https://mp.weixin.qq.com/s/5rsgtUER2q6EP2C3ViMR4w)
|
|
|
|
|
|
|
|
[事件分发机制,我们从细节中学习!](https://mp.weixin.qq.com/s/KU32XpwDFBOl8ueXIaA8Tw)
|