android仿直播圆点加载效果

今天实现一个很多app中使用到的加载进度条的效果,可能我们平时数据加载都使用到的是系统自带的,但是也有很多app加载进度条的效果实现挺好看,就是三个点不停的水平跑而且是变换颜色的,其实这个效果很简单,

分析:

第一步:

第二步:

为了圆的颜色 大小,以及移动的距离都对外开放,采用了自定义属性的方式,当然也可以进行设置,

分析了后 代码就直接上了,

<?xml version="1.0" encoding="utf-8"?>
<resources>
  <declare-styleable name="CirclePointLoadView">
    <attr name="leftPointColor" format="color|reference"></attr>
    <attr name="middlePointColor" format="color|reference"></attr>
    <attr name="rightPointColor" format="color|reference"></attr>
    <attr name="radius" format="integer|reference"></attr>
    <attr name="translationDistance" format="dimension|reference"></attr>
  </declare-styleable>
</resources>

这是自定义属性,左,中,右颜色,圆的半径,以及圆x轴移动的距离

CircleItemPointView.java

是每个子view的代码,很简单就是画了圆,然后设置了下paint的颜色而已

package com.circle.load;
import android.content.Context;
import android.graphics.Canvas;
import android.graphics.Paint;
import android.support.annotation.Nullable;
import android.util.AttributeSet;
import android.view.View;
/**
 * Created by zhouguizhijxhz on 2018/5/29.
 */
public class CircleItemPointView extends View {
  private Paint mPaint;
  private int mColor;
  public CircleItemPointView(Context context) {
    this(context,null);
  }

  public CircleItemPointView(Context context, @Nullable AttributeSet attrs) {
    this(context, attrs,0);
  }

  public CircleItemPointView(Context context, @Nullable AttributeSet attrs, int defStyleAttr) {
    super(context, attrs, defStyleAttr);
    mPaint = new Paint();
    mPaint.setAntiAlias(true);
    mPaint.setDither(true);
  }

  @Override
  protected void onDraw(Canvas canvas) {
    int cx = getWidth()/2;
    int cy = getHeight()/2;
    canvas.drawCircle(cx,cy,cx,mPaint);
  }
  /**
   * 切换颜色
   */
  public void changeColor(int color){
    mColor = color;
    mPaint.setColor(color);
    invalidate();
  }
  public void setColor(int color){
    mColor = color;
    mPaint.setColor(color);
    invalidate();
  }
  /**
   * 获取当前的颜色
   */
  public int getColor() {
    return mColor;
  }
}

CirclePointLoadView.java

package com.circle.load;
import android.animation.Animator;
import android.animation.AnimatorListenerAdapter;
import android.animation.AnimatorSet;
import android.animation.ObjectAnimator;
import android.content.Context;
import android.content.res.TypedArray;
import android.graphics.Color;
import android.util.AttributeSet;
import android.view.View;
import android.view.animation.AccelerateInterpolator;
import android.widget.RelativeLayout;
/**
 * Created by zhouguizhijxhz on 2018/5/29.
 */
public class CirclePointLoadView extends RelativeLayout{
  private int defaultLeftColor = Color.parseColor("#FF8247");
  private int defaultMiddleColor = Color.parseColor("#EE4000");
  private int defaultRightColor = Color.parseColor("#CD2626");
  private int leftColor;
  private int middleColor;
  private int rightColor;
  private int defaultCircleRadius = 10;
  private int defaultTranslationDistance = 36;
  private int translationDistance;
  private static final long ANIMATION_DURATION = 400;
  private int radius;
  private CircleItemPointView leftView;
  private CircleItemPointView middleView;
  private CircleItemPointView rightView;
  private AnimatorSet spreadAnimation;
  private AnimatorSet closedAnimation;
  public CirclePointLoadView(Context context) {
    this(context,null);
  }
  public CirclePointLoadView(Context context, AttributeSet attrs) {
    this(context, attrs,0);
  }
  public CirclePointLoadView(Context context, AttributeSet attrs, int defStyleAttr) {
    super(context, attrs, defStyleAttr);
    parseAttrs(context,attrs);
    addViewToLayout(context);
  }

