您的位置:首页 > 其它

自定义View---怎么解决View的滑动冲突

2015-11-06 22:15 447 查看

自定义View—怎么解决View的滑动冲突

常见View的滑动冲突有以下几种:

1.外部滑动和内部滑动方向不一样

2.外部滑动和内部滑动方向一样

3.以上两种情况的嵌套糅合

滑动冲突解决的规则:

1.根据自定义View的特征来解决滑动冲突。例如:外部滑动和内部滑动方向不一样时,我们可以通过滑动的水平方向上和垂直方向的距离来解决。

2.根据具体业务来解决滑动冲突。这种情况得具体问题具体分析。

废话不多说,下面展示解决滑动冲突的两种方式,最后再通过两个例子来加深:

1.外部拦截法:所谓外部拦截法,指事件都先经过父容器的拦截处理方式。如果父容器需要此事件就拦截,反之~不拦截。外部拦截法需要重写父容器的onInterceptTouchEvent( … )方法,在此方法内部做相应的拦截处理,伪代码如下:

@Override
public boolean onInterceptTouchEvent(MotionEvent ev) {
boolean intercepter = false;
int x = (int) ev.getX();
int y = (int) ev.getY();
switch (ev.getAction()) {
case MotionEvent.ACTION_DOWN:
intercepter = false;
// 其他处理
break;
case MotionEvent.ACTION_MOVE:
if (isSolve) {// 父容器需要拦截当前点击事件
intercepter = true;// 拦截事件
} else {
intercepter = false;
}
break;
case MotionEvent.ACTION_UP:
intercepter = false;//必须返回false,此事件ACTION_UP本身没有多大意义
break;
default:
break;
}
mLastXIntercept = x;
mLastYIntercept = y;
return intercepter;
}


2.内部吸收法:指父容器不拦截任何事件,所有事件都传递给子元素。如果子元素需要则接受,反之,传递给父容器来处理。此方法与Android的事件分发机制不一样。需要配合requestDissallowInterceptTouchEvent处理,使用起来相对来说有点复杂,伪代码如下:

@Override
public boolean dispatchTouchEvent(MotionEvent ev) {
int x = (int) ev.getX();
int y = (int) ev.getY();
switch (ev.getAction()) {
case MotionEvent.ACTION_DOWN:
parent.requestDisallowInterceptTouchEvent(true);//父容器不处理,parent必须为ViewGroup容器类型
break;
case MotionEvent.ACTION_MOVE:
int deltaX = x-mLastX;
int deltaY = y-mLastY;
if(!isSolve){//条件:父容器需要处理此类事件
parent.requestDisallowInterceptTouchEvent(false);//交给父容器处理
}
break;

case MotionEvent.ACTION_UP:

break;
default:
break;
}
mLastX = x;
mLastY = y;

return super.dispatchTouchEvent(ev);//返回的是父类的分发事件的值

}


除了子元素需要处理,父容器也需要做相应的处理,父容器需要默认拦截除ACTION_DOWN以外的其他事件,只有这样,当子元素调用parent.requestDisallowInterceptTouchEvent(false)方法时,父容器才能继续拦截所需要的事件,父容器处理伪代码如下:

@Override
public boolean onInterceptTouchEvent(MotionEvent ev) {
boolean intercepter = false;
int x = (int) ev.getX();
int y = (int) ev.getY();
switch (ev.getAction()) {
case MotionEvent.ACTION_DOWN:
return false;
break;
case MotionEvent.ACTION_MOVE:
return true;
break;
case MotionEvent.ACTION_UP:
return true;
break;
default:
return true;
}
}


ok,伪代码分析完成,是不是很简单….此片博文时通过阅读任玉刚大神的《Android开发艺术探索》,加上自己的理解编写。具体例子将在下一篇展示。谢谢~
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息