如何在Android中更改进度条的进度颜色

我在我的Android应用程序中使用水平进度条,我想改变其进度颜色(默认为黄色)。 我怎样才能使用code (而不是XML)?

对不起,这不是答案,但是是什么推动了从代码中设置它的要求? 如果定义正确, .setProgressDrawable应该可以正常工作

 <layer-list xmlns:android="http://schemas.android.com/apk/res/android"> <item android:id="@android:id/background"> <shape> <corners android:radius="5dip" /> <gradient android:startColor="#ff9d9e9d" android:centerColor="#ff5a5d5a" android:centerY="0.75" android:endColor="#ff747674" android:angle="270" /> </shape> </item> <item android:id="@android:id/secondaryProgress"> <clip> <shape> <corners android:radius="5dip" /> <gradient android:startColor="#80ffd300" android:centerColor="#80ffb600" android:centerY="0.75" android:endColor="#a0ffcb00" android:angle="270" /> </shape> </clip> </item> <item android:id="@android:id/progress"> <clip> <shape> <corners android:radius="5dip" /> <gradient android:startColor="@color/progress_start" android:endColor="@color/progress_end" android:angle="270" /> </shape> </clip> </item> </layer-list> 

对于水平ProgressBar,也可以使用ColorFilter ,如下所示:

 progressBar.getProgressDrawable().setColorFilter( Color.RED, android.graphics.PorterDuff.Mode.SRC_IN); 

如果progressBar不确定,则使用getIndeterminateDrawable()而不是getProgressDrawable()

红色的ProgressBar使用彩色滤光片

由于棒棒糖(API 21),你可以设置进度色彩:

 progressBar.setProgressTintList(ColorStateList.valueOf(Color.RED)); 

红色ProgressBar使用进度色调

对于我不确定的进度条(微调),我只是在drawable上设置一个颜色过滤器。 很好,只是一条线。

将颜色设置为红色的示例:

 ProgressBar spinner = new android.widget.ProgressBar( context, null, android.R.attr.progressBarStyle); spinner.getIndeterminateDrawable().setColorFilter(0xFFFF0000, android.graphics.PorterDuff.Mode.MULTIPLY); 

在这里输入图像描述

这不是编程,但我认为它可以帮助很多人! 我尝试了很多,最有效的方法是将这些行添加到我的ProgressBar的.xml文件中:

  android:indeterminate="true" android:indeterminateTintMode="src_atop" android:indeterminateTint="@color/secondary" 

所以最后这个代码为我做了:

 <ProgressBar android:id="@+id/progressBar" style="?android:attr/progressBarStyleLarge" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_centerHorizontal="true" android:layout_centerVertical="true" android:layout_marginTop="50dp" android:layout_marginBottom="50dp" android:visibility="visible" android:indeterminate="true" android:indeterminateTintMode="src_atop" android:indeterminateTint="@color/secondary"> 

此解决方案适用于API 21+

这是一个老问题,但是在这里没有提到使用主题。 如果您的默认主题使用的是AppCompat ,则ProgressBar的颜色将为您定义的colorAccent

改变colorAccent也会改变你的ProgressBar的颜色,但是改变也反映在多个地方。 所以,如果您想为特定的PregressBar创建不同的颜色,您可以通过将主题应用于ProgressBar

  • 扩展您的默认主题并覆盖colorAccent

     <style name="AppTheme.WhiteAccent"> <item name="colorAccent">@color/white</item> <!-- Whatever color you want--> </style> 
  • 并在ProgressBar添加android:theme属性:

     android:theme="@style/AppTheme.WhiteAccent" 

所以它会看起来像这样:

 <ProgressBar android:id="@+id/loading" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_gravity="center" android:padding="10dp" android:theme="@style/AppTheme.WhiteAccent" /> 

所以你只是改变你的特定ProgressBarcolorAccent

注意 :使用style将不起作用。 您只需要使用android:theme 。 您可以在这里找到更多使用主题: https : //plus.google.com/u/0/+AndroidDevelopers/posts/JXHKyhsWHAH

