Comment puis-je changer la couleur du texte du bouton de dialogue par défaut dans Android 5

160

J'ai de nombreuses boîtes de dialogue d'alerte dans mon application. C'est une mise en page par défaut, mais j'ajoute des boutons positifs et négatifs à la boîte de dialogue. Ainsi, les boutons obtiennent la couleur du texte par défaut d'Android 5 (vert). J'ai essayé de le changer sans succès. Une idée de comment changer cette couleur de texte?

Ma boîte de dialogue personnalisée:

public class MyCustomDialog extends AlertDialog.Builder {

    public MyCustomDialog(Context context,String title,String message) {
        super(context);

        LayoutInflater inflater = (LayoutInflater) context.getSystemService( Context.LAYOUT_INFLATER_SERVICE );
        View viewDialog = inflater.inflate(R.layout.dialog_simple, null, false);

        TextView titleTextView = (TextView)viewDialog.findViewById(R.id.title);
        titleTextView.setText(title);
        TextView messageTextView = (TextView)viewDialog.findViewById(R.id.message);
        messageTextView.setText(message);

        this.setCancelable(false);

        this.setView(viewDialog);

    } }

Création de la boîte de dialogue:

MyCustomDialog builder = new MyCustomDialog(getActivity(), "Try Again", errorMessage);
builder.setNegativeButton("OK", new DialogInterface.OnClickListener() {
                        @Override
                        public void onClick(DialogInterface dialogInterface, int i) {
                            ...
                        }
}).show();

Ce bouton négatif est un bouton de dialogue par défaut et prend la couleur verte par défaut d'Android 5 Lollipop.

Merci beaucoup

Boîte de dialogue personnalisée avec bouton vert

Développeur FOM
la source
Presque dupliquer la question / réponse stackoverflow.com/a/29810469/2291 que je pense est plus applicable de nos jours.
Jon Adams

Réponses:

191

