前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >Android 进度条按钮实现(ProgressButton)

Android 进度条按钮实现(ProgressButton)

作者头像
用户1289394
发布2021-07-30 16:26:56
1.8K0
发布2021-07-30 16:26:56
举报
文章被收录于专栏:Java学习网

有些App在点击下载按钮的时候,可以在按钮上显示进度,我们可以通过继承原生Button,重写onDraw来实现带进度条的按钮。

Github:https://github.com/imcloudfloating/ProgressBar

1.效果:

2.原理:

创建三个GradientDrawable作为按钮背景、进度条背景和进度条前景,通过计算进度条的百分比来设置宽度,然后调用invalidate()重绘。GradientDrawable设置颜色、圆角等参数,当然你也可以直接加载xml作为背景。

3.自定义参数:

在values目录建一个attrs.xml文件

代码语言:javascript
复制
 1 <?xml version="1.0" encoding="utf-8"?>  2 <resources>  3  4 <attr name="progressColor" format="color" />  5 <attr name="progressBackColor" format="color" />  6 <attr name="progress" format="integer" />  7 <attr name="minProgress" format="integer" />  8 <attr name="maxProgress" format="integer" />  9 10 <declare-styleable name="ProgressButton"> 11 <attr name="progressColor" /> 12 <attr name="progressBackColor" /> 13 <attr name="buttonColor" format="color" /> 14 <attr name="cornerRadius" format="dimension" /> 15 <attr name="progress" /> 16 <attr name="minProgress" /> 17 <attr name="maxProgress" /> 18 <attr name="progressMargin" format="dimension" /> 19 </declare-styleable> 20 21 </resources>

3.按钮类:

在setProgress方法中改变mProgress的值,然后调用invalidate()重绘,因为我这里定义了一个minProgress(默认为0),所以在计算进度条宽度的时候,当前进度和最大进度都要先减去minProgress再做除法。

