Android 如何更改浮动操作按钮的颜色

644

我一直在尝试更改 Material 的浮动操作按钮颜色,但没有成功。

<android.support.design.widget.FloatingActionButton
    android:id="@+id/profile_edit_fab"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:layout_gravity="end|bottom"
    android:layout_margin="16dp"
    android:clickable="true"
    android:src="@drawable/ic_mode_edit_white_24dp" />

我尝试添加:

android:background="@color/mycolor"

或通过代码:

FloatingActionButton fab = (FloatingActionButton) rootView.findViewById(R.id.profile_edit_fab);
fab.setBackgroundColor(Color.parseColor("#mycolor"));
或者
fab.setBackgroundDrawable(new ColorDrawable(Color.parseColor("#mycolor")));

但是上述方法都没有奏效。我还尝试了提出的重复问题中的解决方案,但它们都无法正常工作;该按钮仍然保持绿色,并且变成了一个正方形。

另外,知道如何添加涟漪效果也会很好,但我也没搞懂怎么做。


涟漪效果在早期的安卓设备上不可用,因为它使用了新的RenderThread - tachyonflux
@karaokyo 好的,但我该如何做呢? - Jjang
52
我认为谷歌在让这些东西易于使用方面做得很差。 - Joop
要以编程方式实现向后兼容,请参见https://dev59.com/D10Z5IYBdhLWcg3w4jhy#38618011 - Ralph Pina
28个回答

1231
根据文档描述,默认情况下,FloatingActionButton 会使用在 styles.xml 中设置的 colorAccent 属性作为背景颜色。如果您想在运行时更改此颜色,则可以通过 setBackgroundTintList(ColorStateList) 方法来实现。
如果您想要改变这个颜色:
- 可以在XML中使用属性 app:backgroundTint
<android.support.design.widget.FloatingActionButton
    xmlns:app="http://schemas.android.com/apk/res-auto"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:src="@drawable/ic_add"
    app:backgroundTint="@color/orange"
    app:borderWidth="0dp"
    app:elevation="6dp"
    app:fabSize="normal" >
  • 使用.setBackgroundTintList代码更改浮动操作按钮颜色(下面是来自ywwynm的答案)

如@Dantalian在评论中提到的,如果您希望为Design Support库的图标颜色(包括v22及以下版本)进行更改,则可以使用

android:tint="@color/white"     

对于 Design Support Library 自 v23 起,您可以使用以下内容:


app:tint="@color/white"   

同时,使用androidX库时,您需要在XML布局中设置一个0dp的边框:

<com.google.android.material.floatingactionbutton.FloatingActionButton
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:src="@drawable/ic_add"
    app:backgroundTint="@color/orange"
    app:borderWidth="0dp"
    app:elevation="6dp"
    app:fabSize="normal" />

24
这在Design Support Library v23中对于API 12以下的设备不起作用。在v22中它是有效的,所以显然他们破坏了什么。 - hungryghost
6
请注意,如果您想将图像颜色更改为白色,您可以使用以下代码:android:tint="@android:color/white" - Dantalian
1
android:tint="@color/white" 对我来说不起作用,因为由于某些原因它无法解决。但是 android:tint="#ffffff" 对我有效。 - realappie
2
这是因为您的colors.xml中不存在@color/white。请使用@android:color/white或创建一个名为white的颜色或任何您需要的颜色。 - Dantalian
247
请使用 "app:backgroundTint" 而不是 "android:backgroundTint"。 - Vasil Valchev
显示剩余6条评论

262

Vijet Badigannavar的答案是正确的,但使用ColorStateList通常比较复杂,他也没有告诉我们如何做到。由于我们通常会专注于更改View在正常和按下状态下的颜色,因此我将添加更多细节:

  1. 如果您想要更改FAB在正常状态下的颜色,只需编写:

    mFab.setBackgroundTintList(ColorStateList.valueOf(your color in int));
    
    如果你想要改变FAB在按下状态下的颜色,感谢Design Support Library22.2.1,你只需要写如下代码:
  2. mFab.setRippleColor(your color in int);
    

    通过设置这个属性,当您长按FAB时,一个带有您颜色的涟漪将出现在您的触摸点,并展示到整个FAB表面。请注意,它不会改变正常状态下FAB的颜色。 在API 21(棒棒糖)以下版本中,没有涟漪效果,但是当您按下它时,FAB的颜色仍将发生变化。

    最后,如果您想为状态实现更复杂的效果,则应深入了解ColorStateList,这里有一个SO问题讨论它:How do I create ColorStateList programmatically?

    更新: 感谢@Kaitlyn的评论。要使用backgroundTint作为其颜色来移除FAB的描边,您可以在xml中设置app:borderWidth="0dp"


