还是我们自定View的那几个步骤:
1、自己定义View的属性
2、在View的构造方法中获得我们自己定义的属性
3、重写onMesure (不是必须)
4、重写onDraw
自己定义View的属性
<? xml version="1.0" encoding="utf-8"?>
<resources>
<attr name="firstColor" format="color" />
<attr name="secondColor" format="color" />
<attr name="circleWidth" format="dimension" />
<attr name="speed" format="integer" /> <declare-styleable name="progressStyle">
<attr name="firstColor"/>
<attr name="secondColor"/>
<attr name="circleWidth"/>
<attr name="speed"/>
</declare-styleable>
</resources>
自己定义View,而且使用自己定义的View
public class ProgressView extends View { /**
* 第一圈的颜色
*/
private int mFirstColor;
/**
* 第二圈的颜色
*/
private int mSecondColor;
/**
* 圈的宽度
*/
private int mCircleWidth;
/**
* 画笔
*/
private Paint mPaint;
/**
* 当前进度
*/
private int mProgress; /**
* 速度
*/
private int mSpeed; /**
* 是否应该開始下一个
*/
private boolean isNext = false;
public ProgressView(Context context) {
this(context, null);
} public ProgressView(Context context, AttributeSet attrs) {
this(context, attrs, 0);
} public ProgressView(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
TypedArray typedArray = context.getTheme().obtainStyledAttributes(attrs, R.styleable.progressStyle,defStyleAttr,0); int n = typedArray.getIndexCount(); for (int i =0 ;i < n ; i ++){
int attr =typedArray.getIndex(i);
switch (attr){//这里的0,1,2。3相应attrs中declare-styleable name="progressStyle"数组元素的顺序。我是为了举例方便,实际开发中不要这样写
case 0:
mFirstColor = typedArray.getColor(attr, Color.BLACK);
break;
case 1:
mSecondColor = typedArray.getColor(attr, Color.RED);
break;
case 2:
mCircleWidth = typedArray.getDimensionPixelSize(attr,(int) TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_SP,
16,getResources().getDisplayMetrics()));
break;
case 3:
mSpeed = typedArray.getInt(attr,20);
break;
}
}
typedArray.recycle();
mPaint = new Paint();
startMyThread();
} @Override
protected void onDraw(Canvas canvas) {
int center = getWidth() / 2; // 获取圆心的x坐标
int radius = (center - mCircleWidth)/2 ;// 半径 mPaint.setAntiAlias(true);
mPaint.setStrokeWidth(mCircleWidth);
mPaint.setStyle(Paint.Style.STROKE); RectF rectf = new RectF(center-radius,center-radius,center+radius,center+radius);
//颜色的切换
if(!isNext){
canvas.save();
mPaint.setColor(mFirstColor);// 设置圆环的颜色
canvas.drawCircle(center,center,radius,mPaint);//划出圆圈
mPaint.setColor(mSecondColor);
canvas.drawArc(rectf,-90,mProgress,false,mPaint);//依据进度画圆弧
canvas.restore();
}else {
canvas.save();
mPaint.setColor(mSecondColor);// 设置圆环的颜色
canvas.drawCircle(center,center,radius,mPaint);
mPaint.setColor(mFirstColor);
canvas.drawArc(rectf,-90,mProgress,false,mPaint);
canvas.restore();
}
} private void startMyThread() {
new Thread(new Runnable() {
@Override
public void run() {
while (true){
mProgress++;//进度
if(mProgress == 360){//当360度时候值变为初始状态
mProgress = 0; if(!isNext){//设置是否切换颜色开关
isNext = true;
}else {
isNext = false;
} } postInvalidate(); try {
Thread.sleep(mSpeed);
}catch (InterruptedException e){
e.printStackTrace();
}
}
}
}).start();;
}
<strong>
</strong>
以上代码就是自己定义View的所有代码,使用的话没什么多说的 直接在Xml中引用这个新建的ProgressView就能够了
重画ondraw 不多解释直接看代码
@Override
protected void onDraw(Canvas canvas) {
int center = getWidth() / 2; // 获取圆心的x坐标
int radius = (center - mCircleWidth)/2 ;// 半径 mPaint.setAntiAlias(true);
mPaint.setStrokeWidth(mCircleWidth);
mPaint.setStyle(Paint.Style.STROKE); RectF rectf = new RectF(center-radius,center-radius,center+radius,center+radius); if(!isNext){
canvas.save();
mPaint.setColor(mFirstColor);// 设置圆环的颜色
canvas.drawCircle(center,center,radius,mPaint);//划出圆圈
mPaint.setColor(mSecondColor);
canvas.drawArc(rectf,-90,mProgress,false,mPaint);//依据进度画圆弧
canvas.restore();
}else {
canvas.save();
mPaint.setColor(mSecondColor);// 设置圆环的颜色
canvas.drawCircle(center,center,radius,mPaint);
mPaint.setColor(mFirstColor);
canvas.drawArc(rectf,-90,mProgress,false,mPaint);
canvas.restore();
}
}
效果是不是和progress相似呢 。自己试试看吧
由于有的人说效果非常生硬,我就做了个完整的gif图,速度是能够调节的,依据不同的速度值。移动能够调剂频率