根据一些建议,你可以指定一个形状,并用一种​​颜色剪裁,然后设置它。 我有这个编程的工作。 我就是这么做的

首先确保您导入绘图库

import android.graphics.drawable.*;

然后使用类似于下面的代码;

 ProgressBar pg = (ProgressBar)row.findViewById(R.id.progress); final float[] roundedCorners = new float[] { 5, 5, 5, 5, 5, 5, 5, 5 }; pgDrawable = new ShapeDrawable(new RoundRectShape(roundedCorners, null,null)); String MyColor = "#FF00FF"; pgDrawable.getPaint().setColor(Color.parseColor(MyColor)); ClipDrawable progress = new ClipDrawable(pgDrawable, Gravity.LEFT, ClipDrawable.HORIZONTAL); pg.setProgressDrawable(progress); pg.setBackgroundDrawable(getResources().getDrawable(android.R.drawable.progress_horizontal)); pg.setProgress(45); 

在修改默认进度栏的外观时,遇到同样的问题。 这里有一些更多的信息,希望可以帮助人们:)

  • xml文件的名称只能包含字符: a-z0-9_. (即没有首都!)
  • 为了引用你的“drawable”,它是R.drawable.filename
  • 要覆盖默认外观,您可以使用myProgressBar.setProgressDrawable(...) ,但是您不需要将您的自定义布局引用为R.drawable.filename ,则需要将其作为Drawable进行检索:
     Resources res = getResources(); myProgressBar.setProgressDrawable(res.getDrawable(R.drawable.filename); 
  • 您需要在设置进度/二级进度/最大值之前设置样式(之后为我设置一个“空”进度条)

如果不确定:

 ((ProgressBar)findViewById(R.id.progressBar)) .getIndeterminateDrawable() .setColorFilter(Color.RED, PorterDuff.Mode.SRC_IN); 

现在在2016年,我发现一些pre-Lollipop设备不尊重colorAccent设置,所以我现在对于所有API的最终解决方案如下:

 // fixes pre-Lollipop progressBar indeterminateDrawable tinting if (Build.VERSION.SDK_INT < Build.VERSION_CODES.LOLLIPOP) { Drawable wrapDrawable = DrawableCompat.wrap(mProgressBar.getIndeterminateDrawable()); DrawableCompat.setTint(wrapDrawable, ContextCompat.getColor(getContext(), android.R.color.holo_green_light)); mProgressBar.setIndeterminateDrawable(DrawableCompat.unwrap(wrapDrawable)); } else { mProgressBar.getIndeterminateDrawable().setColorFilter(ContextCompat.getColor(getContext(), android.R.color.holo_green_light), PorterDuff.Mode.SRC_IN); } 

对于奖励积分,它不使用任何弃用的代码。 尝试一下!

在这个答案中可能有一件事没有被提及:

如果您的主题是从Theme.AppCompat继承的,则ProgressBar将假定您在主题中定义为"colorAccent"的颜色。

所以,使用..

<item name="colorAccent">@color/custom_color</item>

..将自动将ProgressBar的颜色着色到@color/custom_color

这对我工作:

 <ProgressBar android:indeterminateTint="#d60909" ... /> 

我如何在水平ProgressBar中做到这一点:

  LayerDrawable layerDrawable = (LayerDrawable) progressBar.getProgressDrawable(); Drawable progressDrawable = layerDrawable.findDrawableByLayerId(android.R.id.progress); progressDrawable.setColorFilter(color, PorterDuff.Mode.SRC_IN); 
 android:progressTint="#ffffff" 

如果你继承了一个基础主题,那么主题解决方案还有一个小的功能,所以对于应用程序的紧凑,你的主题应该是:

 <style name="AppTheme.Custom" parent="@style/Theme.AppCompat"> <item name="colorAccent">@color/custom</item> </style> 

然后在进度条主题中进行设置

 <ProgressBar android:id="@+id/progressCircle_progressBar" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_gravity="center_horizontal" android:theme="@style/AppTheme.Custom" android:indeterminate="true"/> 

这个解决方案为我工作:

 <style name="Progressbar.White" parent="AppTheme"> <item name="colorControlActivated">@color/white</item> </style> <ProgressBar android:layout_width="@dimen/d_40" android:layout_height="@dimen/d_40" android:indeterminate="true" android:theme="@style/Progressbar.White"/> 

对于我使用的水平样式ProgressBar:

 import android.widget.ProgressBar; import android.graphics.drawable.GradientDrawable; import android.graphics.drawable.ClipDrawable; import android.view.Gravity; import android.graphics.drawable.Drawable; import android.graphics.drawable.LayerDrawable; public void setColours(ProgressBar progressBar, int bgCol1, int bgCol2, int fg1Col1, int fg1Col2, int value1, int fg2Col1, int fg2Col2, int value2) { //If solid colours are required for an element, then set //that elements Col1 param s the same as its Col2 param //(eg fg1Col1 == fg1Col2). //fgGradDirection and/or bgGradDirection could be parameters //if you require other gradient directions eg LEFT_RIGHT. GradientDrawable.Orientation fgGradDirection = GradientDrawable.Orientation.TOP_BOTTOM; GradientDrawable.Orientation bgGradDirection = GradientDrawable.Orientation.TOP_BOTTOM; //Background GradientDrawable bgGradDrawable = new GradientDrawable( bgGradDirection, new int[]{bgCol1, bgCol2}); bgGradDrawable.setShape(GradientDrawable.RECTANGLE); bgGradDrawable.setCornerRadius(5); ClipDrawable bgclip = new ClipDrawable( bgGradDrawable, Gravity.LEFT, ClipDrawable.HORIZONTAL); bgclip.setLevel(10000); //SecondaryProgress GradientDrawable fg2GradDrawable = new GradientDrawable( fgGradDirection, new int[]{fg2Col1, fg2Col2}); fg2GradDrawable.setShape(GradientDrawable.RECTANGLE); fg2GradDrawable.setCornerRadius(5); ClipDrawable fg2clip = new ClipDrawable( fg2GradDrawable, Gravity.LEFT, ClipDrawable.HORIZONTAL); //Progress GradientDrawable fg1GradDrawable = new GradientDrawable( fgGradDirection, new int[]{fg1Col1, fg1Col2}); fg1GradDrawable.setShape(GradientDrawable.RECTANGLE); fg1GradDrawable.setCornerRadius(5); ClipDrawable fg1clip = new ClipDrawable( fg1GradDrawable, Gravity.LEFT, ClipDrawable.HORIZONTAL); //Setup LayerDrawable and assign to progressBar Drawable[] progressDrawables = {bgclip, fg2clip, fg1clip}; LayerDrawable progressLayerDrawable = new LayerDrawable(progressDrawables); progressLayerDrawable.setId(0, android.R.id.background); progressLayerDrawable.setId(1, android.R.id.secondaryProgress); progressLayerDrawable.setId(2, android.R.id.progress); //Copy the existing ProgressDrawable bounds to the new one. Rect bounds = progressBar.getProgressDrawable().getBounds(); progressBar.setProgressDrawable(progressLayerDrawable); progressBar.getProgressDrawable().setBounds(bounds); // setProgress() ignores a change to the same value, so: if (value1 == 0) progressBar.setProgress(1); else progressBar.setProgress(0); progressBar.setProgress(value1); // setSecondaryProgress() ignores a change to the same value, so: if (value2 == 0) progressBar.setSecondaryProgress(1); else progressBar.setSecondaryProgress(0); progressBar.setSecondaryProgress(value2); //now force a redraw progressBar.invalidate(); } 

一个示例调用将是:

  setColours(myProgressBar, 0xff303030, //bgCol1 grey 0xff909090, //bgCol2 lighter grey 0xff0000FF, //fg1Col1 blue 0xffFFFFFF, //fg1Col2 white 50, //value1 0xffFF0000, //fg2Col1 red 0xffFFFFFF, //fg2Col2 white 75); //value2 

如果您不需要“二级进度”,只需将value2设置为value1即可。

发布,以添加有关PaulieG的答案 ,因为ateiob要求我解释一些东西的信息…

不幸的是,当我提出解决方案的编辑时,很久以前,我不记得所有的细节。


我可以说,在ProgressBar代码中存在(或者至少是在编写本文的时候,当我看到当前版本的Android源代码时)BUG /问题/优化,忽略了将进度设置为值的尝试它已经在。

  • 即如果进度= 45,并且您尝试将其设置为45,则代码将不执行任何操作,并且不会重新绘制进度

调用ProgressBar.setProgressDrawable() ,你的进度条将是空白的(因为你改变了drawable部分)。

这意味着你需要设置进度,并重新绘制。 但是,如果您只将进度设置为保留的值,那么它将不会执行任何操作。

您必须先将其设置为0,然后再将其设置为“旧”值,并重新绘制条。


所以总结一下:

  • 保留“旧”的进度值
  • 更新绘图/颜色(使栏变空白)
  • 重置进度到0(否则下一行什么都不做)
  • 重置进度到“旧”值(修复栏)
  • 废止

下面是我有这样做的方法 – 我希望它是有用的。 我不是100%确定为什么我从onResume()调用它 – 这可能是重要的,或不相关的:

 protected void onResume() { super.onResume(); progBar = (ProgressBar) findViewById(R.id.progress_base); int oldProgress = progBar.getProgress(); // define new drawable/colour final float[] roundedCorners = new float[] { 5, 5, 5, 5, 5, 5, 5, 5 }; ShapeDrawable shape = new ShapeDrawable(new RoundRectShape( roundedCorners, null, null)); String MyColor = "#FF00FF"; shape.getPaint().setColor(Color.parseColor(MyColor)); ClipDrawable clip = new ClipDrawable(shape, Gravity.LEFT, ClipDrawable.HORIZONTAL); progBar.setProgressDrawable(clip); progBar.setBackgroundDrawable(getResources().getDrawable( android.R.drawable.progress_horizontal)); // work around: setProgress() ignores a change to the same value progBar.setProgress(0); progBar.setProgress(oldProgress); progBar.invalidate(); } 

至于HappyEngineer的解决方案,我认为这是一个类似的解决方法,手动设置“进展”抵消(我不记得确切)。 无论哪种情况,上面的代码都适合你。

对不起,如果我不记得所有的细节 – 这就是为什么我试图编辑答案。 希望这可以帮助…

 ProgressBar bar; private Handler progressBarHandler = new Handler(); GradientDrawable progressGradientDrawable = new GradientDrawable( GradientDrawable.Orientation.LEFT_RIGHT, new int[]{ 0xff1e90ff,0xff006ab6,0xff367ba8}); ClipDrawable progressClipDrawable = new ClipDrawable( progressGradientDrawable, Gravity.LEFT, ClipDrawable.HORIZONTAL); Drawable[] progressDrawables = { new ColorDrawable(0xffffffff), progressClipDrawable, progressClipDrawable}; LayerDrawable progressLayerDrawable = new LayerDrawable(progressDrawables); int status = 0; /** Called when the activity is first created. */ @Override public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); // TODO Auto-generated method stub setContentView(R.layout.startup); bar = (ProgressBar) findViewById(R.id.start_page_progressBar); bar.setProgress(0); bar.setMax(100); progressLayerDrawable.setId(0, android.R.id.background); progressLayerDrawable.setId(1, android.R.id.secondaryProgress); progressLayerDrawable.setId(2, android.R.id.progress); bar.setProgressDrawable(progressLayerDrawable); } 

这帮助我通过代码将自定义颜色设置为进度条。 希望它有帮助

将此自定义样式应用于进度栏。

 <style name="customProgress" parent="@android:style/Widget.ProgressBar.Small"> <item name="android:indeterminateDrawable">@drawable/progress</item> <item name="android:duration">40</item> <item name="android:animationCache">true</item> <item name="android:drawingCacheQuality">low</item> <item name="android:persistentDrawingCache">animation</item> </style> 

@ drawable / progress.xml –

 <?xml version="1.0" encoding="utf-8"?> <animated-rotate xmlns:android="http://schemas.android.com/apk/res/android" android:drawable="@drawable/spinner_white" android:pivotX="50%" android:pivotY="50%" /> 

使用这种类型的图像的进度条。 在这里输入图像描述

为了更好的结果,你可以使用多个进度图像。 而且请不要犹豫,使用图像,因为Android平台本身使用进度条的图像。 代码是从sdk中提取的:)

根据muhammad-adil建议的SDK版本21和更高版本

 android:indeterminateTint="@color/orange" 

在XML Works中对我来说很简单。

Horizontal ProgressBar使用可绘制的rectangle shape作为背景, ClipDrawablerectangle shape构建为进度(主要和次要)。 着色会将颜色更改为某种色彩。 如果你想分别为所有三个有针对性的颜色 ,那么你可以使用ProgressBar.setProgressDrawable()如下:

  LayerDrawable progressBarDrawable = new LayerDrawable( new Drawable[]{ new GradientDrawable(GradientDrawable.Orientation.TOP_BOTTOM, new int[]{Color.parseColor("#ff0000ff"),Color.parseColor("#ff0000ff")}), new ClipDrawable( new GradientDrawable(GradientDrawable.Orientation.TOP_BOTTOM, new int[]{Color.parseColor("#ff00ff00"),Color.parseColor("#ff00ff00")}), Gravity.START, ClipDrawable.HORIZONTAL), new ClipDrawable( new GradientDrawable(GradientDrawable.Orientation.TOP_BOTTOM, new int[]{Color.parseColor("#ffff0000"),Color.parseColor("#ffff0000")}), Gravity.START, ClipDrawable.HORIZONTAL) }); progressBarDrawable.setId(0,android.R.id.background); progressBarDrawable.setId(1,android.R.id.secondaryProgress); progressBarDrawable.setId(2,android.R.id.progress); ((ProgressBar)findViewById(R.id.progressBar)).setProgressDrawable(progressBarDrawable); 

请注意,在初始化LayerDrawable ,可绘制图层的顺序很重要。 第一个drawable应该是背景。 根据我的实验,切换ID不起作用。 如果您将填充设置为progressbar则此方法无效。 如果你需要填充,那么你可以使用容器的进度条,如LinearLayout

使用attr这么简单,如果你正在处理multistyle应用程序:

试试这个方法:

声明属性attrs.xml下面

  <attr name="circularProgressTheme" format="reference"></attr> 

将下面的代码粘贴到styles.xml中

  <style name="ProgressThemeWhite" parent="ThemeOverlay.AppCompat.Light"> <item name="colorAccent">#FF0000</item> </style> <style name="circularProgressThemeWhite"> <item name="android:theme">@style/ProgressThemeWhite</item> </style> <style name="AppTheme" parent="Theme.AppCompat.NoActionBar"> <item name="circularProgressTheme">@style/circularProgressThemeWhite</item> </style> 

使用下面的进度条

  <ProgressBar style="?attr/circularProgressTheme" android:id="@+id/commonProgress" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_gravity="center" android:visibility="visible"/> 

以下是以编程方式更改ProgressBar颜色的代码。

 ProgressBar progressBar = (ProgressBar) findViewById(R.id.pb_listProgressBar); int colorCodeDark = Color.parseColor("#F44336"); progressBar.setIndeterminateTintList(ColorStateList.valueOf(colorCodeDark)); 

水平进度条定制材质风格:

改变背景的颜色和水平进度条的进度。

 <style name="MyProgressBar" parent="@style/Widget.AppCompat.ProgressBar.Horizontal"> <item name="android:progressBackgroundTint">#69f0ae</item> <item name="android:progressTint">#b71c1c</item> <item name="android:minWidth">200dp</item> </style> 

通过设置样式属性将其应用于进度条,对于自定义材质样式和自定义进度条,请查看http://www.zoftino.com/android-progressbar-and-custom-progressbar-examples

这对我来说是一个简单的解决方案。

 progressDialog.setMessage( Html.fromHtml("<font color='white'>" + Message + "</font>"));