MotionEvent:
触控事件对应的是MotionEvent类,事件的主要类型:
1).ACTION_DOWN:
按下事件;
2).ACTION_MOVE:
按下并且移动;
3).ACTION_UP:
手指离开屏幕;
4).ACTION_CANCEL:
按下屏幕时,ACTION_DOWN被我们返回true处理,当手指移动到当前控件的外面,这时候就会触发ACTION_CANCLE事件,触发cancle事件就不会接收到ACTION_UP事件,这个触摸事件被他的父控件拦截掉,触发了cancle事件.之后的触摸事件就再也不会传递到当前控件的onTouchEvent里面;
事件传递的三个阶段:
1).分发(dispatchTouchEvent):
public boolean dispatchTouchEvent(MotionEvent event) {
throw new RuntimeException("Stub!");
}
A).返回true表示事件被当前视图消费掉,不再继续分发事件;
B).返回super.dispatchTouchEvent表示继续分发该事件;
C).如果当前视图是ViewGroup及其子类,则会调用onInterceptTouchEvent来判断是否拦截改事件;
2).拦截(onInterceptTouchEvent):
onInterceptTouchEvent只在ViewGroup及其子类中存在,在View和Activity中不存在;
public boolean onInterceptTouchEvent(MotionEvent ev) {
throw new RuntimeException("Stub!");
}
A).返回true表示拦截了这个事件,不继续分发给子视图, 同时交给了自身的onTouchEvent分发来消费这个事件;
B).返回false或者返回super.onInterceptTouchEvent表示不对该事件进行拦截,需要继续传递给子视图
3).消费(onTouchEvent):
public boolean onTouchEvent(MotionEvent event) {
throw new RuntimeException("Stub!");
}
A).返回true表示当前视图可以处理对应的触摸事件,事件不会向上传递给父视图;
B).返回false表示视图不处理这个事件,事件会被传递给父控件的onTouchEvent方法进行处理;
总结:
1).不做任何处理时,传递流程是从dispatchTouchEvent开始,,事件由嵌套的外层进入到内层传递,最后达到里面层的view,由view的onTouchEvent方法进行处理,如果onTouchEvent能处理这个事件,则返回true , 否则返回false, 返回false事件会向外层View的onTouchEvent进行处理,以此类推;
2).如果一开始返回true , 则事件不会进到内层view , 事件会提前被消费掉;
3).View的事件触发顺序是先执行onTouch方法, 最后才执行onClick方法,如果onTouch返回true ,事件不会被传递下去,最后也不会调用onClick事件; 如果返回false, 则事件继续传递;
4).触摸事件的传递顺序由Activity--->ViewGroup--->View;
5).ViewGroup通过onIntercept方法对事件进行拦截,如果该方法返回true,则事件不会继续传递给子View,如果返回false或者super.onInterceptTonchEvent,则事件会继续传递给子View.
6).在子View中对事件进行消费后,ViewGroup将不在收到任何事件;
7).如果View不消耗出ACTION_DOWN以外的其他事件,那么这个点击事件会消失,此时父视图的onTouchEvent并不会被调用,并且当前View可以持续收到后续的事件,最终这些消失的点击事件会传递给Activity处理;
8).ViewGroup默认不拦截任何事件,onInterceptTouchEvent默认返回false;
9).View没有onInterceptTouchEvent方法,一旦点击时间传递给它 , 它的onTouchEvent就会被调用;
10).View的onTouchEvent默认返回值为true(默认消费事件),除非他是不可点检的(clickble和longClickable同时为false).View的longClickable属性默认为false,clickble属性要分析,比如Button的clickble属性默认为true ,而TextView的clickble属性默认为false;
11).View的enable属性不影响onTouchEvent的默认返回值;
12).事件传递过程中是由外向内的,即事件总是先传递给父元素,然后再由父元素分发给子View,通过requestDisallowInterceptTouchEvent方法可以在子元素中干预父元素的事件分发,但是ACTION_DOWN事件除外;
其他点击事件: onSingleTapUp(单击), onFling(快速滑动), onScroll(拖动),onLongPress(长按),onDoubleTap(双击)