Material Design not styling alert dialogs - android

I've added the appCompat material design to my app and it seems that the alert dialogs are not using my primary, primaryDark, or accent colors.
Here is my base style:
<style name="MaterialNavyTheme" parent="#style/Theme.AppCompat.Light.DarkActionBar">
<item name="colorPrimary">#color/apptheme_color</item>
<item name="colorPrimaryDark">#color/apptheme_color_dark</item>
<item name="colorAccent">#color/apptheme_color</item>
<item name="android:textColorPrimary">#color/action_bar_gray</item>
</style>
Based on my understanding the dialogs button text should also use these colors. Am I wrong on my understanding or is there something more I need to do?
Solution:
The marked answer got me on the right track.
<style name="MaterialNavyTheme" parent="#style/Theme.AppCompat.Light.DarkActionBar">
<item name="colorPrimary">#color/apptheme_color</item>
<item name="colorPrimaryDark">#color/apptheme_color_dark</item>
<item name="colorAccent">#color/apptheme_color</item>
<item name="android:actionModeBackground">#color/apptheme_color_dark</item>
<item name="android:textColorPrimary">#color/action_bar_gray</item>
<item name="sdlDialogStyle">#style/DialogStyleLight</item>
<item name="android:seekBarStyle">#style/SeekBarNavyTheme</item>
</style>
<style name="StyledDialog" parent="Theme.AppCompat.Light.Dialog">
<item name="colorPrimary">#color/apptheme_color</item>
<item name="colorPrimaryDark">#color/apptheme_color_dark</item>
<item name="colorAccent">#color/apptheme_color</item>
</style>

UPDATED ON Aug 2019 WITH The Material components for android library:
With the new Material components for Android library you can use the new com.google.android.material.dialog.MaterialAlertDialogBuilder class, which extends from the existing androidx.appcompat.AlertDialog.Builder class and provides support for the latest Material Design specifications.
Just use something like this:
new MaterialAlertDialogBuilder(context)
.setTitle("Dialog")
.setMessage("Lorem ipsum dolor ....")
.setPositiveButton("Ok", /* listener = */ null)
.setNegativeButton("Cancel", /* listener = */ null)
.show();
You can customize the colors extending the ThemeOverlay.MaterialComponents.MaterialAlertDialog style:
<style name="CustomMaterialDialog" parent="#style/ThemeOverlay.MaterialComponents.MaterialAlertDialog">
<!-- Background Color-->
<item name="android:background">#006db3</item>
<!-- Text Color for title and message -->
<item name="colorOnSurface">#color/secondaryColor</item>
<!-- Text Color for buttons -->
<item name="colorPrimary">#color/white</item>
....
</style>
To apply your custom style just use the constructor:
new MaterialAlertDialogBuilder(context, R.style.CustomMaterialDialog)
To customize the buttons, the title and the body text check this post for more details.
You can also change globally the style in your app theme:
<!-- Base application theme. -->
<style name="AppTheme" parent="Theme.MaterialComponents.Light">
...
<item name="materialAlertDialogTheme">#style/CustomMaterialDialog</item>
</style>
WITH SUPPORT LIBRARY and APPCOMPAT THEME:
With the new AppCompat v22.1 you can use the new android.support.v7.app.AlertDialog.
Just use a code like this:
import android.support.v7.app.AlertDialog
AlertDialog.Builder builder =
new AlertDialog.Builder(this, R.style.AppCompatAlertDialogStyle);
builder.setTitle("Dialog");
builder.setMessage("Lorem ipsum dolor ....");
builder.setPositiveButton("OK", null);
builder.setNegativeButton("Cancel", null);
builder.show();
And use a style like this:
<style name="AppCompatAlertDialogStyle" parent="Theme.AppCompat.Light.Dialog.Alert">
<item name="colorAccent">#FFCC00</item>
<item name="android:textColorPrimary">#FFFFFF</item>
<item name="android:background">#5fa3d0</item>
</style>
Otherwise you can define in your current theme:
<style name="AppTheme" parent="Theme.AppCompat.Light">
<!-- your style -->
<item name="alertDialogTheme">#style/AppCompatAlertDialogStyle</item>
</style>
and then in your code:
import android.support.v7.app.AlertDialog
AlertDialog.Builder builder =
new AlertDialog.Builder(this);
Here the AlertDialog on Kitkat:

when initializing dialog builder, pass second parameter as the theme. It will automatically show material design with API level 21.
AlertDialog.Builder builder = new AlertDialog.Builder(this, AlertDialog.THEME_DEVICE_DEFAULT_DARK);
or,
AlertDialog.Builder builder = new AlertDialog.Builder(this, AlertDialog.THEME_DEVICE_DEFAULT_LIGHT);

