Android自定义圆形进度条
Android自定义圆形进度条
github地址:https://github.com/opq1289/CircleProgressView
效果图:
无动画:
有动画:
整圆:
切割圆:
具体步骤:
1. 绘制最基础的两个圆
定义两个画笔:
//进度条画笔
mProgressPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
mProgressPaint.setStyle(Paint.Style.STROKE);
mProgressPaint.setStrokeWidth(30);
mProgressPaint.setColor(Color.parseColor("#d81b60"));
//背景圆画笔
mBackgroundPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
mBackgroundPaint.setStyle(Paint.Style.STROKE);
mBackgroundPaint.setStrokeWidth(30);
mBackgroundPaint.setColor(Color.parseColor("#f1f1f1"));
复制代码
画圆:
mRectf = new RectF(0, 0, 200, 200);
canvas.drawCircle(100, 100, 100, mBackgroundPaint);
canvas.drawArc(mRectf, 0, 120, false, mProgressPaint);
复制代码
边缘被切割,增加参数进度条宽度,优化边缘:
private void initPaint() {//进度条画笔mProgressPaint = new Paint(Paint.ANTI_ALIAS_FLAG);mProgressPaint.setStyle(Paint.Style.STROKE);mProgressPaint.setStrokeWidth(mProgressWidth);mProgressPaint.setColor(Color.parseColor("#d81b60"));//背景圆画笔mBackgroundPaint = new Paint(Paint.ANTI_ALIAS_FLAG);mBackgroundPaint.setStyle(Paint.Style.STROKE);mBackgroundPaint.setStrokeWidth(mProgressWidth);mBackgroundPaint.setColor(Color.parseColor("#f1f1f1"));
}@Override
protected void onDraw(Canvas canvas) {super.onDraw(canvas);mRectf = new RectF(mProgressWidth / 2, mProgressWidth / 2, 200 - mProgressWidth / 2, 200 - mProgressWidth / 2);canvas.drawCircle(100, 100, 100 - mProgressWidth / 2, mBackgroundPaint);canvas.drawArc(mRectf, 0, 120, false, mProgressPaint);
}
复制代码
2. 计算尺寸
main_activity.xml
中的布局是:
android:layout_width="100dp"
android:layout_height="100dp"
复制代码
显示布局边界后发现view的宽高是屏幕宽高:
重新设置view的尺寸:
//设置默认最小尺寸
private int mDefaultWidth = CommonUtil.dp2px(getContext(), 10);
复制代码
@Override
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {super.onMeasure(widthMeasureSpec, heightMeasureSpec);int width = measureWidth(widthMeasureSpec);int height = measureHeight(heightMeasureSpec);mViewWidth = Math.min(width, height);setMeasuredDimension(mViewWidth, mViewWidth);
}
复制代码
private int measureWidth(int widthMeasureSpec) {int width;int size = MeasureSpec.getSize(widthMeasureSpec);int mode = MeasureSpec.getMode(widthMeasureSpec);switch (mode) {case MeasureSpec.EXACTLY:width = size < mProgressWidth ? mProgressWidth : size;break;case MeasureSpec.AT_MOST:width = mDefaultWidth * 2;break;default:width = CommonUtil.getScreenWidthInPx(getContext());break;}return width;
}private int measureHeight(int heightMeasureSpec) {int height;int size = MeasureSpec.getSize(heightMeasureSpec);int mode = MeasureSpec.getMode(heightMeasureSpec);switch (mode) {case MeasureSpec.EXACTLY:height = size < mProgressWidth ? mProgressWidth : size;break;case MeasureSpec.AT_MOST:height = mDefaultWidth * 2;break;default:height = CommonUtil.getScreenHeightInPx(getContext());break;}return height;
}
复制代码
然后修改绘制:
@Override
protected void onDraw(Canvas canvas) {super.onDraw(canvas);mRectf = new RectF(mProgressWidth / 2, mProgressWidth / 2, mViewWidth - mProgressWidth / 2, mViewWidth - mProgressWidth / 2);canvas.drawCircle(mViewWidth / 2, mViewWidth / 2, mViewWidth / 2 - mProgressWidth / 2, mBackgroundPaint);canvas.drawArc(mRectf, 0, 120, false, mProgressPaint);
}
复制代码
至此,静态进度条就画好了。
将参数设置为动态,通过方法和属性设置。
<declare-styleable name="CircleProgressView"><attr name="progressWidth" format="dimension"/><attr name="progressColor" format="reference"/><attr name="backgroundColor" format="reference"/><attr name="startAngle" format="integer"/>
</declare-styleable>复制代码
public CircleProgressView(Context context, AttributeSet attrs, int defStyleAttr) {super(context, attrs, defStyleAttr);initPaint();TypedArray typedArray = getContext().obtainStyledAttributes(attrs, R.styleable.CircleProgressView, defStyleAttr, 0);mProgressWidth = (int) typedArray.getDimension(R.styleable.CircleProgressView_progressWidth, mDefaultWidth);mProgressColor = (int) typedArray.getDimension(R.styleable.CircleProgressView_progressColor, ContextCompat.getColor(getContext(), R.color.colorAccent));mStartAngle = typedArray.getInt(R.styleable.CircleProgressView_startAngle, 0);mEndAngle = typedArray.getInt(R.styleable.CircleProgressView_startAngle, 360);mBackgroundColor = (int) typedArray.getDimension(R.styleable.CircleProgressView_backgroundColor, ContextCompat.getColor(getContext(), R.color.grey_f1));typedArray.recycle();mProgressPaint.setStrokeWidth(mProgressWidth);mProgressPaint.setColor(mProgressColor);mBackgroundPaint.setStrokeWidth(mProgressWidth);mBackgroundPaint.setColor(mBackgroundColor);
}复制代码
3. 添加动画
public void setProgress(float progress) {mValueAnimator = ValueAnimator.ofFloat(progress);mValueAnimator.setDuration(1000);mValueAnimator.setInterpolator(new LinearInterpolator());mValueAnimator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {@Overridepublic void onAnimationUpdate(ValueAnimator animation) {mProgress = (float) animation.getAnimatedValue();invalidate();}});mValueAnimator.start();
}复制代码
增加进度监听:
public interface OnProgressChangedListener {void onProgressChanged(float currentProgress);
}复制代码
public void setOnProgressChangedListener(OnProgressChangedListener listener) {mListener = listener;
}复制代码
在布局中增加文字,设置居中:
4. 优化代码
增加静态和动画的区分:
/**
* @param progress 进度
* @param showAnimation 是否展示动画
*/
public void setProgress(float progress, boolean showAnimation) {mShowAnimation = showAnimation;if (mValueAnimator != null && mValueAnimator.isRunning()) {mValueAnimator.cancel();}if (mShowAnimation) {mValueAnimator = ValueAnimator.ofFloat(progress);mValueAnimator.setDuration(mDuration);mValueAnimator.setInterpolator(new LinearInterpolator());mValueAnimator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {@Overridepublic void onAnimationUpdate(ValueAnimator animation) {mProgress = (float) animation.getAnimatedValue();if (mListener != null) {mListener.onProgressChanged(mProgress);}invalidate();}});mValueAnimator.start();} else {mProgress = progress;invalidate();}
}复制代码
设置画笔类型,增加圆头画笔:
public void setCap(Paint.Cap cap) {mProgressPaint.setStrokeCap(cap);mBackgroundPaint.setStrokeCap(cap);
}复制代码
5. 增加切割圆类型
增加进度条类型mProgressType:
/*** 整圆进度条*/
public static final int TYPE_CIRCLE = 0;
/*** 切割圆进度条*/
public static final int TYPE_CLIP = 1;复制代码
切割圆从开始角度到结束角度之间,总进度为100。所以这种情况下:总进度=终止角度 - 起始角度
设置进度的方法修改:
public void setProgress(float progress, boolean showAnimation) {mShowAnimation = showAnimation;if (mProgressType == TYPE_CLIP) {progress = (int) ((mEndAngle - mStartAngle) * 100 / 360.0f);mTotalProgress = progress;} else {mTotalProgress = 100;}if (mValueAnimator != null && mValueAnimator.isRunning()) {mValueAnimator.cancel();}if (mShowAnimation) {mValueAnimator = ValueAnimator.ofFloat(progress);mValueAnimator.setDuration(mDuration);mValueAnimator.setInterpolator(new LinearInterpolator());mValueAnimator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {@Overridepublic void onAnimationUpdate(ValueAnimator animation) {mProgress = (float) animation.getAnimatedValue();if (mListener != null) {mListener.onProgressChanged(mProgress * 100 / mTotalProgress);}invalidate();}});mValueAnimator.start();} else {mProgress = progress;invalidate();}
}复制代码
OnDraw修改,区分切割圆和整圆:
@Override
protected void onDraw(Canvas canvas) {super.onDraw(canvas);mRectf = new RectF(mProgressWidth / 2, mProgressWidth / 2, mViewWidth - mProgressWidth / 2, mViewWidth - mProgressWidth / 2);if (mProgressType == TYPE_CIRCLE) {canvas.drawCircle(mViewWidth / 2, mViewWidth / 2, mViewWidth / 2 - mProgressWidth / 2, mBackgroundPaint);canvas.drawArc(mRectf, mStartAngle, mProgress * 360 / 100, false, mProgressPaint);} else if (mProgressType == TYPE_CLIP) {canvas.drawArc(mRectf, mStartAngle, mEndAngle - mStartAngle, false, mBackgroundPaint);canvas.drawArc(mRectf, mStartAngle, mProgress * 360 / 100, false, mProgressPaint);}
}复制代码
完成。
github地址:https://github.com/opq1289/CircleProgressView
Android自定义圆形进度条相关推荐
- android自定义圆形进度条,实现动态画圆效果
自定义圆形进度条效果图如下:应用场景如动态显示分数等. view的自定义属性如下attr.xml <?xml version="1.0" encoding="UTF ...
- Android 自定义圆形进度条(圆环刻度)View
转载请注明出处http://blog.csdn.net/shallcheek/article/details/50343677 这个也刚好是公司软件最近的需求需要到的,当初最早的版本是使用美工切好的图 ...
- android 自定义圆形进度条拖动样式,android自定义圆形进度条
首先在布局文件定义Progressbar xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tool ...
- android绘制环形进度_Android动态自定义圆形进度条
这篇文章主要介绍了Android动态自定义圆形进度条,需要的朋友可以参考下 效果图: A.绘制圆环,圆弧,文本 //1.画圆环 //原点坐标 float circleX = width / 2; fl ...
- android 环形时间显示_Android_Android实现自定义圆形进度条,今天无意中发现一个圆形进度 - phpStudy...
Android实现自定义圆形进度条 今天无意中发现一个圆形进度,想想自己实现一个,如下图: 基本思路是这样的: 1.首先绘制一个实心圆 2.绘制一个白色实心的正方形,遮住实心圆 3.在圆的中心动态绘制 ...
- android自定义进度条百分比跟着走,Android studio圆形进度条 百分数跟随变化
本文实例为大家分享了Android studio圆形进度条展示的具体代码,供大家参考,具体内容如下 MainActivity import android.support.v7.app.AppComp ...
- Android 绘制圆形进度条
Android 绘制圆形进度条 最近项目上有一些需求,需要绘制圆形的进度条满足设计上和交互上的需求: 实现思路 在画布上直接绘制View,需要了解一下几点 1.需要画一个圆 2.圆圈上有不同进度的颜色 ...
- 自定义圆形进度条的实现方式
如何自定义圆形进度条哪,也就是替换一下进度条的图片而已. 先分析一下,系统对进度条如何定义的: 咱们一般情况下载布局文件中这么书写: //在布局文件里的代码<ProgressBarandroid ...
- android 自定义背景园,Android 自定义ProgressBar 进度条颜色和背景颜色
Android 自定义ProgressBar 进度条颜色和背景颜色 首先,在drawable目录下新建文件 personal_center_level_progress_bg.xmlandroid a ...
最新文章
- 人工智能应用于建筑领域新前沿
- 星巴克在GitHub中泄漏API密钥,发现者获4000美金奖励
- POJ - 3700 Missile Defence System.(dfs+最优性剪枝)
- Coding Interview Guide -- 向有序的环形单链表中插入新节点
- windowsCE异常和中断服务程序初探(=)
- Bootstrap 工具提示插件Tooltip的方法
- 「mac操作指南」WidsMob HEIC将HEIC/HEIF 转换为 JPEG/PNG/TIFF格式
- HTML5日期输入框(date)
- atmega168p与328p_ATMEGA328P-MU产品说明
- Tomcat出现中文乱码
- 【Windows】替换系统文件
- mac 当前位置打开终端
- js根据银行卡号进行判断属于哪个银行并返回银行卡类型
- 存储服务器在监控中的作用,监控项目中存储服务器IPSAN云存储方案的优劣势对比...
- 世界7条高智商测试题
- 通关4级之词汇(2021.02.26)
- 蓝牙协议spec文档免费下载官网下载(免费)
- WPF: WPF 中的 Triggers 和 VisualStateManager
- sprite(雪碧图,也叫精灵图)
- AT89C51单片机流水灯c语言程序及详解(扫盲教程)
热门文章
- MyBatis-08MyBatis注解方式之@Insert
- Oracle-内存管理解读
- Android Scroll分析
- HTML基础_Day02
- linux接收网络数据并存存储,linux网络数据包数据结构 Socket Buffer
- 导出matlab程序,Matlab数据导入导出
- git指定版本openwrt源码_[OpenWrt Wiki] LEDE源代码
- native字体尺寸自适应 react_react-native中 屏幕以及字体 大小适配
- 系统部署文档_惊喜!Alibaba架构师终于发布“微服务架构与实践”文档
- 2021-02-27 永磁同步电机 自抗扰控制 PI调节器 矢量控制 SVPWM