3
谢谢您,我不知道如何使用ColorStateList。不过,您的代码使我的FAB带有主题强调颜色的描边(轮廓)。您有任何想法如何去掉这个描边(或者改变它的颜色),并且让FAB呈现一个特殊颜色,看起来像这个特殊颜色是主题强调颜色吗? - Kaitlyn Hanrahan
@KaitlynHanrahan 请查看我的更新。感谢您的评论。 - ywwynm
那个完美运作了——Lollypop和Kitkat看起来一样,即使两者都有那个小阴影,所以FAB在背景中弹出相同的颜色(我将其部分覆盖在工具栏上)。非常感谢!这很简单,但我不知道我自己是否能找到它。 - Kaitlyn Hanrahan
有没有一种方法可以通过编程方式设置 app:borderWidth?谢谢。 - Štarke
@Štarke 嗯,经过查看 FloatingActionButton 的源代码后,我恐怕现在无法通过编程设置它,因为 mBorderWidth 没有 setter。 - ywwynm
显示剩余4条评论

142

正如Vasil Valchev在评论中指出的那样,它比看起来简单,但是在我的XML中我没有注意到一个微妙的区别。

<android.support.design.widget.FloatingActionButton
    android:id="@+id/profile_edit_fab"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:layout_gravity="end|bottom"
    android:layout_margin="16dp"
    android:clickable="true"
    android:src="@drawable/ic_mode_edit_white_24dp"
    app:backgroundTint="@android:color/white"/>

请注意:

app:backgroundTint="@android:color/white"

不是

android:backgroundTint="@android:color/white"

8
这很重要,因为这是两件完全不同的事情:android:backgroundTint="" 来自 Api level 21 和 Lollipop Material Design,会在低于 Lollipop 的版本中被忽略。此外,它不会完全改变 FAB 的颜色,因为它不是一个纯色。你必须使用 app: 这个属性才能使其生效。 - creativecreatorormaybenot
1
谢谢,使用 android:color 导致我的应用程序崩溃,这让我很疯狂!感谢您挽救了我的应用程序和我剩下的理智;-) - Kapenaar
@Kapenaar 没问题,我也挠了一会儿头才注意到 ;) - HenriqueMS
从程序的角度来看,由于Java端在XML中没有像app:和android:这样的区别,因此这将如何工作? - marienke
@marienke,您可以使用ColorStatesList进行设置,发布一个新问题并在此处发布链接,以便我回答它 ;) - HenriqueMS

62

如果您尝试使用应用程序更改FAB的颜色,可能会出现一些问题。 按钮的框架具有不同的颜色,所以您必须要做什么:

app:backgroundTint="@android:color/transparent"

并在代码中设置颜色:

actionButton.setBackgroundTintList(ColorStateList.valueOf(getResources().getColor(R.color.white)));

2
这适用于普通颜色。如果我给出了类似 #44000000 的 alpha 颜色,则框架颜色问题是可重现的。 - Dinesh
7
getResources.getColor()已经过时,请考虑改用ContextCompat.getColor(context, your colour)。希望有所帮助。 - Tinashe Chinyanga

55

只需使用,

app:backgroundTint="@color/colorPrimary"

请勿使用,

android:backgroundTint="@color/colorPrimary"

嗯嗯,这会导致Android Studio自动完成功能给出使用android:backgroundTint的结果,这个答案非常好。 - Yudi karma

35

FAB的颜色基于您的colorAccent

<style name="AppTheme" parent="Base.Theme.AppCompat.Light">
    <item name="colorAccent">@color/accent</item>
</style>

