Android滑动的实现

坐标系

  1. android 坐标系
//int[] location = new int[2];
getLocationOnScreen(int location[]);获取view的左上角在android坐标系的坐标
getRawX();                          触控过程中,获取触点在android坐标系的坐标
  1. View坐标系
    getX() getY();

滑动的七种实现

1. layout
2. offsetLeftAndRight,offsetTopAndBottom
3. LayoutParams
4. scrollTo,scrollBy

移动的是View的Content。如果在ViewGroup使用,滑动的是它的子View,而在View中滑动的是它的内容(TextView content是它的文本)

@Override
public boolean onTouchEvent(MotionEvent event) {
    int x = (int) event.getX();
    int y = (int) event.getY();
    switch (event.getAction()) {
        case MotionEvent.ACTION_DOWN:
            lastX = (int) event.getX();
            lastY = (int) event.getY();
            break;
        case MotionEvent.ACTION_MOVE:
            int offsetX = x - lastX;
            int offsetY = y - lastY;
            //1.((View) getParent()).scrollBy(-offsetX, -offsetY);
            //2.layout(getLeft() + offsetX,getTop() + offsetY,getRight() + offsetX,getBottom() + offsetY);
            //3.offsetLeftAndRight(offsetX);offsetTopAndBottom(offsetY);
            ViewGroup.MarginLayoutParams layoutParams = (ViewGroup.MarginLayoutParams) getLayoutParams();
            layoutParams.leftMargin = getLeft() + offsetX;
            layoutParams.topMargin = getTop() + offsetY;
            setLayoutParams(layoutParams);  
            break;
    }
    return true;
}
5. Scroller
//1.在构造函数中初始化 Scroller
mScroller = new Scroller(context,new BounceInterpolator());
//2.重写 view 的 computeScroll
@Override
public void computeScroll() {
    super.computeScroll();
    // 判断Scroller是否执行完毕
    if (mScroller.computeScrollOffset()) {
        ((View) getParent()).scrollTo(
                mScroller.getCurrX(),   //获取当前的滑动坐标
                mScroller.getCurrY());
        // 通过重绘来不断调用computeScroll
        invalidate();
    }
}
//3.startScroll 设置参数
@Override
public boolean onTouchEvent(MotionEvent event) {
    int x = (int) event.getX();
    int y = (int) event.getY();
    switch (event.getAction()) {
        case MotionEvent.ACTION_DOWN:
            lastX = (int) event.getX();
            lastY = (int) event.getY();
            break;
        case MotionEvent.ACTION_MOVE:
            int offsetX = x - lastX;
            int offsetY = y - lastY;
            ((View) getParent()).scrollBy(-offsetX, -offsetY);
            break;
        case MotionEvent.ACTION_UP:
            // 手指离开时,执行滑动过程
            View viewGroup = ((View) getParent());
            mScroller.startScroll(  //回到原来的位置
                    viewGroup.getScrollX(), //总共滑动的距离
                    viewGroup.getScrollY(),
                    -viewGroup.getScrollX(),
                    -viewGroup.getScrollY());
            invalidate();
            break;
    }
    return true;
}
scroller.gif

Scroll的绘制原理:
重点在于 mScroller.startScroll(...)下面的 invalidate 方法,这将导致 View 进行重绘,View 的 draw 方法又会去调用 computeScroll 方法,computeScroll 在 View中是个空实现。这就是为什么一定要 Override computeScroll 的原因。

6. 属性动画
7. ViewDragHelper (参考DragLayout-master)
最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
【社区内容提示】社区部分内容疑似由AI辅助生成,浏览时请结合常识与多方信息审慎甄别。
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

相关阅读更多精彩内容

  • Android 自定义View的各种姿势1 Activity的显示之ViewRootImpl详解 Activity...
    passiontim阅读 176,279评论 25 709
  • 内容是博主照着书敲出来的,博主码字挺辛苦的,转载请注明出处,后序内容陆续会码出。 当了解了Android坐标系和触...
    Blankj阅读 11,715评论 3 60
  • 导语 滑动算是Android比较常用的效果了,滑动的操作具有很好的用户体验性。 主要内容 滑动效果是如何产生的 实...
    一个有故事的程序员阅读 11,529评论 3 11
  • 预备知识 Android屏幕区域划分我们先看一副图来了解一下Android屏幕的区域划分,如下:Android屏幕...
    小芸论阅读 12,913评论 6 44
  • 今日教师节,各种对老师表达感恩、祝福的美文铺满微信,思绪也回到了少年青年时代,老师们或温情、或粗犷的教育风格给我们...
    计静怡阅读 1,261评论 0 0

友情链接更多精彩内容