主题警报对话框按钮

最近我从支持库转到了 com.google.android.Materials: 1.0.0

但现在我有一个问题,在这页有一个注意 https://github.com/material-components/material-components-android/blob/master/docs/getting-started.md

注意: 使用“材质组件”主题可以创建一个自定义视图充气器,用它们的“材质”对应物替换默认组件。目前,这只是将 Button XML 组件替换为 Materials ialButton。

还有我的主题

Theme.MaterialComponents.Light.NoActionBar

它完全按照注释中所说的那样,将 AlertDialog 按钮替换为 Materials 按钮,但问题是,在默认情况下,Materials 按钮是彩色背景,现在按钮看起来是这样的:enter image description here

我怎样才能让它们再次变得没有边界和背景呢?

PS 我使用警报生成器来创建警报对话框:

android.app.AlertDialog.Builder
45022 次浏览

I figured out what was causing this problem. I need to use different AlertDialog class:

androidx.appcompat.app.AlertDialog

When I switched to this everything started working as expected. Here's where I found the solution:

https://github.com/material-components/material-components-android/issues/162

Found another solution for this with using MaterialComponents here: https://issuetracker.google.com/issues/116861837#comment9

<style name="Theme.Custom.Material.Alert.Dialog.Light" parent="Theme.MaterialComponents.Light.Dialog.Alert">
<item name="materialButtonStyle">@style/Widget.AppCompat.Button.Borderless</item>
</style>


<style name="Theme.Custom.Material.Base.Light" parent="Theme.MaterialComponents.Light.NoActionBar">
<item name="android:dialogTheme">@style/Theme.Custom.Material.Alert.Dialog.Light</item>
<item name="android:alertDialogTheme">@style/Theme.Custom.Material.Alert.Dialog.Light</item>
....
</style>

Though it is still not "intended behavior" to me.

When using com.google.android.material:material:1.0.0 and androidx.appcompat.app.AlertDialog you can customize each button in the buttonBar by using Widget.MaterialComponents.Button.TextButton as parent.

val builder: AlertDialog.Builder = AlertDialog.Builder(ContextThemeWrapper(context, R.style.AlertDialogTheme))

Use the default layout or add a custom by builder.setView(R.layout.my_dialog)

In your styles:

<style name="AlertDialogTheme" parent="Theme.MaterialComponents.Light.Dialog.Alert">
<item name="buttonBarPositiveButtonStyle">@style/Alert.Button.Positive</item>
<item name="buttonBarNegativeButtonStyle">@style/Alert.Button.Neutral</item>
<item name="buttonBarNeutralButtonStyle">@style/Alert.Button.Neutral</item>
</style>


<style name="Alert.Button.Positive" parent="Widget.MaterialComponents.Button.TextButton">
<item name="backgroundTint">@color/transparent</item>
<item name="rippleColor">@color/colorAccent</item>
<item name="android:textColor">@color/colorPrimary</item>
<item name="android:textSize">14sp</item>
<item name="android:textAllCaps">false</item>
</style>


<style name="Alert.Button.Neutral" parent="Widget.MaterialComponents.Button.TextButton">
<item name="backgroundTint">@color/transparent</item>
<item name="rippleColor">@color/colorAccent</item>
<item name="android:textColor">@color/gray_dark</item>
<item name="android:textSize">14sp</item>
</style>

Screenshot

If you are using the com.android.support:design:28.0.0 library, using android.support.v7.app.AlertDialog works as expected.

If you don't want to use androidx.appcompat.app.AlertDialog, you can just redefine the style of the dialog buttons:

In your style.xml :

<style name="AppTheme" parent="Theme.MaterialComponents.Light.NoActionBar">
...
<item name="android:buttonBarButtonStyle">@style/DialogButton</item>
...
</style>


<style name="DialogButton" parent="Widget.MaterialComponents.Button.TextButton"/>


If you are using the Material Components library the best way to have an AlertDialog is to use the MaterialAlertDialogBuilder.