  private void addViewToLayout(Context context) {
    if(null==context){
      return;
    }
    leftView = createView(context);
    leftView.setColor(leftColor);
    middleView = createView(context);
    middleView.setColor(middleColor);
    rightView = createView(context);
    rightView.setColor(rightColor);
    addView(leftView);
    addView(rightView);
    addView(middleView);
  }
  /**
   * 展开动画
   */
  private void spreadAnimation() {
    ObjectAnimator leftTranslationAnimator = ObjectAnimator.ofFloat(leftView,"translationX",0,-translationDistance);
    ObjectAnimator rightTranslationAnimator = ObjectAnimator.ofFloat(rightView,"translationX",0,translationDistance);
    spreadAnimation = new AnimatorSet();
    spreadAnimation.setDuration(ANIMATION_DURATION);
    spreadAnimation.playTogether(leftTranslationAnimator,rightTranslationAnimator);
    spreadAnimation.addListener(new AnimatorListenerAdapter() {
      @Override
      public void onAnimationEnd(Animator animation) {
        closedAnimation();
      }
    });
    spreadAnimation.start();
  }

  private void closedAnimation() {
    ObjectAnimator leftTranslationAnimator = ObjectAnimator.ofFloat(leftView,"translationX",-translationDistance,0);
    ObjectAnimator rightTranslationAnimator = ObjectAnimator.ofFloat(rightView,"translationX",translationDistance,0);
    closedAnimation = new AnimatorSet();
    closedAnimation.setInterpolator(new AccelerateInterpolator());
    closedAnimation.setDuration(ANIMATION_DURATION);
    closedAnimation.playTogether(leftTranslationAnimator,rightTranslationAnimator);
    closedAnimation.addListener(new AnimatorListenerAdapter() {
      @Override
      public void onAnimationEnd(Animator animation) {
        int leftColor = leftView.getColor();
        int rightColor = rightView.getColor();
        int middleColor = middleView.getColor();
        middleView.changeColor(leftColor);
        rightView.changeColor(middleColor);
        leftView.changeColor(rightColor);
        spreadAnimation();
      }
    });
    closedAnimation.start();
  }
  public CircleItemPointView createView(Context context) {
    CircleItemPointView itemPointView = new CircleItemPointView(context);
    LayoutParams params = new LayoutParams(DensityUtils.dp2px(context,radius),DensityUtils.dp2px(context,radius));
    params.addRule(CENTER_IN_PARENT);
    itemPointView.setLayoutParams(params);
    return itemPointView;
  }
  private void parseAttrs(Context context, AttributeSet attrs) {
    if(null==context||null==attrs){
      return;
    }
    TypedArray typedArray = context.obtainStyledAttributes(attrs,R.styleable.CirclePointLoadView);
    leftColor = typedArray.getColor(R.styleable.CirclePointLoadView_leftPointColor,defaultLeftColor);
    middleColor = typedArray.getColor(R.styleable.CirclePointLoadView_middlePointColor,defaultMiddleColor);
    rightColor = typedArray.getColor(R.styleable.CirclePointLoadView_rightPointColor,defaultRightColor);
    radius = typedArray.getInteger(R.styleable.CirclePointLoadView_radius,defaultCircleRadius);
    translationDistance = (int) typedArray.getDimension(R.styleable.CirclePointLoadView_translationDistance,defaultTranslationDistance);
    translationDistance = DensityUtils.dp2px(context,translationDistance);
    typedArray.recycle();
  }

  /**
   * 开启动画
   */
  public void startLoad(){
    if(spreadAnimation==null){
      spreadAnimation();
    }
  }
  /**
   * 停止动画
   */
  public void stopLoad(){
    clearAnimation();
    leftView.setVisibility(View.GONE);
    middleView.setVisibility(View.GONE);
    rightView.setVisibility(View.GONE);
  }

  /**
   * 设置左侧颜色值
   * @param leftColor
   */
  public void setLeftColor(int leftColor) {
    this.leftColor = leftColor;
  }
  /**
   * 设置中间颜色值
   * @param middleColor
   */
  public void setMiddleColor(int middleColor) {
    this.middleColor = middleColor;
  }
  /**
   * 设置右侧颜色值
   * @param rightColor
   */
  public void setRightColor(int rightColor) {
    this.rightColor = rightColor;
  }
  /**
   * 设置圆的半径
   * @param radius
   */
  public void setRadius(int radius) {
    this.radius = radius;
  }
  /**
   * 设置动画x轴方向移动的距离
   * @param translationDistance
   */
  public void setTranslationDistance(int translationDistance) {
    translationDistance = translationDistance;
  }
}

效果图:

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持我们。

(0)

