android自定义进度条渐变色View的实例代码

 更新时间:2014年01月10日 16:26:07   投稿:shangke  
这篇文章主要介绍了android自定义进度条渐变色View的实例代码,有需要的朋友可以参考一下

最近在公司,项目不是很忙了,偶尔看见一个兄台在CSDN求助,帮忙要一个自定义的渐变色进度条,我当时看了一下进度条,感觉挺漂亮的,就尝试的去自定义view实现了一个,废话不说,先上图吧!

这个自定义的view,完全脱离了android自带的ProgressView,并且没使用一张图片,这样就能更好的降低程序代码上的耦合性!

下面我贴出代码  ,大概讲解一下实现思路吧!

复制代码 代码如下:

package com.spring.progressview;

import android.content.Context;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.LinearGradient;
import android.graphics.Matrix;
import android.graphics.Paint;
import android.graphics.RectF;
import android.graphics.Shader;
import android.util.AttributeSet;
import android.view.View;

/***
 * 自定义进度条
 * @author spring sky
 * Email:vipa1888@163.com
 * 创建时间:2014-1-6下午3:28:51
 */
public class SpringProgressView extends View {
 
 /**分段颜色*/
 private static final int[] SECTION_COLORS = {Color.GREEN,Color.YELLOW,Color.RED};
 /**进度条最大值*/
 private float maxCount;
 /**进度条当前值*/
 private float currentCount;
 /**画笔*/
 private Paint mPaint;
 private int mWidth,mHeight;
 
 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) {
 }

 @Override
 protected void onDraw(Canvas canvas) {
  super.onDraw(canvas);
  mPaint = new Paint();
  mPaint.setAntiAlias(true);
  int round = mHeight/2;
  System.out.println("max="+maxCount + "  current="+currentCount);
  mPaint.setColor(Color.rgb(71, 76, 80));
  RectF rectBg = new RectF(0, 0, mWidth, mHeight);
  canvas.drawRoundRect(rectBg, round, round, mPaint);
  mPaint.setColor(Color.BLACK);
  RectF rectBlackBg = new RectF(2, 2, mWidth-2, mHeight-2);
  canvas.drawRoundRect(rectBlackBg, round, round, mPaint);
  
  float section = currentCount/maxCount;
  RectF rectProgressBg = new RectF(3, 3, (mWidth-3)*section, mHeight-3);
  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(3, 3, (mWidth-3)*section, mHeight-3, 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
  */
 public void setCurrentCount(float currentCount) {
  this.currentCount = currentCount > maxCount ? maxCount : currentCount;
  invalidate();
 }
 
 public float getMaxCount() {
  return maxCount;
 }
 
 public float getCurrentCount() {
  return currentCount;
 }
 
 @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);
 }
 


}


以上代码就是该控件的全部核心代码了
具体思路:
1.进度条,其实就是一个最大值和最小值的比例值,这个比例就是 当前值/最大值;
2.自定义的圆角问题,只要还是用到了Canvar的画板的drawRoundRect ;
3.渐变色:LinearGradient对象渲染,具体渲染的比例要自己计算,目前我的程序提供3中颜色渲染,具体规则是:
(1)当进度条占最大值的三分之一以下,则提供一种颜色
   (2)当最大值超过三分之一话,就区分是否超过三分之二,如果超过则用三种,否则用两种颜色,因为三种颜色各占总进度条的三分之一,这是一个初中数据的问题,自己慢慢画图吧!
4.怎么把进度条放在一个有圆角背景的上面,这个就是绘制两个圆角长方形:第一个作为背景,第二个作为进度条的实体,具体第二个进度的实体占多长,就是当前 currentCount/maxCount*自定义View的长度   ;


其他的,没啥技术难点了,做这种自定义控件,最重要的是,自定要根据人家的效果图,看懂实现思路,具体代码简历在思路上的,否则只会纸上谈兵!如果看不懂,就要多画图,具体的一步步计算,天长地久,也就能“练”出来了!

下面提供一个demo下载地址:http://xiazai.jb51.net/201401/yuanma/SpringProgressDemo(jb51.net).zip

相关文章

  • Android 状态管理之Lifecycle浅析

    Android 状态管理之Lifecycle浅析

    这篇文章主要介绍了Android 状态管理之Lifecycle浅析,Lifecycle主要用于Activity、Fragment这一类具有状态的组件的状态监听,更多相关资料介绍需要的小伙伴可以参考下面文章内容
    2022-06-06
  • Android编程设计模式之原型模式实例详解

    Android编程设计模式之原型模式实例详解

    这篇文章主要介绍了Android编程设计模式之原型模式,结合实例形式详细分析了Android设计模式之原型模式的概念、原理、定义、使用方法及相关注意事项,需要的朋友可以参考下
    2017-12-12
  • Android实现网络多线程断点续传下载实例

    Android实现网络多线程断点续传下载实例

    本示例介绍在Android平台下通过HTTP协议实现断点续传下载。具有一定的参考价值,感兴趣的小伙伴们可以参考一下。
    2016-10-10
  • Android中Retrofit库的高级使用与原理

    Android中Retrofit库的高级使用与原理

    在 Android 开发中,网络请求是一个极为关键的部分,Retrofit 作为一个强大的网络请求库,能够简化开发流程,提供高效的网络请求能力,本文将深入介绍 Retrofit 的高级使用与原理,帮助读者更全面地理解和应用这一库,需要的朋友可以参考下
    2023-08-08
  • 21天学习android开发教程之MediaPlayer

    21天学习android开发教程之MediaPlayer

    21天学习android开发教程之MediaPlayer,MediaPlayer可以播放音频和视频,操作相对简单,感兴趣的小伙伴们可以参考一下
    2016-02-02
  • 超实用的android网络工具类

    超实用的android网络工具类

    这篇文章主要为大家详细介绍了超实用的android网络工具类,具有一定的参考价值,感兴趣的小伙伴们可以参考一下
    2018-04-04
  • Android软件启动动画及动画结束后跳转的实现方法

    Android软件启动动画及动画结束后跳转的实现方法

    这篇文章主要介绍了Android软件启动动画及动画结束后跳转的实现方法,实例分析了Android图片播放及定时器的相关使用技巧,非常具有使用价值,需要的朋友可以参考下
    2015-10-10
  • Android studio配置国内镜像源的实现

    Android studio配置国内镜像源的实现

    这篇文章主要介绍了Android studio配置国内镜像源的实现,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧
    2020-11-11
  • Android inflater 用法及不同点

    Android inflater 用法及不同点

    在 实际开发中LayoutInflater这个类还是非常有用的,它的作用类似于findViewById()。这篇文章主要介绍了Android inflater 用法,需要的朋友可以参考下
    2018-11-11
  • PHP autoload 机制详解

    PHP autoload 机制详解

    本文主要介绍 PHP autoload 机制,这里整理了详细的知识资料供大家学习参考,希望能帮助有需要的小伙伴
    2016-08-08

最新评论