目录1、效果视频2、剖析Android坐标系3、实现方式3.1 layout3.2 scrollBy3.3 offsetLeftAndRight offsetTopAndButton
滑动的本质是移动,滑动的原理就是通过不断的改变View的坐标而实现。
Android
系统提供了很多方法获取坐标值,可以将其分为两种类别,具体如下:
View 提供的获取坐标的方法:
getTop():
获取到的是View自身的顶边到其父布局顶边的距离getLeft():
获取到的是View自身的左边到其父布局左边的距离getRight():
获取到的是View自身的右边到其父布局左边的距离getBottom():
获取到的是View自身的底边到其父布局顶边的距离MotionEvent 提供的方法:
getX():
获取点击事件距离控件左边的距离,即视图坐标getY():
获取点击事件距离控件顶边的距离,即视图坐标getRawX():
获取点击事件距离整个屏幕左边的距离,即绝对坐标getRawY():
获取点击事件距离整个屏幕顶边的距离,即绝对坐标使用绝对坐标系,每次执行移动逻辑后需要重新设置初始化坐标
@Override
public boolean onTouchEvent(MotionEvent event) {
int rawX = (int) (event.getRawX());
int rawY = (int) (event.getRawY());
switch (event.getAction()){
case MotionEvent.ACTION_DOWN:
lastX = rawX;
lastY = rawY;
break;
case MotionEvent.ACTION_MOVE:
int offsetX = rawX - lastX;
int offsetY = rawY - lastY;
layout( getLeft()+offsetX,getTop()+offsetY,getRight()+offsetX,getBottom()+offsetY );
lastX = rawX;
lastY = rawY;
break;
case MotionEvent.ACTION_UP:
break;
}
return true;
}
@Override
public boolean onTouchEvent(MotionEvent event) {
int x = (int) event.getX();
int y = (int) event.getY();
switch (event.getAction()) {
case MotionEvent.ACTION_DOWN:
lastX = x;
lastY = y;
break;
case MotionEvent.ACTION_MOVE:
int offsetX = x - lastX;
int offsetY = y - lastY;
((View) getParent()).scrollBy( -offsetX, -offsetY );
break;
case MotionEvent.ACTION_UP:
break;
}
return true;
}
@Override
public boolean onTouchEvent(MotionEvent event) {
int x = (int) event.getX();
int y = (int) event.getY();
switch (event.getAction()){
case MotionEvent.ACTION_DOWN:
lastX = x;
lastY = y;
break;
case MotionEvent.ACTION_MOVE:
int offsetX = x - lastX;
int offsetY = y - lastY;
offsetLeftAndRight( offsetX );
offsetTopAndBottom( offsetY );
break;
case MotionEvent.ACTION_UP:
break;
}
return true;
}
通过getLayoutParams()
获取LayoutParams
时,需要根据不同的父类型使用设置不同的类型,比如父布局为LinearLayout则设置类型为 LinearLayout.LayoutParams
@Override
public boolean onTouchEvent(MotionEvent event) {
int x = (int) event.getX();
int y = (int) event.getY();
switch (event.getAction()){
case MotionEvent.ACTION_DOWN:
lastX = x;
lastY = y;
break;
case MotionEvent.ACTION_MOVE:
int offsetX = x - lastX;
int offsetY = y - lastY;
LinearLayout.LayoutParams layoutParams = (LinearLayout.LayoutParams)getLayoutParams();
layoutParams.leftMargin = getLeft()+offsetX;
layoutParams.topMargin = getTop()+offsetY;
setLayoutParams( layoutParams );
break;
case MotionEvent.ACTION_UP:
break;
}
return true;
}
更方便的是直接使用ViewGroup
,不需要判断父布局类型
ViewGroup.MarginLayoutParams layoutParams = (ViewGroup.MarginLayoutParams)getLayoutParams();
layoutParams.leftMargin = getLeft()+offsetX;
layoutParams.topMargin = getTop()+offsetY;
setLayoutParams( layoutParams );
初始化Scroller:
scroller = new Scroller( context );
重写computeScroll()
方法
使用computeScrollOffset()
判定是否完成了整个滑动:
@Override
public void computeScroll() {
if (scroller.computeScrollOffset()) {
((View) getParent()).scrollTo( scroller.getCurrX(), scroller.getCurrY() );
invalidate();
}
super.computeScroll();
}
@Override
public boolean onTouchEvent(MotionEvent mv) {
View parent = (View) getParent();
switch (mv.getAction()) {
case MotionEvent.ACTION_DOWN:
lastX = (int) mv.getX();
lastY = (int) mv.getY();
break;
case MotionEvent.ACTION_MOVE:
int upX = (int) (mv.getX() - lastX);
int upY = (int) (mv.getY() - lastY);
parent.scrollBy( -upX, -upY );
break;
case MotionEvent.ACTION_UP:
scroller.startScroll( parent.getScrollX(), parent.getScrollY(), -parent.getScrollX(), -parent.getScrollY(), 1000 );
invalidate();
break;
}
return super.onTouchEvent( mv );
}
效果视频:
private void InitAnimation(){
animation = new TranslateAnimation( 0,200,0,200 );
animation.setDuration( 1000 );
}
moveButton.startAnimation( animation );
到此这篇关于Android 实现滑动的六种方式的文章就介绍到这了,更多相关Android 实现滑动的方式内容请搜索编程网以前的文章或继续浏览下面的相关文章希望大家以后多多支持编程网!
--结束END--
本文标题: Android 实现滑动的六种方式
本文链接: https://www.lsjlt.com/news/156774.html(转载时请注明来源链接)
有问题或投稿请发送至: 邮箱/279061341@qq.com QQ/279061341
下载Word文档到电脑,方便收藏和打印~
2024-01-21
2023-10-28
2023-10-28
2023-10-27
2023-10-27
2023-10-27
2023-10-27
回答
回答
回答
回答
回答
回答
回答
回答
回答
回答
0