代码语言:javascript
复制
if (progressWidth < mCornerRadius * 2) {  progressWidth = mCornerRadius * 2; } 当进度条宽度小于2倍圆角半径的时候,进度条的圆角就和背景的圆角不一致,所以加上了上面这段代码。
获取宽度和高度其实用getWidth()和getHeight()也可以,只不过在设计器中没法看到效果,所以我用了getMeasuredWidth()和getMeasuredHeight()。
代码语言:javascript
复制
 1 package com.cloud.customviews;  2  3 import android.content.Context;  4 import android.content.res.TypedArray;  5 import android.graphics.Canvas;  6 import android.graphics.drawable.GradientDrawable;  7 import android.support.v7.widget.AppCompatButton;  8 import android.util.AttributeSet;  9  10 public class ProgressButton extends AppCompatButton {  11  12 private float mCornerRadius = 0;  13 private float mProgressMargin = 0;  14  15 private boolean mFinish;  16  17 private int mProgress;  18 private int mMaxProgress = 100;  19 private int mMinProgress = 0;  20  21 private GradientDrawable mDrawableButton;  22 private GradientDrawable mDrawableProgressBackground;  23 private GradientDrawable mDrawableProgress;  24  25 public ProgressButton(Context context, AttributeSet attrs) {  26 super(context, attrs);  27  initialize(context, attrs);  28  }  29  30 public ProgressButton(Context context, AttributeSet attrs, int defStyle) {  31 super(context, attrs, defStyle);  32  initialize(context, attrs);  33  }  34  35 private void initialize(Context context, AttributeSet attrs) {  36 //Progress background drawable  37 mDrawableProgressBackground = new GradientDrawable();  38 //Progress drawable  39 mDrawableProgress = new GradientDrawable();  40 //Normal drawable  41 mDrawableButton = new GradientDrawable();  42  43 //Get default normal color  44 int defaultButtonColor = getResources().getColor(R.color.colorGray, null);  45 //Get default progress color  46 int defaultProgressColor = getResources().getColor(R.color.colorGreen, null);  47 //Get default progress background color  48 int defaultBackColor = getResources().getColor(R.color.colorGray, null);  49  50 TypedArray attr = context.obtainStyledAttributes(attrs, R.styleable.ProgressButton);  51  52 try {  53 mProgressMargin = attr.getDimension(R.styleable.ProgressButton_progressMargin, mProgressMargin);  54 mCornerRadius = attr.getDimension(R.styleable.ProgressButton_cornerRadius, mCornerRadius);  55 //Get custom normal color  56 int buttonColor = attr.getColor(R.styleable.ProgressButton_buttonColor, defaultButtonColor);  57 //Set normal color  58  mDrawableButton.setColor(buttonColor);  59 //Get custom progress background color  60 int progressBackColor = attr.getColor(R.styleable.ProgressButton_progressBackColor, defaultBackColor);  61 //Set progress background drawable color  62  mDrawableProgressBackground.setColor(progressBackColor);  63 //Get custom progress color  64 int progressColor = attr.getColor(R.styleable.ProgressButton_progressColor, defaultProgressColor);  65 //Set progress drawable color  66  mDrawableProgress.setColor(progressColor);  67  68 //Get default progress  69 mProgress = attr.getInteger(R.styleable.ProgressButton_progress, mProgress);  70 //Get minimum progress  71 mMinProgress = attr.getInteger(R.styleable.ProgressButton_minProgress, mMinProgress);  72 //Get maximize progress  73 mMaxProgress = attr.getInteger(R.styleable.ProgressButton_maxProgress, mMaxProgress);  74  75 } finally {  76  attr.recycle();  77  }  78  79 //Set corner radius  80  mDrawableButton.setCornerRadius(mCornerRadius);  81  mDrawableProgressBackground.setCornerRadius(mCornerRadius);  82 mDrawableProgress.setCornerRadius(mCornerRadius - mProgressMargin);  83  setBackgroundDrawable(mDrawableButton);  84  85 mFinish = false;  86  }  87  88  @Override  89 protected void onDraw(Canvas canvas) {  90 if (mProgress > mMinProgress && mProgress <= mMaxProgress && !mFinish) {  91 //Calculate the width of progress  92 float progressWidth =  93 (float) getMeasuredWidth() * ((float) (mProgress - mMinProgress) / mMaxProgress - mMinProgress);  94  95 //If progress width less than 2x corner radius, the radius of progress will be wrong  96 if (progressWidth < mCornerRadius * 2) {  97 progressWidth = mCornerRadius * 2;  98  }  99 100 //Set rect of progress 101 mDrawableProgress.setBounds((int) mProgressMargin, (int) mProgressMargin, 102 (int) (progressWidth - mProgressMargin), getMeasuredHeight() - (int) mProgressMargin); 103 104 //Draw progress 105  mDrawableProgress.draw(canvas); 106 107 if (mProgress == mMaxProgress) { 108  setBackgroundDrawable(mDrawableButton); 109 mFinish = true; 110  } 111  } 112 super.onDraw(canvas); 113  } 114 115 /** 116  * Set current progress 117 */ 118 public void setProgress(int progress) { 119 if (!mFinish) { 120 mProgress = progress; 121  setBackgroundDrawable(mDrawableProgressBackground); 122  invalidate(); 123  } 124  } 125 126 public void setMaxProgress(int maxProgress) { 127 mMaxProgress = maxProgress; 128  } 129 130 public void setMinProgress(int minProgress) { 131 mMinProgress = minProgress; 132  } 133 134 public void reset() { 135 mFinish = false; 136 mProgress = mMinProgress; 137  } 138 }

使用:

代码语言:javascript
复制
 1 <com.cloud.customviews.ProgressButton  2 android:id="@+id/button_progress_green"  3  android:layout_width="270dp"  4  android:layout_height="wrap_content"  5  android:layout_marginTop="4dp"  6  android:textAllCaps="false"  7  android:textColor="@color/colorWhite"  8  android:text="@string/button_progress"  9  app:cornerRadius="8dp" 10  app:progressMargin="2dp" 11  app:progressColor="@color/colorGreen" 12  app:buttonColor="@color/colorGreen" />
本文参与 腾讯云自媒体同步曝光计划,分享自微信公众号。
原始发表:2021-07-16,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 Java学习网 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 1.效果:
  • 2.原理:
  • 3.自定义参数:
  • 3.按钮类:
  • 使用:
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档