new MaterialAlertDialogBuilder(context)
.setTitle("Dialog")
.setMessage("Lorem ipsum dolor ....")
.setPositiveButton("Ok", /* listener = */ null)
.setNegativeButton("Cancel", /* listener = */ null)
.show();

It is the default result:

enter image description here

If you want also to apply a different style or color to the buttons you can check this answer.

First, it's better to use use MaterialAlertDialog if you are using Material Theme.

You can read more here – Material.io → Theming dialogs

enter image description here

MaterialAlertDialogBuilder(context)
.setTitle(R.string.confirm)
.setMessage(R.string.logout)
.setPositiveButton(R.string.logout_alert_positive) { _, _ -> activity?.logout() }
.setNegativeButton(R.string.never_mind, null)
.show()

 

This is the layout.xml of the MaterialAlertDialog actions. As you can see there are 3 buttons and each has their own styles. So, here is how you can change them.

Step 1: Tell Android that you want to alter the default MaterialAlertDialog theme.

<style name="Base.AppTheme" parent="Theme.MaterialComponents.DayNight.NoActionBar">
...
<item name="materialAlertDialogTheme">@style/AlertDialog</item>
...
</style>

Step 2: Tell Android that you want to alter a specific button style. buttonBarNeutralButtonStyle, buttonBarNegativeButtonStyle or buttonBarPositiveButtonStyle

<style name="AlertDialog" parent="ThemeOverlay.MaterialComponents.MaterialAlertDialog">
<item name="buttonBarNegativeButtonStyle">@style/NegativeButtonStyle</item>
</style>

Step 3: Define your custom style

<style name="NegativeButtonStyle" parent="Widget.MaterialComponents.Button.TextButton">
<item name="android:textColor">#FF0000</item>
</style>

I tested the above answers. Although I got a good idea, none worked for my case. So, this is my answer.

  1. Make sure to have android:theme="@style/AppMaterialTheme" in your manifest file under Application or Activity.

  2. Open your Styles.xml file and change it based on the following.

    <style name="AppMaterialTheme" parent="Theme.MaterialComponents.DayNight.NoActionBar">
    <item name="colorPrimary">@color/primaryBlue</item>
    <item name="colorPrimaryDark">@color/primaryBlue</item>
    <item name="colorAccent">@color/colorAccent</item>
    <item name="colorControlActivated">@color/primaryBlue</item>
    <item name="colorControlHighlight">@color/colorAccent_main</item>
    <item name="colorButtonNormal">@color/white</item>
    
    
    <item name="materialAlertDialogTheme">@style/AlertDialogMaterialTheme</item>
    </style>
    
    
    <style name="AlertDialogMaterialTheme" parent="ThemeOverlay.MaterialComponents.MaterialAlertDialog">
    <item name="buttonBarPositiveButtonStyle">@style/Alert.Button.Positive</item>
    <item name="buttonBarNegativeButtonStyle">@style/Alert.Button.Negative</item>
    </style>
    
    
    <style name="Alert.Button.Positive" parent="Widget.MaterialComponents.Button.UnelevatedButton">
    <item name="android:fillColor">@color/color_0054BB</item>
    <item name="android:textColor">@color/white</item>
    <item name="android:textAllCaps">false</item>
    <item name="android:textSize">14sp</item>
    <item name="rippleColor">@color/colorAccent_main</item>
    </style>
    
    
    <style name="Alert.Button.Negative" parent="Widget.MaterialComponents.Button.OutlinedButton">
    <item name="strokeColor">@color/color_0054BB</item>
    <item name="android:textColor">@color/color_0054BB</item>
    <item name="android:textAllCaps">false</item>
    <item name="android:textSize">14sp</item>
    <item name="android:layout_marginEnd">8dp</item>
    <item name="rippleColor">@color/colorAccent_main</item>
    </style>
    

  3. You won't need to apply the theme to your AlertDialog as your Activity applies the theme to it. So, create the dialog normally.

enter image description here

The result will be.

enter image description here