频道栏目
IT货架 > > 正文
Android Ripple 按钮水波纹效果(一)
网友分享于:Jan 1, 1970 8:00:00 AM    来源: IT货架   

标签:动画   android   按钮   

看到android 5.0有一个按钮点击效果非常棒,先来看效果图:
这里写图片描述

但是这种效果只能在5.0的系统上有效果,如何在低版本上实现呢?
这种效果网上也有人实现了,
blog 地址http://blog.csdn.net/singwhatiwanna/article/details/42614953

ok,直接进入主题,
要实现这种动画效果也不难,原理可以用一句话概括:就是,在我们按下view的时候,从按下的位置开始绘制圆,圆的半径一直增大,直至把View全部覆盖掉。

通过实现原理我们可以分析出,要实现这种效果,需要重写onDraw方法,onTouchEvent方法,如果有必要还需要通过onMeasure方法来获取View的size

1、onDraw方法,就是不断的绘制圆,这里需要循环调用,
2、onTouchEvent方法:通过MotionEvent.ACTION_DOWN和MotionEvent.ACTION_UP做相应的操作并触发onDraw方法
3、onMeasure计算View的size,通过size加上MotionEvent.ACTION_DOWN起始点计算出圆的最大半径

代码实现:
保存view的大小,用于计算绘制 圆的最大半径

@Override
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
   super.onMeasure(widthMeasureSpec, heightMeasureSpec);
   mRect.set(0, 0, getMeasuredWidth(), getMeasuredHeight());
}

手指按下view的时候,计算按下点的位置,并触发onDraw方法

public boolean onTouchEvent(MotionEvent event) {
        final int action = MotionEventCompat.getActionMasked(event);
        switch (action) {
            case MotionEvent.ACTION_DOWN: {
                mDrawFinish = false;
                int index = MotionEventCompat.getActionIndex(event);
                int eventId = MotionEventCompat.getPointerId(event, index);
                if (eventId != -1) {
                    mInitX = (int) MotionEventCompat.getX(event, index);
                    mInitY = (int) MotionEventCompat.getY(event, index);
                    updateDrawData();
                    ViewCompat.postInvalidateOnAnimation(this);
                }
                return true;
            }

更新数据,重新计算圆的半径和步长

private void updateDrawData() {
        int radiusLeftTop = (int) Math.sqrt((mRect.left - mInitX) * (mRect.left - mInitX) +
                (mRect.top - mInitY) * (mRect.top - mInitY));
        int radiusRightTop = (int) Math.sqrt((mRect.right - mInitX) * (mRect.right - mInitX) +
                (mRect.top - mInitY) * (mRect.top - mInitY));
        int radiusLeftBottom = (int) Math.sqrt((mRect.left - mInitX) * (mRect.left - mInitX) +
                (mRect.bottom - mInitY) * (mRect.bottom - mInitY));
        int radiusRightBottom = (int) Math.sqrt((mRect.right - mInitX) * (mRect.right - mInitX) +
                (mRect.bottom - mInitY) * (mRect.bottom - mInitY));
        mRadius = getMax(radiusLeftTop, radiusRightTop, radiusLeftBottom, radiusRightBottom);
        mStep = mRadius/mCycle;
    }

手指抬起的时候需要做的操做,把步长加大2.5倍,加快圆的绘制

 @Override
    public boolean onTouchEvent(MotionEvent event) {
        final int action = MotionEventCompat.getActionMasked(event);
        switch (action) {
        //..
            case MotionEvent.ACTION_CANCEL:
            case MotionEvent.ACTION_UP:
                mStep = (int) (2.5f * mStep);
                mDrawBack = true ;
                break;
        }
        return super.onTouchEvent(event);
    }

最后就是绘制圆了,这里需要做判断,如果当前绘制的圆半径没有达到我们计算的最大半径,需要继续绘制

@Override
    protected void onDraw(Canvas canvas) {
        if (mDrawFinish) {
            super.onDraw(canvas);
            return;
        }
        canvas.drawColor(0x08000000);
        super.onDraw(canvas);
        if (mStep == 0) {
            return;
        }
        mDrawRadius = mDrawRadius + mStep;


        if (mDrawRadius > mRadius) {
            mDrawRadius = 0;
            canvas.drawCircle(mInitX, mInitY, mRadius, mRevealPaint);
            mDrawFinish = true;
            ViewCompat.postInvalidateOnAnimation(this);
            return;
        }

        canvas.drawCircle(mInitX, mInitY, mDrawRadius, mRevealPaint);
        ViewCompat.postInvalidateOnAnimation(this);
    }

整个效果的实现,相对比较简单,只是很无聊的一直绘圆。
最后要说明一点,如果你想对TextView做这种效果,则继承TextView即可,LinearLayout等其他组件同理;

demo下载

Android Ripple 按钮水波纹效果(一)

标签:动画   android   按钮   

广告服务联系QQ:1134687142 | 网站地图

版权所有: IT货架- 内容来自互联网,仅供用于技术学习,请遵循相关法律法规. 京ICP备11030978号-1