Vous pouvez d'abord essayer de créer l' AlertDialogobjet, puis l'utiliser pour configurer la modification de la couleur du bouton, puis l'afficher. (Notez que sur builderobjet au lieu d'appeler, show()nous appelons create()pour obtenir leAlertDialog objet:

//1. create a dialog object 'dialog'
MyCustomDialog builder = new MyCustomDialog(getActivity(), "Try Again", errorMessage); 
AlertDialog dialog = builder.setNegativeButton("OK", new DialogInterface.OnClickListener() {

                @Override
                public void onClick(DialogInterface dialogInterface, int i) {
                    ...
                }

            }).create();

//2. now setup to change color of the button
dialog.setOnShowListener( new OnShowListener() {
    @Override
    public void onShow(DialogInterface arg0) {
        dialog.getButton(AlertDialog.BUTTON_NEGATIVE).setTextColor(COLOR_I_WANT);
    }
});

dialog.show()

La raison pour laquelle vous devez le faire onShow()et ne pouvez pas simplement obtenir ce bouton après avoir créé votre boîte de dialogue est que le bouton n'aurait pas encore été créé.

J'ai changé AlertDialog.BUTTON_POSITIVEpour AlertDialog.BUTTON_NEGATIVErefléter le changement dans votre question. Bien qu'il soit étrange que le bouton "OK" soit un bouton négatif. C'est généralement le bouton positif.

trungdinhtrong
la source
Merci pour votre réponse, mais je n'ai pas cette méthode dans AlertDialog. Voir mon message mis à jour.
FOMDeveloper
5
Cette méthode est dans la classe AlertDialog, pas dans la classe Builder. Ainsi, au lieu d'appeler Builder.show (), vous pouvez Builder.create (), qui renvoie la classe AlertDialog. Vous configurez ensuite l'écouteur, puis appelez show () sur l'objet AlertDialog
trungdinhtrong
3
Mais il doit y avoir une autre façon de faire cela. On dirait que c'est une couleur du thème, pouvons-nous la changer via le thème / style?
milosmns
C'est parfait. Je viens d'essayer dans Xamarin.Android et cela fonctionne parfaitement. Merci beaucoup.
perozzo
282

Voici une façon naturelle de le faire avec les styles:

Si votre AppThemeest hérité de Theme.MaterialComponents, alors:

<style name="AlertDialogTheme" parent="ThemeOverlay.MaterialComponents.Dialog.Alert">
    <item name="buttonBarNegativeButtonStyle">@style/NegativeButtonStyle</item>
    <item name="buttonBarPositiveButtonStyle">@style/PositiveButtonStyle</item>
</style>

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

<style name="PositiveButtonStyle" parent="Widget.MaterialComponents.Button.TextButton.Dialog">
    <item name="android:textColor">#00f</item>
</style>

Si votre AppThemeest hérité de Theme.AppCompat:

<style name="AlertDialogTheme" parent="ThemeOverlay.AppCompat.Dialog.Alert">
    <item name="buttonBarNegativeButtonStyle">@style/NegativeButtonStyle</item>
    <item name="buttonBarPositiveButtonStyle">@style/PositiveButtonStyle</item>
</style>

<style name="NegativeButtonStyle" parent="Widget.AppCompat.Button.ButtonBar.AlertDialog">
    <item name="android:textColor">#f00</item>
</style>

<style name="PositiveButtonStyle" parent="Widget.AppCompat.Button.ButtonBar.AlertDialog">
    <item name="android:textColor">#00f</item>
</style>

Utilisez votre AlertDialogThemedans votreAppTheme

<item name="alertDialogTheme">@style/AlertDialogTheme</item>

ou en constructeur

androidx.appcompat.app.AlertDialog.Builder(context, R.style.AlertDialogTheme)
Alexandre Perfilyev
la source
34
J'ai dû changer buttonBarNegativeButtonStyle en android: buttonBarNegativeButtonStyle et buttonBarPositiveButtonStyle en android: buttonBarPositiveButtonStyle. Ensuite, cela a fonctionné (API 21+).
Vlad
23
N'oubliez pas d'utiliser android.support.v7.app.AlertDialog au lieu de android.app.AlertDialog. Une erreur de conneries m'a pris 2 heures
thanhbinh84
2
J'ai dû changer le parent d'AlertDialogTheme en "Base.Theme.AppCompat.Light.Dialog.Alert". Et supprimez buttonBarNegativeButtonStyle & buttonBarPositiveButtonStyle. Ajoutez également <item name = "colorAccent"> @ color / dashboard_red_color </item> dans AlertDialogTheme. nd fonctionne parfaitement.
zephyr le
3
Cela ne fonctionne pas lors de l'utilisation d'une nouvelle bibliothèque de matériaux com.google.android.material:material:1.0.0-beta01et j'utilise Theme.MaterialComponents.Light.Dialog.Alert
Sanjeev
2
@LX a mis à jour la réponse pour inclure le thème des composants matériels
Alexander Perfilyev
120

La couleur des boutons et autre texte peut également être modifiée via le thème:

valeurs-21 / styles.xml

<style name="AppTheme" parent="...">
  ...
  <item name="android:timePickerDialogTheme">@style/AlertDialogCustom</item>
  <item name="android:datePickerDialogTheme">@style/AlertDialogCustom</item>
  <item name="android:alertDialogTheme">@style/AlertDialogCustom</item>
</style>

<style name="AlertDialogCustom" parent="android:Theme.Material.Light.Dialog.Alert">
  <item name="android:colorPrimary">#00397F</item>
  <item name="android:colorAccent">#0AAEEF</item>
</style>

Le résultat:

Dialogue Sélecteur de date

peceps
la source
1
Actuellement, je ne connais pas de moyen de modifier uniquement la couleur de la case à cocher ou la couleur du bouton. La couleur d'accent change les deux.
peceps
4
J'ai aimé cette approche, mais j'ai l'impression que la réponse sur stackoverflow.com/a/29810469/2291 est une façon légèrement plus propre de le faire.
Jon Adams
12
Pour que cela fonctionne dans mon projet, j'ai dû supprimer la android:pièce de android:alertDialogThemeet de android:colorAccent.
ban-
2
Avoir le préfixe android: sur les valeurs dépend de l'endroit où vous mettez styles.xml, dans les valeurs ou dans values-vXX
peceps
1
Pour que cela fonctionne avec AppCompat et un dossier de valeurs simples, suivez simplement les modifications suggérées par @ ban-geoengineering
Felix
94

La solution la plus simple est:

dialog.show(); //Only after .show() was called
dialog.getButton(AlertDialog.BUTTON_NEGATIVE).setTextColor(neededColor);
dialog.getButton(AlertDialog.BUTTON_POSITIVE).setTextColor(neededColor);
Artemiy
la source
4
Ces champs ne doivent pas être référencés à partir de la variable non statique, doivent être AlertDialog.BUTTON_NEGATIVEetc.
Joe Maher
C'était le moyen le meilleur et le plus simple de le faire. Notez que je n'ai pas utilisé le "créer" plutôt attrapé la boîte de dialogue après le show (). Comme AlertDialog dialog = builder.show ();
Stephen McCormick
2
Bien que cette solution puisse fonctionner, elle est logiquement défectueuse. Ce qui se passe ici, c'est que vous affichez d'abord la boîte de dialogue, puis vous modifiez son apparence. Dépend de l'implémentation sous-jacente (qui pourrait être modifiée au fil du temps) et des performances de l'appareil, vous pourriez théoriquement voir un "scintillement" où l'utilisateur voit une boîte de dialogue apparaît et change rapidement son apparence.
trungdinhtrong
31

Il existe deux façons de modifier la couleur du bouton de la boîte de dialogue.

Voie de base

Si vous souhaitez simplement modifier une activité, écrivez les deux lignes ci-dessous après alertDialog.show();

alertDialog.getButton(AlertDialog.BUTTON_POSITIVE).setTextColor(getResources().getColor(R.color.colorPrimary));
alertDialog.getButton(AlertDialog.BUTTON_NEGATIVE).setTextColor(getResources().getColor(R.color.colorPrimaryDark));

conseillé

Je vous recommande d'ajouter un thème pour AlertDialogin styles.xmlafin que vous n'ayez pas à écrire le même code encore et encore dans chaque appel d'activité / dialogue. Vous pouvez simplement créer un style et appliquer ce thème dans la boîte de dialogue. Ainsi, chaque fois que vous souhaitez changer la couleur de la boîte AlertDialog, changez simplement la couleur dans styles.xml et toutes les boîtes de dialogue seront mises à jour dans toute l'application.

<style name="AlertDialogTheme" parent="Theme.AppCompat.Light.Dialog.Alert">
    <item name="colorAccent">@color/colorPrimary</item>
</style>

Et appliquez le thème dans AlertDialog.Builder

AlertDialog.Builder builder = new AlertDialog.Builder(this, R.style.AlertDialogTheme);
Hassnain Jamil
la source
Cette réponse est la plus claire tout en étant correcte.
Big_Chair
11

Si vous souhaitez modifier la couleur du texte des boutons (positive, négative, neutre), ajoutez simplement à votre style de dialogue personnalisé:

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

Donc, votre style de dialogue doit ressembler à ceci:

<style name="AlertDialog" parent="Theme.AppCompat.Light.Dialog.Alert">
    <item name="android:textColor">@android:color/black</item>
    <item name="colorAccent">@color/topeka_accent</item>
</style>
Stanislav Zakharov
la source
6
<style name="AlertDialogCustom" parent="Theme.AppCompat.Light.Dialog.Alert">
    <item name="android:colorPrimary">#00397F</item>
    <item name="android:textColorPrimary">#22397F</item>
    <item name="android:colorAccent">#00397F</item>
    <item name="colorPrimaryDark">#22397F</item>
</style>

La couleur des boutons et autre texte peut également être modifiée en utilisant appcompat:

Arade
la source
Theme.AppCompat.Light.Dialog.Alert fonctionne bien pour changer la couleur du bouton en blanc.
Leo K
6
  1. Dans le thème / style de votre application, ajoutez les lignes suivantes:

    <item name="android:buttonBarNegativeButtonStyle">@style/NegativeButtonStyle</item>
    <item name="android:buttonBarPositiveButtonStyle">@style/PositiveButtonStyle</item>
    <item name="android:buttonBarNeutralButtonStyle">@style/NeutralButtonStyle</item>
  2. Ajoutez ensuite les styles suivants:

    <style name="NegativeButtonStyle" parent="Widget.MaterialComponents.Button.TextButton.Dialog">
        <item name="android:textColor">@color/red</item>
    </style>
    
    <style name="PositiveButtonStyle" parent="Widget.MaterialComponents.Button.TextButton.Dialog">
        <item name="android:textColor">@color/red</item>
    </style>
    
    <style name="NeutralButtonStyle" 
    parent="Widget.MaterialComponents.Button.TextButton.Dialog">
        <item name="android:textColor">#00f</item>
    </style>

L'utilisation de cette méthode rend inutile la définition du thème dans le générateur AlertDialog.

Joe Muller
la source
4

Juste comme note latérale:

Les couleurs des boutons (et tout le style) dépendent également du thème actuel qui peut être assez différent lorsque vous utilisez soit

android.app.AlertDialog.Builder builder = new AlertDialog.Builder()

ou

android.support.v7.app.AlertDialog.Builder builder = new AlertDialog.Builder()

(Mieux vaut utiliser le second)

Tobias
la source
3

Voici comment procéder: Une manière simple

// Initializing a new alert dialog
AlertDialog.Builder builder = new AlertDialog.Builder(getActivity());
builder.setMessage(R.string.message);
builder.setPositiveButton(R.string.ok, new DialogInterface.OnClickListener() {
    @Override
    public void onClick(DialogInterface dialog, int which) {
        doAction();
    }
});
builder.setNegativeButton(R.string.cancel, null);

// Create the alert dialog and change Buttons colour
AlertDialog dialog = builder.create();
dialog.setOnShowListener(new DialogInterface.OnShowListener() {
    @Override
    public void onShow(DialogInterface arg0) {
        dialog.getButton(AlertDialog.BUTTON_POSITIVE).setTextColor(getResources().getColor(R.color.red));
        dialog.getButton(AlertDialog.BUTTON_NEGATIVE).setTextColor(getResources().getColor(R.color.blue));
        //dialog.getButton(AlertDialog.BUTTON_NEUTRAL).setTextColor(getResources().getColor(R.color.black));
    }
});
dialog.show();
MrGuy
la source
1

pour moi c'était différent, j'ai utilisé un thème de bouton

<style name="ButtonLight_pink" parent="android:Widget.Button">
      <item name="android:background">@drawable/light_pink_btn_default_holo_light</item>
      <item name="android:minHeight">48dip</item>
      <item name="android:minWidth">64dip</item>
      <item name="android:textColor">@color/tab_background_light_pink</item>
    </style>

et parce que

android: textColor

était blanc là-bas… je n'ai vu aucun texte de bouton (les boutons de dialogue sont essentiellement des boutons aussi). on y va, on l'a changé, on l'a réparé.

cV2
la source