AppCompat doesn't do that for dialogs (not yet at least)
EDIT: it does now. make sure to use android.support.v7.app.AlertDialog

Material Design styling alert dialogs: Custom Font, Button, Color & shape,..
MaterialAlertDialogBuilder(requireContext(),
R.style.MyAlertDialogTheme
)
.setIcon(R.drawable.ic_dialogs_24px)
.setTitle("Feedback")
//.setView(R.layout.edit_text)
.setMessage("Do you have any additional comments?")
.setPositiveButton("Send") { dialog, _ ->
val input =
(dialog as AlertDialog).findViewById<TextView>(
android.R.id.text1
)
Toast.makeText(context, input!!.text, Toast.LENGTH_LONG).show()
}
.setNegativeButton("Cancel") { _, _ ->
Toast.makeText(requireContext(), "Clicked cancel", Toast.LENGTH_SHORT).show()
}
.show()
Style:
<style name="MyAlertDialogTheme" parent="Theme.MaterialComponents.DayNight.Dialog.Alert">
<item name="android:textAppearanceSmall">#style/MyTextAppearance</item>
<item name="android:textAppearanceMedium">#style/MyTextAppearance</item>
<item name="android:textAppearanceLarge">#style/MyTextAppearance</item>
<item name="buttonBarPositiveButtonStyle">#style/Alert.Button.Positive</item>
<item name="buttonBarNegativeButtonStyle">#style/Alert.Button.Neutral</item>
<item name="buttonBarNeutralButtonStyle">#style/Alert.Button.Neutral</item>
<item name="android:backgroundDimEnabled">true</item>
<item name="shapeAppearanceOverlay">#style/ShapeAppearanceOverlay.MyApp.Dialog.Rounded
</item>
</style>
<style name="MyTextAppearance" parent="TextAppearance.AppCompat">
<item name="android:fontFamily">#font/rosarivo</item>
</style>
<style name="Alert.Button.Positive" parent="Widget.MaterialComponents.Button.TextButton">
<!-- <item name="backgroundTint">#color/colorPrimaryDark</item>-->
<item name="backgroundTint">#android:color/transparent</item>
<item name="rippleColor">#color/colorAccent</item>
<item name="android:textColor">#color/colorPrimary</item>
<!-- <item name="android:textColor">#android:color/white</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">#android:color/transparent</item>
<item name="rippleColor">#color/colorAccent</item>
<item name="android:textColor">#color/colorPrimary</item>
<!--<item name="android:textColor">#android:color/darker_gray</item>-->
<item name="android:textSize">14sp</item>
<item name="android:textAllCaps">false</item>
</style>
<style name="ShapeAppearanceOverlay.MyApp.Dialog.Rounded" parent="">
<item name="cornerFamily">rounded</item>
<item name="cornerSize">8dp</item>
</style>
Output:

You could use
Material Design Library
Material Design Library made for pretty alert dialogs, buttons, and other things like snack bars. Currently it's heavily developed.
Guide, code, example - https://github.com/navasmdc/MaterialDesignLibrary
Guide how to add library to Android Studio 1.0 - How do I import material design library to Android Studio?
.
Happy coding ;)

You can consider this project:
https://github.com/fengdai/AlertDialogPro
It can provide you material theme alert dialogs almost the same as lollipop's. Compatible with Android 2.1.