好的,默認顏色不是綠色。你在哪裡設置了綠色? - tachyonflux
1
我没有。正如您所看到的,这个xml是我设置按钮布局的唯一位置... - Jjang
也许你应该创建一个只包含 FAB 的新项目,并发布整个代码。 - tachyonflux
3
哇...我基本上只是要求你做同样的事情,而你却不愿意这么做。认为你的代码足够好,但对我的代码补充不足够好,这很虚伪。提供一个最小可行示例(MCVE)是提问者的责任。谢谢。 - tachyonflux
5
根据主题属性映射,浮动操作按钮现在不再采用之前的颜色,而是使用 colorSecondary (_com.google.android.material:material:1.1.0-alpha02_)进行着色(我已经验证过)。 - ievgen
显示剩余6条评论

28
mFab.setBackgroundTintList(ColorStateList.valueOf(ContextCompat.getColor(mContext,R.color.mColor)));

这是最简单的解决方案,比使用自定义可绘制对象要容易得多。 - IgorGanapolsky

21

材料1.1.0中浮动操作按钮的新主题属性映射

在您的应用程序主题中:

  • 设置colorSecondary以设置FAB背景的颜色(映射到backgroundTint)
  • 设置colorOnSecondary以设置FAB图标/文本和涟漪颜色的颜色(映射到tint和rippleColor)

<style name="AppTheme" parent="Theme.MaterialComponents.Light.NoActionBar">
    <!-- ...whatever else you declare in your app theme.. -->
    <!-- Set colorSecondary to change background of FAB (backgroundTint) -->
    <item name="colorSecondary">@color/colorSecondary</item>
    <!-- Customize colorSecondary to change icon/text of FAB (maps to tint and rippleColor) -->
    <item name="colorOnSecondary">@android:color/white</item>
</style>

终于有人提供了简单的解决方案,用于设置FAB背景和前景(图标)颜色。 - ManuelTS
谢谢。这正是我在寻找的。 - Mateus Nascimento
更多信息请参见:https://material.io/develop/android/theming/color + https://material.io/design/color/the-color-system.html#color-theme-creation - jacoballenwood

17

其他方案可能有效。这是一种重量级的解决方案,具有广泛适用于此类似情况的优点:

Styles.xml:

<style name="AppTheme.FloatingAccentButtonOverlay" >
    <item name="colorAccent">@color/colorFloatingActionBarAccent</item>
</style>

你的布局XML:

<android.support.design.widget.FloatingActionButton
       android:theme="AppTheme.FloatingAccentButtonOverlay"
       ...
 </android.support.design.widget.FloatingActionButton>

嗯,看起来应该可以工作,但是在布局文件中我得到了编译器错误 String types not allowed (at 'theme' with value 'AppTheme.FloatingAccentButtonOverlay')。也许我在styles.xml方面漏掉了一些要点... - SMBiggs
@ScottBiggs 使用 android:theme="@style/AppTheme.FloatingAccentButtonOverlay",但这个解决方案对我来说都不起作用... - jpact
API 16 没有 colorAccent 属性怎么办? - Dushyant Suthar

16

使用默认的Material主题材料组件FloatingActionButton,它默认采用styles.xml中的colorSecondary属性设置的颜色。

  • 您可以在xml中使用app:backgroundTint属性:
<com.google.android.material.floatingactionbutton.FloatingActionButton
       ...
       app:backgroundTint=".."
       app:srcCompat="@drawable/ic_plus_24"/>
  • 您可以使用 fab.setBackgroundTintList(); 方法。

  • 您可以使用 <item name="backgroundTint"> 属性自定义样式。

  <!--<item name="floatingActionButtonStyle">@style/Widget.MaterialComponents.FloatingActionButton</item> -->
  <style name="MyFloatingActionButton" parent="@style/Widget.MaterialComponents.FloatingActionButton">
    <item name="backgroundTint">#00f</item>
    <!-- color used by the icon -->
    <item name="tint">@color/...</item>
  </style>
  • 从材料组件1.1.0版本开始,您可以使用新的materialThemeOverlay属性仅覆盖一些组件的默认颜色:
  <style name="MyFloatingActionButton" parent="@style/Widget.MaterialComponents.FloatingActionButton">
    <item name="materialThemeOverlay">@style/MyFabOverlay</item>
  </style>

  <style name="MyFabOverlay">
    <item name="colorSecondary">@color/custom2</item>
    <!-- color used by the icon -->
    <item name="colorOnSecondary">@color/...</item>
  </style>

enter image description here


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接