注意:调用直接在布局文件中用就行,setDuration直接用,也可以自己修改,颜色可以自己修改 import android.content.Context; import android.graphics.Canvas; import android.graphics.Paint; import android.graphics.Rect; import android.graphics.RectF; import android.graphics.Typeface; import android.os.CountDownTimer; import android.util.AttributeSet; import android.view.View; import com.iqilu.phonetoken.R; public class CountDownProgressBar extends View { /** * 当前进度值 */ private int currentValue ; /** * 每次扫过的角度,用来设置进度条圆弧所对应的圆心角,alphaAngle=(currentValue/maxValue)*360 */ private float alphaAngle; /** * 圆环的宽度 */ private int circleWidth = 10; /** * 画圆弧的画笔 */ private Paint circlePaint; /** * 画文字的画笔 */ private Paint textPaint; private OnFinishListener listener; private int time_x,time_y,name_y,number_y,home_y; private CountDownTimer countDownTimer; private String keyName,keyNumber,sysName = "111"; public CountDownProgressBar(Context context) { this(context, null); } public CountDownProgressBar(Context context, AttributeSet attrs) { this(context, attrs, 0); } public CountDownProgressBar(Context context, AttributeSet attrs, int defStyleAttr) { super(context, attrs, defStyleAttr); circlePaint = new Paint(); circlePaint.setAntiAlias(true); // 抗锯齿 circlePaint.setDither(true); // 防抖动 circlePaint.setStrokeWidth(circleWidth);//画笔宽度 textPaint = new Paint(); textPaint.setAntiAlias(true); textPaint.setDither(true); } @Override protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { // 分别获取期望的宽度和高度,并取其中较小的尺寸作为该控件的宽和高,并且不超过屏幕宽高 int widthPixels = this.getResources().getDisplayMetrics().widthPixels;//获取屏幕宽 int heightPixels = this.getResources().getDisplayMetrics().heightPixels;//获取屏幕高 int width = MeasureSpec.getSize(widthMeasureSpec); int hedight = MeasureSpec.getSize(heightMeasureSpec); int minWidth = Math.min(widthPixels, width); int minHedight = Math.min(heightPixels, hedight); setMeasuredDimension(Math.min(minWidth, minHedight), Math.min(minWidth, minHedight)); } @Override protected void onDraw(Canvas canvas) { time_x = this.getWidth() / 2; time_y = this.getHeight(); number_y = time_y/2; name_y = number_y/2; home_y = number_y + 100; int radius = time_x - circleWidth / 2-10; drawCircle(canvas, radius); // 绘制进度圆弧 drawText(canvas); } /** * 绘制进度圆弧 * * @param canvas 画布对象 * time_x 圆心的x和y坐标 * @param radius 圆的半径 */ private void drawCircle(Canvas canvas, int radius) { circlePaint.setShader(null); // 清除上一次的shader circlePaint.setColor(getContext().getColor(R.color.countdown_back)); // 设置底部圆环的颜色,这里使用第一种颜色 circlePaint.setStyle(Paint.Style.STROKE); // 设置绘制的圆为空心 canvas.drawCircle(time_x, time_x, radius, circlePaint); // 画底部的空心圆 RectF oval = new RectF(time_x - radius, time_x - radius, time_x + radius, time_x + radius); // 圆的外接正方形 circlePaint.setColor(getContext().getColor(R.color.mytoken_blue)); // 设置圆弧的颜色 circlePaint.setStrokeCap(Paint.Cap.ROUND); // 把每段圆弧改成圆角的 alphaAngle = currentValue * 6; canvas.drawArc(oval,90, alphaAngle, false, circlePaint); } /** * 绘制文字 * * @param canvas 画布对象 */ private void drawText(Canvas canvas) { //时间 String percent; percent = currentValue + "/" + "60s"; textPaint.setTextSize(36); // 设置要绘制的文字大小 textPaint.setTextAlign(Paint.Align.CENTER); // 设置文字居中,文字的x坐标要注意 textPaint.setColor(getContext().getColor(R.color.mytoken_blue)); // 设置文字颜色 textPaint.setStrokeWidth(0); // 注意此处一定要重新设置宽度为0,否则绘制的文字会重叠 Rect bounds = new Rect(); // 文字边框 textPaint.getTextBounds(percent, 0, percent.length(), bounds); // 获得绘制文字的边界矩形 canvas.drawText(percent, time_x, time_y-30, textPaint); // 绘制表示进度的文字 //号 textPaint.setTextSize(125); textPaint.setTypeface(Typeface.DEFAULT_BOLD); canvas.drawText(keyNumber, time_x, number_y, textPaint); // 绘制表示进度的文字 //名 textPaint.setTextSize(28); textPaint.setTypeface(Typeface.DEFAULT); textPaint.setColor(getContext().getColor(R.color.text_color_33)); canvas.drawText("NO:"+keyName, time_x, name_y, textPaint); // 绘制表示进度的文字 //固定 textPaint.setTextSize(26); textPaint.setTypeface(Typeface.DEFAULT); textPaint.setColor(getContext().getColor(R.color.text_gray)); canvas.drawText(sysName, time_x, home_y, textPaint); // 绘制表示进度的文字 } /** * 按进度显示百分比,可选择是否启用数字动画 *countDownTimer 需要cancel然后new出来 * @param duration 动画时长 */ public void setDuration(int duration,String keyName,String keyNumber, OnFinishListener listener) { this.keyName = keyName; this.keyNumber = keyNumber; this.listener = listener; currentValue = duration/1000; if(countDownTimer!=null){ countDownTimer.cancel(); countDownTimer = null; } countDownTimer = new CountDownTimer(duration,1000) { @Override public void onTick(long millisUntilFinished) { currentValue--; invalidate(); } @Override public void onFinish() { CountDownProgressBar.this.listener.onFinish(); } }; countDownTimer.start(); } public interface OnFinishListener { void onFinish(); } }
Activity中
countDownProgressBar.setDuration(timeCount,tokenName,secretNumber,new CountDownProgressBar.OnFinishListener() { @Override public void onFinish() { timeCount = 60*1000; countDownProgressBar.setDuration(timeCount,tokenName,secretNumber,this); //处理自己的方法 } });