相关推荐

  • Android实现加载广告图片和倒计时的开屏布局

    这是一个android开屏布局的实例,可以用于加载广告图片和倒计时的布局.程序中设置的LayoutParams,划分额外空间比例为6分之5,具体权重比例可根据用户自己需求来自定义,异步加载广告图片,相关的Android代码. 具体实现代码如下: package cn.waps.extend; import android.app.Activity; import android.content.Context; import android.content.res.Configuration;

  • Android中Glide加载库的图片缓存配置究极指南

    零.选择Glide 为什么图片加载我首先推荐Glide? 图片加载框架用了不少,从afinal框架的afinalBitmap,Xutils的BitmapUtils,老牌框架universalImageLoader,著名开源组织square的picasso,google推荐的glide到FaceBook推出的fresco.这些我前前后后都体验过,那么面对这么多的框架,该如何选择呢?下面简单分析下我的看法. afinal和Xuils在github上作者已经停止维护了,开源社区最新的框架要属KJFra

  • Android使用控件ImageView加载图片的方法

    在 Android 加载图片一般使用 ImageView,这里简单记录一下这个控件的使用方法. 最简单就是在 xml 里直接使用 ImageView 标签: <?xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:orientation="

  • Android加载大分辨率图片到手机内存中的实例方法

    还原堆内存溢出的错误首先来还原一下堆内存溢出的错误.首先在SD卡上放一张照片,分辨率为(3776 X 2520),大小为3.88MB,是我自己用相机拍的一张照片.应用的布局很简单,一个Button一个ImageView,然后按照常规的方式,使用BitmapFactory加载一张照片并使用一个ImageView展示. 代码如下: 复制代码 代码如下: btn_loadimage.setOnClickListener(new View.OnClickListener() { @Override   

  • android异步加载图片并缓存到本地实现方法

    在android项目中访问网络图片是非常普遍性的事情,如果我们每次请求都要访问网络来获取图片,会非常耗费流量,而且图片占用内存空间也比较大,图片过多且不释放的话很容易造成内存溢出.针对上面遇到的两个问题,首先耗费流量我们可以将图片第一次加载上面缓存到本地,以后如果本地有就直接从本地加载.图片过多造成内存溢出,这个是最不容易解决的,要想一些好的缓存策略,比如大图片使用LRU缓存策略或懒加载缓存策略.今天首先介绍一下本地缓存图片. 首先看一下异步加载缓存本地代码: 复制代码 代码如下: public

  • Android中ListView异步加载图片错位、重复、闪烁问题分析及解决方案

    Android ListView异步加载图片错位.重复.闪烁分析以及解决方案,具体问题分析以及解决方案请看下文. 我们在使用ListView异步加载图片的时候,在快速滑动或者网络不好的情况下,会出现图片错位.重复.闪烁等问题,其实这些问题总结起来就是一个问题,我们需要对这些问题进行ListView的优化. 比如ListView上有100个Item,一屏只显示10个Item,我们知道getView()中convertView是用来复用View对象的,因为一个Item的对应一个View对象,而Ima

  • Android中使用RecyclerView实现下拉刷新和上拉加载

    推荐阅读:使用RecyclerView添加Header和Footer的方法                       RecyclerView的使用之HelloWorld RecyclerView 是Android L版本中新添加的一个用来取代ListView的SDK,它的灵活性与可替代性比listview更好.本文给大家介绍如何为RecyclerView添加下拉刷新和上拉加载,过去在ListView当中添加下拉刷新和上拉加载是非常方便的利用addHeaderView和addFooterVie

  • android WebView加载html5介绍

    Android设备多分辨率的问题 Android浏览器默认预览模式浏览 会缩小页面 WebView中则会以原始大小显示 Android浏览器和WebView默认为mdpi.hdpi相当于mdpi的1.5倍 ldpi相当于0.75倍 三种解决方式:1 viewport属性 2 CSS控制 3 JS控制 1 viewport属性放在HTML的<meta>中 Html代码 复制代码 代码如下: <SPANstyle="FONT-SIZE: x-small"> <

  • Android下拉刷新上拉加载控件(适用于所有View)

    前面写过一篇关于下拉刷新控件的文章下拉刷新控件终结者:PullToRefreshLayout,后来看到好多人还有上拉加载更多的需求,于是就在前面下拉刷新控件的基础上进行了改进,加了上拉加载的功能.不仅如此,我已经把它改成了对所有View都通用!可以随心所欲使用这两个功能~~ 我做了一个大集合的demo,实现了ListView.GridView.ExpandableListView.ScrollView.WebView.ImageView.TextView的下拉刷新和上拉加载.后面会提供demo的

  • android动态加载布局文件示例

    一.布局文件part.xml: 复制代码 代码如下: <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"    xmlns:tools="http://schemas.android.com/tools"    android:layout_width="match_parent"    android:layout_height="

随机推荐