Android自定义加载动画-感染体

Android自定义动画系列七,今天来分享第七个自定义Loading动画(InfectionBallBuilder),看上去感觉有种病毒源被感染的感觉,所以名字就叫感染体,这个动画做出来的效果,我不怎么满意,但是实现方式还是可以介绍介绍的。效果图如下:

GIF有点大,手机流量请三思。

效果图

演示效果动画

介绍

首先依旧是声明,我做这些动画的初衷是为了学习和分享,所以希望大家可以指点错误,让我更好的进步。(系列加载动画的截止时间:我放弃的时候)。

最近清明放假,我也给我自己放了一个假,放松之余,玩了几天几夜的 王者荣耀 😄。 五黑上分的感觉--爽歪歪呀。假期的最后一天了,收收心,继续来一波动画。

上一个动画链接:Android自定义加载动画-颤抖吧!球球

言归正传,开始新的动画。

正文

这里先把之前一个动画进行了简单的重构,然后提取了一个基类 BaseBallBuilder ,包含了画笔的初始化,贝塞尔曲线画圆方法,以及圆点内部类。具体的实现方法可以见上一个动画,或者前往Github上进行查看,这里就不做具体说明了。

abstract class BaseBallBuilder extends ZLoadingBuilder
{
    //贝塞尔曲线常量
    private static final float                   PROP_VALUE  = 0.551915024494f;
    //小球点集合
    protected final      LinkedList<CirclePoint> mBallPoints = new LinkedList<>();
    //画笔
    protected Paint mPaint;

    /**
     * 初始化画笔
     */
    protected void initPaint(float lineWidth)
    {
      ...
    }

    /**
     * p10    p9      p8
     * ------  ------
     * p11                     p7
     * |                       |
     * |                       |
     * p0 |      (0,0)         | p6
     * |                       |
     * |                       |
     * p1                      p5
     * ------  ------
     * p2      p3      p4
     */
    protected final void initPoints(float ballR)
    {
     ...
    }

    protected final void drawBall(Canvas canvas, Path path, Paint paint)
    {
        ...
    }

    /**
     * 圆点内部类
     */
    static class CirclePoint
    {
       ...
    }
}

这里开始今天的正题了 InfectionBallBuilder ,部分源码如下,具体步骤介绍就都写在注释里面了。很多方式都和前面的动画介绍类似,大家可以往前翻看。因为动画简单所以我这里就偷个懒,不再一一分析了。

public class InfectionBallBuilder extends BaseBallBuilder
{
    //动画间隔时间
    private static final long DURATION_TIME   = 888;
    private static final long DURATION_TIME_1 = 222;
    private static final long DURATION_TIME_2 = 333;
    private static final long DURATION_TIME_3 = 1333;
    private static final long DURATION_TIME_4 = 1333;
    //最终阶段
    private static final int  FINAL_STATE     = 4;
    private static final int  SUM_POINT_POS   = 3;
    private float mBallR;
    private Path  mPath;
    //当前动画阶段
    private int mCurrAnimatorState = 0;
    //每个小球的偏移量
    private float mCanvasTranslateOffset;

    @Override
    protected void initParams(Context context)
    {
        mBallR = getAllSize() / SUM_POINT_POS;
        mCanvasTranslateOffset = getIntrinsicWidth() / SUM_POINT_POS;
        mPath = new Path();
        initPaint(5);
        initPoints(mBallR);
    }

    @Override
    protected void onDraw(Canvas canvas)
    {
        drawBall(canvas);
    }

    /**
     * 绘制小球
     *
     * @param canvas
     */
    private void drawBall(Canvas canvas)
    {
        canvas.save();
        mPaint.setStyle(Paint.Style.FILL_AND_STROKE);
        canvas.translate(0, -mCanvasTranslateOffset);
        super.drawBall(canvas, mPath, mPaint);
        canvas.restore();
    }

