Android自定义动画-ClockLoadingView

移动开发 AndroidZLoading
Zyao89 2017年3月20日星期一 22:58

有一段时间没写文章了,原因肯定只有两种咯,第一、懒;第二、工作忙。嘿嘿,我的原因肯定是 后者 呗(脸皮厚)。废话不多说,今天我们分享一个自定义的加载动画简单实现。

实现效果在最后,GIF有点大,手机流量慎重。

# 介绍

首先做这个动画的初衷是为了学习和分享,所以从这里起,我准备做一个系列的加载动画(截止时间:我放弃的时候)。

# 正文

这次分享的是一个简单的秒表样式的加载动画。初始化如下,参数随意写的:

    private void init(Context context, AttributeSet attrs)
    {
        mPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
        mPaint.setColor(Color.BLACK);//颜色

        mStartAnimator = ValueAnimator.ofFloat(0, 359);
        mStartAnimator.setStartDelay(500);//起始延迟

        initValues();
    }

    private void initValues()
    {
        mBigRadius = 50;//外框
        mInnerRadius = mBigRadius - 10;//内框
        mInnerCircleRectF = new RectF();

        mStartAngle = 0;//初角度
        mEndAngle = 0;//终角度
    }

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21

当View大小改变时,重新计算。


    @Override
    protected void onSizeChanged(int w, int h, int oldw, int oldh)
    {
        mViewWidth = w;
        mViewHeight = h;
        mViewCenterX = w / 2;
        mViewCenterY = h / 2;

        mInnerCircleRectF.set(mViewCenterX - mInnerRadius, mViewCenterY - mInnerRadius, mViewCenterX + mInnerRadius, mViewCenterY + mInnerRadius);
    }

1
2
3
4
5
6
7
8
9
10
11
12

加载:


    @Override
    protected void onAttachedToWindow()
    {
        super.onAttachedToWindow();
        if (mStartAnimator != null)
        {
            mStartAnimator.setRepeatCount(ValueAnimator.INFINITE);
            mStartAnimator.setDuration(1000);
            mStartAnimator.addListener(this);
            mStartAnimator.addUpdateListener(this);
            mStartAnimator.start();
        }
    }

    @Override
    protected void onDetachedFromWindow()
    {
        super.onDetachedFromWindow();
        if (mStartAnimator != null)
        {
            mStartAnimator.setRepeatCount(0);
            mStartAnimator.setDuration(0);
            mStartAnimator.cancel();
            mStartAnimator.removeAllUpdateListeners();
            mStartAnimator.removeAllListeners();
        }
    }

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29

绘制方法,绘制扇形。
额。。。这里就一句话,我都觉得不好意思了,尴尬...


    @Override
    protected void onDraw(Canvas canvas)
    {
        canvas.drawArc(mInnerCircleRectF, mStartAngle, mEndAngle - mStartAngle, true, mPaint);
    }

1
2
3
4
5
6
7

动画Animation监听回调

    @Override
    public void onAnimationStart(Animator animation)
    {
        mStartAngle = 0;
        mEndAngle = 0;
    }

    @Override
    public void onAnimationEnd(Animator animation)
    {
        mStartAngle = 0;
        mEndAngle = 0;
    }

    @Override
    public void onAnimationCancel(Animator animation)
    {
        mStartAngle = 0;
        mEndAngle = 0;
    }

    @Override
    public void onAnimationRepeat(Animator animation)
    {
        mIsFirstState = !mIsFirstState;
        if (mIsFirstState)//动画分为两个阶段,这里简单判断是否是第一阶段。
        {
            mStartAngle = 0;
            mEndAngle = 0;
        }
        else
        {
            mStartAngle = 0;
            mEndAngle = 360;
        }

    }

    @Override
    public void onAnimationUpdate(ValueAnimator animation)
    {
        float value = (float) animation.getAnimatedValue();

        if (mIsFirstState)
        {
            mEndAngle = value;
        }
        else
        {
            mStartAngle = value;
        }

        postInvalidate();
    }
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54

# 总结

文章里举例的代码,是最简单的实现原理,Github上的代码是进一步的优化。这里先到这里,希望大家能给个Star,后面我还会持续分享的。谢谢。

# 演示

结果演示图

Github:zyao89/ZCustomView

作者: Zyao89; 转载请保留
版权声明: 自由转载-非商用-非衍生-保持署名
上次编辑时间: 2023年11月27日星期一 11:18