View位置的變化和觸控操做都涉及到MotionEvent
類,MotionEvent
中封裝了一些與觸摸相關的東西,好比觸摸事件Action
,觸摸座標等。移動View
無疑就是改變其位置,一般有如下幾種方式。git
在View
類中,咱們知道有一個layout
方法是給View
定位的 ,結合onTouchEvent
方法 ,咱們能夠很好的實現一個View
的移動.github
int lastX, lastY; @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; } return true; }12345678910111213141516171819202122232425262728293031323334
這裏面使用了絕對座標,使用絕對座標的時候,須要在每次ACTION_MOVE
後從新設置初始座標.web
使用offsetLeftAndRight();offsetTopAndBottom();
方法,經過設置偏移量來滑動Viewide
int lastX, lastY; @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); offsetLeftAndRight(offsetX); offsetTopAndBottom(offsetY); lastX = rawX; lastY = rawY; break; } return true; }12345678910111213141516171819202122232425262728293031323334353637
LayoutParams
,使用LayoutParams
滑動View
,經過改變佈局參數來達到滑動View
的目的.佈局
int lastX, lastY; @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);// offsetLeftAndRight(offsetX);// offsetTopAndBottom(offsetY); ViewGroup.MarginLayoutParams layoutParams = (ViewGroup.MarginLayoutParams) getLayoutParams(); layoutParams.leftMargin = getLeft() + offsetX ; layoutParams.topMargin = getTop() +offsetY; setLayoutParams(layoutParams); lastX = rawX; lastY = rawY; break; } return true; }123456789101112131415161718192021222324252627282930313233343536373839404142
使用ScrollTo() 和ScrollBy()
方法來改變View
的位置.動畫
int lastX, lastY; @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);// offsetLeftAndRight(offsetX);// offsetTopAndBottom(offsetY);// ViewGroup.MarginLayoutParams layoutParams = (ViewGroup.MarginLayoutParams) getLayoutParams();// layoutParams.leftMargin = getLeft() + offsetX ;// layoutParams.topMargin = getTop() +offsetY;// setLayoutParams(layoutParams); ((View) getParent()).scrollBy( -offsetX, -offsetY); lastX = rawX; lastY = rawY; break; } return true; }123456789101112131415161718192021222324252627282930313233343536373839404142434445
這裏須要注意的是
1.首先咱們的ScrollTo() and ScrollBy()
方法移動的是View的Content
2.咱們移動的是畫布,所以須要設置相反的值,才能讓View
跟隨手指移動.spa
使用Scroller
類來移動View
,與ScrollBy()
方法關係緊密,ScrollBy()
移動是瞬時完成,Scroller
類在ACTION_MOVE
中對偏移量進行劃分,達到平滑效果.咱們須要三個步驟code
mScroller = new Scroller(context);1
@Override public void computeScroll() { super.computeScroll(); if (mScroller.computeScrollOffset()) { ((View) getParent()).scrollTo(mScroller.getCurrX(), mScroller.getCurrY()); invalidate(); } }12345678
case MotionEvent.ACTION_UP: ViewGroup viewGroup = (ViewGroup) getParent(); mScroller.startScroll(viewGroup.getScrollX(),viewGroup.getScrollY(),-viewGroup.getScrollX(),-viewGroup.getScrollY()); invalidate(); break;1234567
經過 屬性動畫對View
位置對改變orm
int w = text.getWidth(); int screenW = UiUtil.getScreenWidth(); int transX = screenW - w; ObjectAnimator transAnim = ObjectAnimator.ofFloat(text, "translationX", 0, transX);1234
使用v4包中的ViewDragHelper
能很好的實現View
的滑動和事件分發,典型谷歌官方的 Drawerlayout
事件