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

(0)

相关推荐

  • Android控件之SeekBar的用法总结

    1 SeekBar简介 SeekBar是进度条.我们使用进度条时,可以使用系统默认的进度条:也可以自定义进度条的图片和滑块图片等. 2 SeekBar示例 创建一个activity,包含2个SeekBar. 第1个SeekBar是系统默认的SeekBar. 第2个SeekBar是自定义SeekBar,使用自定义的背景图和滑块图片. 应用层代码 package com.skywang.control; import android.os.Bundle; import android.app.Act

  • Android自定义SeekBar实现视频播放进度条

    首先来看一下效果图,如下所示: 其中进度条如下: 接下来说一说我的思路,上面的进度拖动条有自定义的Thumb,在Thumb正上方有一个PopupWindow窗口,窗口里面显示当前的播放时间.在SeekBar右边有一个文本框显示当前播放时间/总时间. step1.先来看一看PopupWindow的布局文件,seek_popu.xml,效果如下图所示: <?xml version="1.0" encoding="utf-8"?> <RelativeLa

  • Android 可拖动的seekbar自定义进度值

    最近接了个项目其中有需要要实现此功能:seekbar需要显示最左和最右值,进度要跟随进度块移动.下面通过此图给大家展示下效果,可能比文字描述要更清晰. 其实实现起来很简单,主要是思路.自定义控件的话也不难,之前我的博客也有专门介绍,这里就不再多说. 实现方案 这里是通过继承seekbar来自定义控件,这样的方式最快.主要难点在于进度的显示,其实我很的是最笨的方法,就是用了一个popwindow显示在进度条的上方,然后在移动滑块的时候实时的改变它显示的横坐标.看进度显示的核心代码: private

  • Android下修改SeekBar样式的解决办法

    SeekBar配置文件:Xml代码 复制代码 代码如下: <SeekBar              android:id="@+id/player_seekbar"             android:layout_width="245px"             android:layout_height="25px"             android:progressDrawable="@drawable/see

  • Android 七种进度条的样式

    当一个应用在后台执行时,前台界面就不会有什么信息,这时用户根本不知道程序是否在执行.执行进度如何.应用程序是否遇到错误终止等,这时需要使用进度条来提示用户后台程序执行的进度.Android系统提供了两大类进度条样式,长形进度条(progress-BarStyleHorizontal) 和圆形进度条(progressBarStyleLarge).进度条用处很多,比如,应用程序装载资源和网络连接时,可以提示用户稍等,这一类进度条只是代表应用程序中某一部分的执行情况,而整个应用程序执行情况呢,则可以通

  • Android 动态改变SeekBar进度条颜色与滑块颜色的实例代码

    遇到个动态改变SeekBar进度条颜色与滑块颜色的需求,有的是根据不同进度改变成不同颜色. 对于这个怎么做呢?大家都知道设置下progressDrawable与thumb即可,但是这样设置好就是确定的了,要动态更改需要在代码里实现. 用shape进度条与滑块 SeekBar设置 代码里动态设置setProgressDrawable与setThumb 画图形,大家都比较熟悉,background是背景图,secondaryProgress第二进度条,progress进度条: <layer-list

  • Android中实现Webview顶部带进度条的方法

    写这篇文章,做份备忘,简单滴展示一个带进度条的Webview示例,进度条位于Webview上面. 示例图如下: 主Activity代码: 复制代码 代码如下: package com.droidyue.demo.webviewprogressbar; import android.app.Activity; import android.os.Bundle; import android.view.Menu; import android.view.View; import android.vi

  • Android自定义垂直拖动seekbar进度条

    Android自带的SeekBar是水平的,要垂直的,必须自己写一个类,继承SeekBar. 一个简单的垂直SeekBar的例子: (但是它其实是存在一些问题的.不过要是满足基本需要还是可以凑合的) package com.example.helloverticalseekbar; import android.content.Context; import android.graphics.Canvas; import android.util.AttributeSet; import and

  • Android自定义竖直方向SeekBar多色进度条

    写在前面 因为有这样的一个场景,需要实现竖直方向的多色进度条,然后在网上也找了下,没看到符合需要的,于是自定义了一个,效果如下: 具体实现 本来想定义水平的,然后旋转一下,后来发现还不如直接定义竖直方向来的直接,就直接在竖直方向画了下. 首先讲一下思路,就是通过继承View,然后通过onDraw()方法进行绘制.具体绘制的时候,需要处理一些小细节. 比如,我们需要画一个圆形的滑动块,那么我们的背景色带就不能把整个宽度占满,要不然,小圆块只能和色带一样宽了,效果不是很好看,所以在绘制的时候应该把背

  • android之SeekBar控件用法详解

    MainActivity.java package com.example.mars_2400_seekbar; import android.support.v7.app.ActionBarActivity; import android.support.v7.app.ActionBar; import android.support.v4.app.Fragment; import android.app.Activity; import android.os.Bundle; import a

随机推荐