    @Override
    protected void computeUpdateValue(ValueAnimator animation, @FloatRange(from = 0.0, to = 1.0) float animatedValue)
    {
        float offset = mCanvasTranslateOffset;
        switch (mCurrAnimatorState)//这里分阶段对每个圆点进行偏移量设置
        {
            case 0:
                animation.setDuration(DURATION_TIME);
                animation.setInterpolator(new AccelerateInterpolator());
                mBallPoints.get(2).setOffsetY(animatedValue * offset);
                mBallPoints.get(3).setOffsetY(animatedValue * offset);
                mBallPoints.get(4).setOffsetY(animatedValue * offset);
                break;
            case 1:
                animation.setDuration(DURATION_TIME_1);
                animation.setInterpolator(new LinearInterpolator());
                mBallPoints.get(5).setOffsetY(animatedValue * offset);
                mBallPoints.get(6).setOffsetY(animatedValue * offset);
                mBallPoints.get(7).setOffsetY(animatedValue * offset);
                mBallPoints.get(1).setOffsetY(animatedValue * offset);
                mBallPoints.get(0).setOffsetY(animatedValue * offset);
                mBallPoints.get(11).setOffsetY(animatedValue * offset);
                break;
            case 2:
                animation.setDuration(DURATION_TIME_2);
                animation.setInterpolator(new AccelerateInterpolator());
                for (int i = 0; i < mBallPoints.size(); i++)
                {
                    if (i > 10 || i < 8)
                    {
                        mBallPoints.get(i).setOffsetY(animatedValue * offset + offset);
                    }
                    else
                    {
                        mBallPoints.get(i).setOffsetY(animatedValue * offset);
                    }
                }
                break;
            case 3:
                animation.setDuration(DURATION_TIME_3);
                animation.setInterpolator(new DecelerateInterpolator());

                mBallPoints.get(8).setOffsetY(animatedValue * offset + offset);
                mBallPoints.get(9).setOffsetY(animatedValue * offset + offset);
                mBallPoints.get(10).setOffsetY(animatedValue * offset + offset);


                mBallPoints.get(5).setOffsetX(animatedValue * offset);
                mBallPoints.get(6).setOffsetX(animatedValue * offset);
                mBallPoints.get(7).setOffsetX(animatedValue * offset);
                mBallPoints.get(1).setOffsetX(-animatedValue * offset);
                mBallPoints.get(0).setOffsetX(-animatedValue * offset);
                mBallPoints.get(11).setOffsetX(-animatedValue * offset);
                break;
            case 4:
                animation.setDuration(DURATION_TIME_4);
                mPaint.setAlpha((int) ((1 - animatedValue) * 255));
                break;
        }
    }

    @Override
    public void onAnimationRepeat(Animator animation)
    {
        if (++mCurrAnimatorState > FINAL_STATE)
        {//还原到第一阶段
            mCurrAnimatorState = 0;
            for (CirclePoint point : mBallPoints)
            {
                point.setOffsetY(0);
                point.setOffsetX(0);
            }
            mPaint.setAlpha(255);
        }
    }

}

总结

小伙伴们,要是想看更多细节,可以前往文章最下面的Github链接,如果大家觉得ok的话,希望能给个喜欢,最渴望的是在Github上给个star。谢谢了。

如果大家有什么更好的方案,或者想要实现的加载效果,可以给我留言或者私信我,我会想办法实现出来给大家。谢谢支持。

Github:zyao89/ZCustomView

作者:Zyao89;转载请保留此行,谢谢;

个人博客:https://zyao89.cn

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 212,657评论 6 492
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 90,662评论 3 385
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 158,143评论 0 348
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 56,732评论 1 284
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 65,837评论 6 386
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 50,036评论 1 291
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 39,126评论 3 410
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 37,868评论 0 268
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 44,315评论 1 303
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 36,641评论 2 327
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 38,773评论 1 341
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 34,470评论 4 333
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 40,126评论 3 317
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 30,859评论 0 21
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 32,095评论 1 267
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 46,584评论 2 362
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 43,676评论 2 351

推荐阅读更多精彩内容

  • Android 自定义View的各种姿势1 Activity的显示之ViewRootImpl详解 Activity...
    passiontim阅读 171,856评论 25 707
  • 发现 关注 消息 iOS 第三方库、插件、知名博客总结 作者大灰狼的小绵羊哥哥关注 2017.06.26 09:4...
    肇东周阅读 12,066评论 4 62
  • “所以金刚经上说要无人相,无我相,无众生相,无寿者相。”白衣书生说完,拿起面前的茶杯一饮而尽。禅师点头,为书生...
    山海花开阅读 275评论 0 0
  • 当橘子失去了酸甜 你还会为她冲动吗 还是你味觉错乱了 怎么都尝不出她的颜色 当你围坐在火炉旁 才开始怀念那漫溢赤膊...
    下午和风阅读 200评论 0 2
  • 七月,狮泉河畔的红柳又开花了,水鸟在河面时而低飞觅食时而翱翔展翅,鱼儿在河里欢快地跳跃着欢唱着,羊儿安详地吃着草,...
    厚土高天阅读 1,603评论 0 4