For some reason the android:textColor only seems to update the title color.
You can change the message text color by using a
SpannableString.AlertDialog.Builder builder = new AlertDialog.Builder(new ContextThemeWrapper(this, R.style.MyDialogTheme));
AlertDialog dialog = builder.create();
Spannable wordtoSpan = new SpannableString("I know just how to whisper, And I know just how to cry,I know just where to find the answers");
wordtoSpan.setSpan(new ForegroundColorSpan(Color.BLUE), 15, 30, Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
dialog.setMessage(wordtoSpan);
dialog.show();

Try this library:
https://github.com/avast/android-styled-dialogs
It's based on DialogFragments instead of AlertDialogs (like the one from #afollestad). The main advantage: Dialogs don't dismiss after rotation and callbacks still work.

Related

Alert dialog button has different colorset

hello, I have an alert dialog. the buttons are purple. yes I can change the color of the text inside using:
alertDialog.getButton(Dialog.BUTTON_NEGATIVE).
setTextColor(Color.parseColor("#000000"));
however when they are touched, there is a purple hue that forms.
I want the hue to be blue like the main accent of my app and the text to be black.
this is my alert style:
<style name="MyCustomAlert2" parent="Theme.MaterialComponents.Dialog.Alert">
<item name="colorAccent">#color/materialBlue</item>
<item name="android:textColorPrimary">#android:color/black</item>
<item name="android:windowBackground">#drawable/custom_alert2</item>
<item name="colorControlNormal">#android:color/black</item>
<item name="colorControlActivated">#color/materialBlue</item>
<item name="textColorAlertDialogListItem">#android:color/black</item>
</style>
note: none of the colors linked above are purple.
thanks for the help
Use new theandroidx.appcompat.app.AlertDialog and the Material components for android library.
Just use something like:
new MaterialAlertDialogBuilder(context)
.setTitle("...")
.setMessage("....")
.setPositiveButton("Ok", /* listener = */ null)
.setNegativeButton("Cancel", /* listener = */ null)
.show();
Then you can customize the style with something like:
<!-- Alert Dialog -->
<style name="MyThemeOverlay.MaterialComponents.MaterialAlertDialog" parent="#style/ThemeOverlay.MaterialComponents.MaterialAlertDialog">
<item name="buttonBarPositiveButtonStyle">#style/PositiveButtonStyle</item>
<item name="buttonBarNegativeButtonStyle">#style/Widget.MaterialComponents.Button.TextButton.Dialog</item>
</style>
and here you can change each button:
<style name="PositiveButtonStyle" parent="Widget.MaterialComponents.Button.TextButton.Dialog">
<item name="android:textColor">#000000</item>
<item name="backgroundTint">#color/selector_bt</item>
</style>
You can set the style globally in your app theme using:
<item name="materialAlertDialogTheme">#style/MyThemeOverlay.MaterialComponents.MaterialAlertDialog</item>
or you can use the constructor:
new MaterialAlertDialogBuilder(context,
R.style.MyThemeOverlay_MaterialComponents_MaterialAlertDialog)

How to change MaterialAlertDialog text color properly?

I try to use widgets from Material Components only, but in many cases, it's not documented how styling can be achieved.
Let's consider MaterialAlertDialog.
Each time I want to show a dialog, I call such part of the code:
MaterialAlertDialogBuilder(context, R.style.Theme_MyApp_Dialog_Alert)
.setTitle("Title")
.setMessage("This is message.")
.setPositiveButton(R.string.ok) { _, _ -> }
.show()
As you can see, I'm using a custom theme.
<style name="Theme.MyApp.Dialog.Alert" parent="ThemeOverlay.MaterialComponents.MaterialAlertDialog">
<!-- attributes here -->
</style>
The problem is that some of the attributes are not working. For example textColor. So the question is how to change the body or title text color in MaterialAlertDialog?
I use the newest version of Material Components - 1.1.0-alpha07.
PS.
I'm not sure which theme should be a parent. In Material Theme Builder they use #style/ThemeOverlay.MaterialComponents.Dialog.Alert which actually gives an "old" look of dialogs.
Change the style as below
<style name="Theme.MyApp.Dialog.Alert" parent="ThemeOverlay.MaterialComponents.MaterialAlertDialog">
<item name="materialAlertDialogTitleTextStyle">#style/MaterialAlertDialogText</item>
</style>
Create MaterialAlertDialogText style and set textColor
<style name="MaterialAlertDialogText" parent="#style/MaterialAlertDialog.MaterialComponents.Title.Text">
<item name="android:textColor">#color/yourTextColor</item>
</style>
You can simply override the default colors using:
<style name="Theme.MyApp.Dialog.Alert" parent="#style/ThemeOverlay.MaterialComponents.MaterialAlertDialog">
<!-- Text Color for title and message -->
<item name="colorOnSurface">#color/....</item>
....
</style>
Otherwise you can customize the style used by the title and the body text using:
<style name="Theme.MyApp.Dialog.Alert" parent="#style/ThemeOverlay.MaterialComponents.MaterialAlertDialog">
<!-- Title -->
<item name="materialAlertDialogTitleTextStyle">#style/MyTitle_MaterialAlertDialog.MaterialComponents.Title.Text</item>
<!-- Body -->
<item name="materialAlertDialogBodyTextStyle">#style/BodyTextAppearance.MaterialComponents.Body2</item>
</style>
<style name="MyTitle_MaterialAlertDialog.MaterialComponents.Title.Text" parent="#style/MaterialAlertDialog.MaterialComponents.Title.Text">
<item name="android:textColor">#color/...</item>
<item name="android:textAppearance">#style/....</item>
</style>
<style name="BodyTextAppearance.MaterialComponents.Body2" parent="#style/MaterialAlertDialog.MaterialComponents.Body.Text">
<item name="android:textColor">#color/....</item>
<item name="android:textSize">20sp</item>
<item name="android:textStyle">bold</item>
<item name="android:textAllCaps">true</item>
<item name="fontFamily">sans-serif-condensed-light</item>
</style>

MaterialComponents theme alert dialog buttons

Recently I switched from support library to com.google.android.material:material:1.0.0
But now I have a problem, in this pages there's a note https://github.com/material-components/material-components-android/blob/master/docs/getting-started.md
Note: Using a Material Components theme enables a custom view inflater which replaces default components with their Material counterparts. Currently, this only replaces Button XML components with MaterialButton.
And the theme I am using
Theme.MaterialComponents.Light.NoActionBar
does exactly what it says in that note, it replaces AlertDialog Buttons to MaterialButtons but the problem is that by default MaterialButtons are colored background and now the buttons looks like this:
How can I make them borderless and backgroundless again?
PS I am using alert builder to create alert dialogs:
android.app.AlertDialog.Builder
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
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>
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:
If you want also to apply a different style or color to the buttons you can check this answer.
I tested the above answers. Although I got a good idea, none worked for my case. So, this is my answer.
Make sure to have android:theme="#style/AppMaterialTheme" in your manifest file under Application or Activity.
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>
You won't need to apply the theme to your AlertDialog as your Activity applies the theme to it. So, create the dialog normally.
The result will be.
First, it's better to use use MaterialAlertDialog if you are using Material Theme.
You can read more here – Material.io → Theming dialogs
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>
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.
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 com.android.support:design:28.0.0 library, using android.support.v7.app.AlertDialog works as expected.

How can I set dialog style in my custom theme?

I tried in many ways but I can't change the AlertDialog style from xml.
The result I would is to define an XML style for dialogs extending and overriding the default and then bind it in my theme, so all the alertDialogs will looks the same.
I tried:
<style name="AppTheme" parent="AppBaseTheme">
<!-- All customizations that are NOT specific to a particular API-level can go here. -->
<item name="android:alertDialogStyle">#style/pippo</item>
</style>
<style name="pippo" parent="#android:style/Theme.Dialog">
<item name="android:bottomBright">#android:color/holo_orange_dark</item>
<item name="android:bottomDark">#android:color/holo_orange_dark</item>
<item name="android:bottomMedium">#android:color/holo_orange_dark</item>
<item name="android:centerBright">#android:color/holo_orange_dark</item>
<item name="android:centerDark">#android:color/holo_orange_dark</item>
<item name="android:centerMedium">#android:color/holo_orange_dark</item>
<item name="android:fullBright">#android:color/holo_orange_dark</item>
<item name="android:fullDark">#android:color/holo_orange_dark</item>
<item name="android:topBright">#android:color/holo_blue_dark</item>
<item name="android:topDark">#android:color/holo_blue_dark</item>
</style>
and then I put in the manifest "AppTheme" as activity theme, but I still see normal alertdialogs.
Where I do wrong?
You can try something like this to apply the desired style:
AlertDialog.Builder builder = new AlertDialog.Builder(new ContextThemeWrapper(this, R.style. pippo));

Changing AlertDialog text color and size on older Android version (2.3.3)

I am developing small Android application, in which I want to customize AlertDialog. For that I created my style for AlertDialog in following way:
<style name="MyTheme" parent="#android:style/Theme">
<item name="android:alertDialogStyle">#style/dialog</item>
</style>
<style name="dialog">
<item name="android:fullDark">#drawable/dialog_title</item>
<item name="android:topDark">#drawable/dialog_title</item>
<item name="android:centerDark">#drawable/dialog_body</item>
<item name="android:bottomDark">#drawable/dialog_footer</item>
<item name="android:fullBright">#drawable/dialog_body</item>
<item name="android:centerBright">#drawable/dialog_body</item>
<item name="android:bottomBright">#drawable/dialog_footer</item>
<item name="android:bottomMedium">#drawable/dialog_footer</item>
<item name="android:centerMedium">#drawable/dialog_body</item>
</style>
And I am applying this theme to my AlertDialog in following way:
ContextThemeWrapper ctw = new ContextThemeWrapper(this, R.style.MyTheme);
AlertDialog.Builder builder = new AlertDialog.Builder(ctw);
But I am not able to change header title text color and its size on older version of Android (2.3.3). How to do this?

Categories

Resources