Android界面上拉下拉的回弹效果实例代码
废话不多说,具体代码如下所示:
publicclassMyScrollViewextendsScrollView{
privateViewchildView;
publicMyScrollView(Contextcontext){
super(context);
}
publicMyScrollView(Contextcontext,AttributeSetattrs){
super(context,attrs);
}
publicMyScrollView(Contextcontext,AttributeSetattrs,intdefStyleAttr){
super(context,attrs,defStyleAttr);
}
//@Override
//protectedvoidonLayout(booleanchanged,intl,intt,intr,intb){
//super.onLayout(changed,l,t,r,b);
//}
//获取子视图
@Override
protectedvoidonFinishInflate(){
super.onFinishInflate();
if(getChildCount()>0){
childView=getChildAt(0);
}
}
privateintlastY;//上一次y轴方向操作的坐标位置
privateRectnormal=newRect();//用于记录临界状态的左、上、右、下
privatebooleanisFinishAnimation=true;//是否动画结束
privateintlastX,downX,downY;
//拦截:实现父视图对子视图的拦截
//是否拦截成功,取决于方法的返回值。返回值true:拦截成功。反之,拦截失败
@Override
publicbooleanonInterceptTouchEvent(MotionEventev){
booleanisIntercept=false;
inteventX=(int)ev.getX();
inteventY=(int)ev.getY();
switch(ev.getAction()){
caseMotionEvent.ACTION_DOWN:
lastX=downX=eventX;
lastY=downY=eventY;
break;
caseMotionEvent.ACTION_MOVE:
//获取水平和垂直方向的移动距离
intabsX=Math.abs(eventX-downX);
intabsY=Math.abs(eventY-downY);
if(absY>absX&&absY>=UIUtils.dp2px(10)){
isIntercept=true;//执行拦截
}
lastX=eventX;
lastY=eventY;
break;
}
returnisIntercept;
}
@Override
publicbooleanonTouchEvent(MotionEventev){
if(childView==null||!isFinishAnimation){
returnsuper.onTouchEvent(ev);
}
inteventY=(int)ev.getY();//获取当前的y轴坐标
switch(ev.getAction()){
caseMotionEvent.ACTION_DOWN:
lastY=eventY;
break;
caseMotionEvent.ACTION_MOVE:
intdy=eventY-lastY;//微小的移动量
if(isNeedMove()){
if(normal.isEmpty()){
//记录了childView的临界状态的左、上、右、下
normal.set(childView.getLeft(),childView.getTop(),childView.getRight(),childView.getBottom());
}
//重新布局
childView.layout(childView.getLeft(),childView.getTop()+dy/2,childView.getRight(),childView.getBottom()+dy/2);
}
lastY=eventY;//重新赋值
break;
caseMotionEvent.ACTION_UP:
if(isNeedAnimation()){
//使用平移动画
inttranslateY=childView.getBottom()-normal.bottom;
TranslateAnimationtranslateAnimation=newTranslateAnimation(0,0,0,-translateY);
translateAnimation.setDuration(200);
//translateAnimation.setFillAfter(true);//停留在最终位置上
translateAnimation.setAnimationListener(newAnimation.AnimationListener(){
@Override
publicvoidonAnimationStart(Animationanimation){
isFinishAnimation=false;
}
@Override
publicvoidonAnimationEnd(Animationanimation){
isFinishAnimation=true;
childView.clearAnimation();//清除动画
//重新布局
childView.layout(normal.left,normal.top,normal.right,normal.bottom);
//清除normal的数据
normal.setEmpty();
}
@Override
publicvoidonAnimationRepeat(Animationanimation){
}
});
//启动动画
childView.startAnimation(translateAnimation);
}
break;
}
returnsuper.onTouchEvent(ev);
}
//判断是否需要执行平移动画
privatebooleanisNeedAnimation(){
return!normal.isEmpty();
}
privatebooleanisNeedMove(){
intchildMeasuredHeight=childView.getMeasuredHeight();//获取子视图的高度
intscrollViewMeasuredHeight=this.getMeasuredHeight();//获取布局的高度
Log.e("TAG","childMeasuredHeight="+childMeasuredHeight);
Log.e("TAG","scrollViewMeasuredHeight="+scrollViewMeasuredHeight);
intdy=childMeasuredHeight-scrollViewMeasuredHeight;//dy>=0
intscrollY=this.getScrollY();//获取用户在y轴方向上的偏移量(上+下-)
if(scrollY<=0||scrollY>=dy){
returntrue;//按照我们自定义的MyScrollView的方式处理
}
//其他处在临界范围内的,返回false。即表示,仍按照ScrollView的方式处理
returnfalse;
}
}
以上所述是小编给大家介绍的Android界面上拉下拉的回弹效果实例代码,希望对大家有所帮助,如果大家有任何疑问请给我留言,小编会及时回复大家的。在此也非常感谢大家对毛票票网站的支持!