简单介绍
一个圆角的渐变色progress的效果,加载时能从0增长到targetCount(如果需要改变颜色,直接在
private static final int[] SECTION_COLORS = {Color.parseColor("#FF62EBEE"), Color.parseColor("#FF50E2FB"), Color.parseColor("#FF4CE1FD")};
这里改下就ok了,自定义你懂得,自己改改就好了)
如何用这个效果在xml中使用该自定义控件
设置最大值setMaxCount(float maxCount)
设置当前显示值setTargetCount(float targetCount)
上代码import android.animation.ValueAnimator;import android.content.Context;import android.graphics.Canvas;import android.graphics.Color;import android.graphics.LinearGradient;import android.graphics.Paint;import android.graphics.RectF;import android.graphics.Shader;import android.os.Handler;import android.os.Looper;import android.os.Message;import android.util.AttributeSet;import android.view.View;import android.view.animation.AccelerateDecelerateInterpolator;/***
* 自定义进度条
*
* @author spring sky
* Email:vipa1888@163.com
* 创建时间:2014-1-6下午3:28:51
* @updatedauthor stefan
* 修改时间:2016-12-19下午1:43:03
*/public class SpringProgressView extends View { /**
* 分段颜色
*/
private static final int[] SECTION_COLORS = {Color.parseColor("#FF62EBEE"), Color.parseColor("#FF50E2FB"), Color.parseColor("#FF4CE1FD")}; /**
* 进度条最大值
*/
private float maxCount; /**
* 进度条当前值
*/
private float currentCount = 0; /**
* 目标值
*/
private float targetCount; private int mBackGroundColor = Color.parseColor("#26000000"); /**
* 当前背景宽
*/
private float mCurrentBgWidth = 0; /**
* 当前背景高度
*/
private float mCurrentBgHeight = 0; /**
* 画笔
*/
private Paint mPaint, mBgPaint; private int mWidth, mHeight; float speed = 20f, bgSpeed = 2f; private Object[] mLock = new Object[]{}; private boolean needShowBgAnimDelay; private long DURATION; public SpringProgressView(Context context, AttributeSet attrs, int defStyleAttr) { super(context, attrs, defStyleAttr);
initView(context);
} public SpringProgressView(Context context, AttributeSet attrs) { super(context, attrs);
initView(context);
} public SpringProgressView(Context context) { super(context);
initView(context);
} private void initView(Context context) {
mPaint = new Paint();
mPaint.setAntiAlias(true);
mPaint.setColor(Color.rgb(71, 76, 80));
mBgPaint = new Paint();
mBgPaint.setAntiAlias(true);
mBgPaint.setColor(mBackGroundColor);
} @Override
protected void onDraw(Canvas canvas) { super.onDraw(canvas); int round = (int) (mCurrentBgHeight / 2);
RectF rectBlackBg = new RectF(0, 0, mCurrentBgWidth, mCurrentBgHeight);
canvas.drawRoundRect(rectBlackBg, round, round, mBgPaint); float section = currentCount / maxCount;
RectF rectProgressBg = new RectF(0, 0, mWidth * section, mCurrentBgHeight); if (section <= 1.0f / 3.0f) { if (section != 0.0f) {
mPaint.setColor(SECTION_COLORS[0]);
} else {
mPaint.setColor(Color.TRANSPARENT);
}
} else { int count = (section <= 1.0f / 3.0f * 2) ? 2 : 3; int[] colors = new int[count];
System.arraycopy(SECTION_COLORS, 0, colors, 0, count); float[] positions = new float[count]; if (count == 2) {
positions[0] = 0.0f;
positions[1] = 1.0f - positions[0];
} else {
positions[0] = 0.0f;
positions[1] = (maxCount / 3) / currentCount;
positions[2] = 1.0f - positions[0] * 2;
}
positions[positions.length - 1] = 1.0f;
LinearGradient shader = new LinearGradient(0, 0, mWidth * section, mCurrentBgHeight, colors, null, Shader.TileMode.MIRROR);
mPaint.setShader(shader);
}
canvas.drawRoundRect(rectProgressBg, round, round, mPaint);
} private int dipToPx(int dip) { float scale = getContext().getResources().getDisplayMetrics().density; return (int) (dip * scale + 0.5f * (dip >= 0 ? 1 : -1));
} /***
* 设置最大的进度值
*
* @param maxCount
*/
public void setMaxCount(float maxCount) { this.maxCount = maxCount;
} /***
* 设置当前的进度值
*
* @param currentCount
*/
private void setCurrentCount(float currentCount) { synchronized (mLock) { this.currentCount = currentCount > targetCount ? targetCount : currentCount;
invalidate();
}
} /***
* 设置当前的进度值
*
* @param currentCount
*/
private void setCurrentBgWidth(float currentCount) { synchronized (mLock) { this.mCurrentBgWidth = currentCount > mWidth ? mWidth : currentCount;
invalidate();
}
} /***
* 设置当前的进度值
*
* @param currentCount
*/
private void setCurrentBgHeight(float currentCount) { synchronized (mLock) { this.mCurrentBgHeight = currentCount > mHeight ? mHeight : currentCount;
invalidate();
}
} public float getTargetCount() { return targetCount;
} public float getMaxCount() { return maxCount;
} public float getCurrentCount() { return currentCount;
} public void setTargetCount(float targetCount) { if (targetCount != 0 && targetCount
this.targetCount = targetCount > maxCount ? maxCount : targetCount;
reset();
ValueAnimator animator = ValueAnimator.ofFloat(currentCount, targetCount);
animator.setInterpolator(new AccelerateDecelerateInterpolator());
DURATION = (long) (targetCount * speed);
animator.setDuration(DURATION);
animator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() { @Override
public void onAnimationUpdate(ValueAnimator animation) {
currentCount = (float) animation.getAnimatedValue();
mHandler.sendEmptyMessageDelayed(1, 100);
}
});
animator.start(); if (mHeight != 0) {
startBgAnim();
} else needShowBgAnimDelay = true;
} private void startBgAnim() {
needShowBgAnimDelay = false;
ValueAnimator animatorWidth = ValueAnimator.ofFloat(mCurrentBgWidth, mWidth);
animatorWidth.setInterpolator(new AccelerateDecelerateInterpolator());
animatorWidth.setDuration((long) ((mWidth) * bgSpeed));
animatorWidth.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() { @Override
public void onAnimationUpdate(ValueAnimator animation) {
mCurrentBgWidth = (float) animation.getAnimatedValue();
mHandler.sendEmptyMessageDelayed(2, 100);
}
});
animatorWidth.start();
ValueAnimator animatorHeight = ValueAnimator.ofFloat(mCurrentBgHeight, mHeight);
animatorHeight.setInterpolator(new AccelerateDecelerateInterpolator());
animatorHeight.setDuration((long) ((mWidth) * bgSpeed));
animatorHeight.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() { @Override
public void onAnimationUpdate(ValueAnimator animation) {
mCurrentBgHeight = (float) animation.getAnimatedValue();
mHandler.sendEmptyMessageDelayed(3, 100);
}
});
animatorHeight.start();
} private void reset() {
currentCount = 0;
mCurrentBgWidth = 0;
mCurrentBgHeight = 0;
invalidate();
} @Override
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { int widthSpecMode = MeasureSpec.getMode(widthMeasureSpec); int widthSpecSize = MeasureSpec.getSize(widthMeasureSpec); int heightSpecMode = MeasureSpec.getMode(heightMeasureSpec); int heightSpecSize = MeasureSpec.getSize(heightMeasureSpec); if (widthSpecMode == MeasureSpec.EXACTLY || widthSpecMode == MeasureSpec.AT_MOST) {
mWidth = widthSpecSize;
} else {
mWidth = 0;
} if (heightSpecMode == MeasureSpec.AT_MOST || heightSpecMode == MeasureSpec.UNSPECIFIED) {
mHeight = dipToPx(15);
} else {
mHeight = heightSpecSize;
}
setMeasuredDimension(mWidth, mHeight); if (needShowBgAnimDelay)
startBgAnim();
} private Handler mHandler = new Handler(Looper.getMainLooper()) { @Override
public void handleMessage(Message msg) { super.handleMessage(msg); switch (msg.what) { case 1:
setCurrentCount(currentCount); break; case 2:
setCurrentBgWidth(mCurrentBgWidth); break; case 3:
setCurrentBgHeight(mCurrentBgHeight); break;
}
}
};
}