Comment afficher une boîte de dialogue Oui / Non sur Android?

358

Oui, je sais qu'il y a AlertDialog.Builder, mais je suis choqué de savoir à quel point (enfin, du moins pas convivial pour les programmeurs) d'afficher une boîte de dialogue dans Android.

J'étais auparavant un développeur .NET, et je me demande s'il existe un équivalent Android des éléments suivants?

if (MessageBox.Show("Sure?", "", MessageBoxButtons.YesNo) == DialogResult.Yes){
    // Do something...
}
Solo
la source
3
Comment récupérer le code AlertDialog et gérer les événements (oui, aucune action) dans tous les écrans? Dans .Net, nous utilisons la classe Action pour gérer les événements, existe-t-il un moyen de l'implémenter? Je sais qu'en utilisant des interfaces, nous pouvons le faire mais d'une autre manière?
Ravikumar11
2
Oui .... nous, les développeurs .NET, avons vraiment du mal avec Android .... Je me demande si Xamarin est un excellent outil?
Daniel Möller

Réponses:

745

AlertDialog.Builder n'est vraiment pas si difficile à utiliser. C'est un peu intimidant au début, bien sûr, mais une fois que vous l'avez utilisé un peu, c'est à la fois simple et puissant. Je sais que vous avez dit que vous savez comment l'utiliser, mais voici tout de même un exemple simple:

DialogInterface.OnClickListener dialogClickListener = new DialogInterface.OnClickListener() {
    @Override
    public void onClick(DialogInterface dialog, int which) {
        switch (which){
        case DialogInterface.BUTTON_POSITIVE:
            //Yes button clicked
            break;

        case DialogInterface.BUTTON_NEGATIVE:
            //No button clicked
            break;
        }
    }
};

AlertDialog.Builder builder = new AlertDialog.Builder(context);
builder.setMessage("Are you sure?").setPositiveButton("Yes", dialogClickListener)
    .setNegativeButton("No", dialogClickListener).show();

Vous pouvez également le réutiliser DialogInterface.OnClickListenersi vous avez d'autres cases oui / non qui devraient faire la même chose.

Si vous créez la boîte de dialogue à partir d'un View.OnClickListener, vous pouvez utiliser view.getContext()pour obtenir le contexte. Vous pouvez également utiliser yourFragmentName.getActivity().

Steve Haley
la source
3
nouveau AlertDialog.Builder (this); Erreur de compilation: «Le constructeur AlertDialog.Builder (nouveau View.OnClickListener () {}) n'est pas défini»
Eric Leschinski
3
Simple et utile, la boîte de dialogue se fermera automatiquement après que l'utilisateur ait cliqué sur le bouton "OUI" ou "NON". Vous n'avez rien à faire.
RRTW
9
Moi-même, je l'ai utilisé beaucoup de fois. Mais j'ai trouvé qu'il était en fait plus facile et plus rapide de le rechercher sur SO. L'exemple de code donné ici est si simple ... Je souhaite vraiment que la documentation Android ressemble à ceci.
Radu
4
@EricLeschinski probablement "ce" n'est pas un contexte, essayez celui-ci: AlertDialog.Builder builder = new AlertDialog.Builder(getView().getContext());
cldrr
1
@davidglorioso L'ordre de oui / non ou non / oui dépend de la version d'Android, et vous ne pouvez pas la contrôler. Je ne me souviens pas quand cela a changé, mais je pense que c'était en 4.x ou 5. En disant cela, vous ne devriez pas le changer de toute façon. Toutes les applications qui utilisent des boîtes de dialogue d'alerte standard utiliseront le même ordre de bouton non / oui, et ce serait déroutant pour les utilisateurs si le vôtre était différent. Si vous voulez vraiment que ce soit différent, vous devrez définir manuellement vos boutons positifs / négatifs en fonction de la version Android.
Steve Haley
163

Essaye ça:

AlertDialog.Builder builder = new AlertDialog.Builder(this);

builder.setTitle("Confirm");
builder.setMessage("Are you sure?");

builder.setPositiveButton("YES", new DialogInterface.OnClickListener() {

    public void onClick(DialogInterface dialog, int which) {
        // Do nothing but close the dialog

        dialog.dismiss();
    }
});

builder.setNegativeButton("NO", new DialogInterface.OnClickListener() {

    @Override
    public void onClick(DialogInterface dialog, int which) {

        // Do nothing
        dialog.dismiss();
    }
});

AlertDialog alert = builder.create();
alert.show();
nikki
la source
25
Personnellement, j'aime cet extrait de code plus que la réponse acceptée
John
1
@nikki pourquoi les deux ont-ils rejeté ()?
likejudo
The constructor AlertDialog.Builder(MainActivity.DrawerItemClickListener) is undefined
hash
@likejiujitsu c'est parce que vous voulez nettoyer la boîte de dialogue de la mémoire dans tous les cas après avoir fait votre travail.
Avi Levin
32

La réponse de Steve H est juste, mais voici un peu plus d'informations: la raison pour laquelle les boîtes de dialogue fonctionnent comme elles le sont parce que les boîtes de dialogue dans Android sont asynchrones (l'exécution ne s'arrête pas lorsque la boîte de dialogue est affichée). Pour cette raison, vous devez utiliser un rappel pour gérer la sélection de l'utilisateur.

Consultez cette question pour une discussion plus longue entre les différences dans Android et .NET (en ce qui concerne les dialogues): Dialogs / AlertDialogs: Comment "bloquer l'exécution" pendant que la boîte de dialogue est ouverte (style .NET)

Erich Douglass
la source
8
Merci, le fait que les dialogues Android soient asynchrones rend tout clair (et raisonnable) maintenant. Il semble que je doive "penser hors de .Net" lors du développement d'applications pour Android :)
Solo
Pour info: ce que vous appelez "dialogue asynchrone" est appelé "dialogue non modal" dans la terminologie de l'interface graphique, tandis que "dialogue synchrone" est appelé "dialogue modal". Android ne propose pas de dialogues modaux (sauf dans des cas très exceptionnels).
Alex
Android n'autorise pas les boîtes de dialogue modales du système pour une très bonne raison: il n'est pas autorisé d'interférer avec d'autres applications sur l'appareil.
Renascienza
14

Cela fonctionne pour moi:

AlertDialog.Builder builder = new AlertDialog.Builder(getApplicationContext());

    builder.setTitle("Confirm");
    builder.setMessage("Are you sure?");

    builder.setPositiveButton("YES", new DialogInterface.OnClickListener() {

        public void onClick(DialogInterface dialog, int which) {

            // Do nothing, but close the dialog
            dialog.dismiss();
        }
    });

    builder.setNegativeButton("NO", new DialogInterface.OnClickListener() {

        @Override
        public void onClick(DialogInterface dialog, int which) {

            // Do nothing
            dialog.dismiss();
        }
    });

    AlertDialog alert = builder.create();
    alert.show();
hacher
la source
7

Demander à une personne si elle veut appeler ou non Dialog ..

import android.app.Activity;
import android.app.AlertDialog;
import android.content.DialogInterface;
import android.content.Intent;
import android.net.Uri;
import android.os.Bundle;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.ImageView;
import android.widget.Toast;

public class Firstclass extends Activity {

    @Override
    protected void onCreate(Bundle savedInstanceState) {    
        super.onCreate(savedInstanceState);    
        setContentView(R.layout.first);

        ImageView imageViewCall = (ImageView) findViewById(R.id.ring_mig);

        imageViewCall.setOnClickListener(new OnClickListener() {
            @Override
            public void onClick(View v){
                try{
                    showDialog("0728570527");
                } catch (Exception e){
                    e.printStackTrace();
                }                   
            }    
        });    
    }

    public void showDialog(final String phone) throws Exception {
        AlertDialog.Builder builder = new AlertDialog.Builder(Firstclass.this);

        builder.setMessage("Ring: " + phone);       

        builder.setPositiveButton("Ring", new DialogInterface.OnClickListener(){
            @Override
            public void onClick(DialogInterface dialog, int which){

                Intent callIntent = new Intent(Intent.ACTION_DIAL);// (Intent.ACTION_CALL);                 
                callIntent.setData(Uri.parse("tel:" + phone));
                startActivity(callIntent);

                dialog.dismiss();
            }
        });

        builder.setNegativeButton("Abort", new DialogInterface.OnClickListener(){   
            @Override
            public void onClick(DialogInterface dialog, int which){
                dialog.dismiss();
            }
        });         
        builder.show();
    }    
}
Zar E Ahmer
la source
5

La réponse de Steves est correcte mais obsolète avec des fragments. Voici un exemple avec FragmentDialog.

La classe:

public class SomeDialog extends DialogFragment {

    @Override
    public Dialog onCreateDialog(Bundle savedInstanceState) {
        return new AlertDialog.Builder(getActivity())
            .setTitle("Title")
            .setMessage("Sure you wanna do this!")
            .setNegativeButton(android.R.string.no, new OnClickListener() {
                @Override
                public void onClick(DialogInterface dialog, int which) {
                    // do nothing (will close dialog)
                }
            })
            .setPositiveButton(android.R.string.yes,  new OnClickListener() {
                @Override
                public void onClick(DialogInterface dialog, int which) {
                    // do something
                }
            })
            .create();
    }
}

Pour démarrer la boîte de dialogue:

            FragmentTransaction ft = getSupportFragmentManager().beginTransaction();
            // Create and show the dialog.
            SomeDialog newFragment = new SomeDialog ();
            newFragment.show(ft, "dialog");

Vous pouvez également laisser la classe implémenter onClickListeneret utiliser cela au lieu d'écouteurs intégrés.

Warpzit
la source
@likejiujitsu ci-dessus est suffisant.
Warpzit
Créer une classe FragmentDialog juste pour faire une case non / oui est un peu de conception excessive ... :) Un AlertDialog par défaut est assez juste pour le moment.
Renascienza
@Renascienza oui mais je pense que c'est obsolète.
Warpzit
Pas vraiment. FragmentDialog a été ajouté comme une chose utile pour vous permettre de réutiliser un fragment dans une boîte de dialogue. Fragments concerne la réutilisation de l'interface utilisateur. Comme vous n'avez pas besoin d'utiliser des fragments simplement parce que c'est une chose nouvelle (les fragments ne viennent pas remplacer des activités), vous n'avez pas besoin d'utiliser FragmentDialog dans les cas où il n'y a aucun gain à faire. Alertes simples Oui / Non, par exemple.
Renascienza
2
Ma recommandation est la suivante: si vous avez besoin de réutiliser non seulement une mise en page, mais le code d'arrière-plan et de cycle de vie, utilisez une boîte de dialogue Fragment. Avec le fragment, vous avez le contrôle du cycle de vie de l'activité associée et pouvez réagir à des événements tels que créer (lorsque l'interface utilisateur est recréée lorsque l'utilisateur fait pivoter son appareil), mettre en pause, reprendre, etc. En bref, une boîte de dialogue avec une interface utilisateur élaborée. Si vous n'en avez pas besoin et que votre boîte de dialogue est assez simple, les boîtes de dialogue régulières fonctionnent correctement.
Renascienza
5

Merci nikki votre réponse m'a aidé à améliorer un existant simplement en ajoutant mon action souhaitée comme suit

AlertDialog.Builder builder = new AlertDialog.Builder(this);

builder.setTitle("Do this action");
builder.setMessage("do you want confirm this action?");

builder.setPositiveButton("YES", new DialogInterface.OnClickListener() {

    public void onClick(DialogInterface dialog, int which) {
        // Do do my action here

        dialog.dismiss();
    }

});

builder.setNegativeButton("NO", new DialogInterface.OnClickListener() {

    @Override
    public void onClick(DialogInterface dialog, int which) {
        // I do not need any action here you might
        dialog.dismiss();
    }
});

AlertDialog alert = builder.create();
alert.show();
CrandellWS
la source
J'ai eu l'impression que l'OP ne voulait pas utiliser AlertDialog.Builder. OP veut savoir s'il existe une méthode utilitaire de raccourci,
walrii
1
J'ai écrit le même code mais NON apparaît en premier, puis OUI en gros c'est une boîte de dialogue NON / OUI mais j'ai besoin d'une boîte de dialogue OUI / NON Comment faire
Sagar Devanga
Quant au OUI / NON vs NON / OUI voir cette réponse: stackoverflow.com/a/13644589/1815624 vous pouvez le manipuler comme décrit dans cette réponse: stackoverflow.com/a/13644536/1815624
CrandellWS
4

À Kotlin:

AlertDialog.Builder(this)
    .setTitle(R.string.question_title)
    .setMessage(R.string.question_message)
    .setPositiveButton(android.R.string.yes) { _, _ -> yesClicked() }
    .setNegativeButton(android.R.string.no) { _, _ -> noClicked() }
    .show()
Cristan
la source
3

Afficher la boîte de dialogue de manière anonyme comme une chaîne de commandes et sans définir un autre objet:

 new AlertDialog.Builder(this).setTitle("Confirm Delete?")
                        .setMessage("Are you sure?")
                        .setPositiveButton("YES",
                                new DialogInterface.OnClickListener() {
                                    public void onClick(DialogInterface dialog, int which) {

                                       // Perform Action & Dismiss dialog                                 
                                        dialog.dismiss();
                                    }
                                })
                        .setNegativeButton("NO", new DialogInterface.OnClickListener() {
                            @Override
                            public void onClick(DialogInterface dialog, int which) {
                                // Do nothing
                                dialog.dismiss();
                            }
                        })
                        .create()
                        .show();
Hitesh Sahu
la source
2

Toutes les réponses ici se résument à un code long et peu convivial: juste ce que la personne qui demandait essayait d'éviter. Pour moi, l'approche la plus simple était d'employer des lambdas ici:

new AlertDialog.Builder(this)
        .setTitle("Are you sure?")
        .setMessage("If you go back you will loose any changes.")
        .setPositiveButton("Yes", (dialog, which) -> {
            doSomething();
            dialog.dismiss();
        })
        .setNegativeButton("No", (dialog, which) -> dialog.dismiss())
        .show();

Lambdas dans Android nécessite le plugin retrolambda ( https://github.com/evant/gradle-retrolambda ), mais il est de toute façon extrêmement utile pour écrire du code plus propre.

javaxian
la source
1

Merci. J'utilise l'API niveau 2 (Android 1.1) et au lieu de BUTTON_POSITIVEet BUTTON_NEGATIVEje dois utiliser BUTTON1et BUTTON2.

Christian
la source
1

1.Créez le message, le titre et le bouton Positif, Négatif AlertDialog:

final AlertDialog alertDialog = new AlertDialog.Builder(this)
                        .setCancelable(false)
                        .setTitle("Confirmation")
                        .setMessage("Do you want to remove this Picture?")
                        .setPositiveButton("Yes",null)
                        .setNegativeButton("No",null)
                        .create();

2. Maintenant, trouvez les deux boutons sur DialogInterface Cliquez puis setOnClickListener ():

alertDialog.setOnShowListener(new DialogInterface.OnShowListener() {
            @Override
            public void onShow(DialogInterface dialogInterface) {
                Button yesButton = (alertDialog).getButton(android.app.AlertDialog.BUTTON_POSITIVE);
                Button noButton = (alertDialog).getButton(android.app.AlertDialog.BUTTON_NEGATIVE);
                yesButton.setOnClickListener(new View.OnClickListener() {
                    @Override
                    public void onClick(View view) {
                        //Now Background Class To Update Operator State
                        alertDialog.dismiss();
                        Toast.makeText(GroundEditActivity.this, "Click on Yes", Toast.LENGTH_SHORT).show();
                        //Do Something here 
                    }
                });

                noButton.setOnClickListener(new View.OnClickListener() {
                    @Override
                    public void onClick(View view) {
                        alertDialog.dismiss();
                        Toast.makeText(GroundEditActivity.this, "Click on No", Toast.LENGTH_SHORT).show();
                        //Do Some Thing Here 
                    }
                });
            }
        });

3.Pour afficher le dialogue d'alerte:

alertDialog.show();

Remarque: N'oubliez pas le mot-clé final avec AlertDialog.

Wajid khan
la source
0
AlertDialog.Builder altBx = new AlertDialog.Builder(this);
    altBx.setTitle("My dialog box");
    altBx.setMessage("Welcome, Please Enter your name");
    altBx.setIcon(R.drawable.logo);

    altBx.setPositiveButton("Ok", new DialogInterface.OnClickListener()
    {
      public void onClick(DialogInterface dialog, int which)
      {
          if(edt.getText().toString().length()!=0)
          {
              // Show any message
          }
          else 
          {

          }
      }
    });
    altBx.setNeutralButton("Cancel", new DialogInterface.OnClickListener()
    {
      public void onClick(DialogInterface dialog, int which)
      {
          //show any message
      }

    });
  altBx.show();  
Singhak
la source
0

vous pouvez implémenter une solution générique pour les décisions et utiliser dans un autre cas non seulement pour oui / non et personnaliser l'alerte avec des animations ou une mise en page:

Quelque chose comme ça; créez d'abord votre classe pour le transfert de données:

public class AlertDecision {

    private String question = "";
    private String strNegative = "";
    private String strPositive = "";

    public AlertDecision question(@NonNull String question) {
        this.question = question;
        return this;
    }

    public AlertDecision ansPositive(@NonNull String strPositive) {
        this.strPositive = strPositive;
        return this;
    }

    public AlertDecision ansNegative(@NonNull String strNegative) {
        this.strNegative = strNegative;
        return this;
    }

    public String getQuestion() {
        return question;
    }

    public String getAnswerNegative() {
        return strNegative;
    }

    public String getAnswerPositive() {
        return strPositive;
    }
}

après une interface pour retourner le résultat

public interface OnAlertDecisionClickListener {

    /**
     * Interface definition for a callback to be invoked when a view is clicked.
     *
     * @param dialog the dialog that was clicked
     * @param object The object in the position of the view
     */
    void onPositiveDecisionClick(DialogInterface dialog, Object object);
    void onNegativeDecisionClick(DialogInterface dialog, Object object);
}

Vous pouvez maintenant créer facilement des utilitaires d'accès (dans cette classe, vous pouvez implémenter différentes animations ou dispositions personnalisées pour l'alerte):

public class AlertViewUtils {

    public static void showAlertDecision(Context context,
                                         @NonNull AlertDecision decision,
                                         final OnAlertDecisionClickListener listener,
                                         final Object object) {

        AlertDialog.Builder builder = new AlertDialog.Builder(context);
        builder.setMessage(decision.getQuestion());
        builder.setPositiveButton(decision.getAnswerPositive(),
                new DialogInterface.OnClickListener() {
                    public void onClick(DialogInterface dialog, int which) {
                        listener.onPositiveDecisionClick(dialog, object);
                    }
                });

        builder.setNegativeButton(decision.getAnswerNegative(),
                new DialogInterface.OnClickListener() {
                    public void onClick(DialogInterface dialog, int which) {
                        listener.onNegativeDecisionClick(dialog, object);
                    }
                });

        android.support.v7.app.AlertDialog dialog = builder.create();
        dialog.show();
    }
}

et le dernier appel en activité ou fragment; vous pouvez l'utiliser dans votre cas ou pour une autre tâche:

public class MainActivity extends AppCompatActivity {

@Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity);
        initResources();
    }

    public void initResources() {
        Button doSomething = (Button) findViewById(R.id.btn);
        doSomething.setOnClickListener(getDecisionListener());
    }

    private View.OnClickListener getDecisionListener() {
        return new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                AlertDecision decision = new AlertDecision()
                        .question("question ...")
                        .ansNegative("negative action...")
                        .ansPositive("positive action... ");
                AlertViewUtils.showAlertDecision(MainActivity.this,
                        decision, getOnDecisionListener(), v);
            }
        };
    }

    private OnAlertDecisionClickListener getOnDecisionListener() {
        return new OnAlertDecisionClickListener() {
            @Override
            public void onPositiveDecisionClick(DialogInterface dialog, Object object) {

                //do something like create, show views, etc...
            }

            @Override
            public void onNegativeDecisionClick(DialogInterface dialog, Object object) {
                //do something like delete, close session, etc ...
            }
        };
    }
} 
Alex Zaraos
la source
0

Vous pouvez le faire si facilement à Kotlin:

 alert("Testing alerts") {
    title = "Alert"
    yesButton { toast("Yess!!!") }
    noButton { }
}.show()
Serg Burlaka
la source
0

Pour Kotlin dans Android ::

    override fun onBackPressed() {
        confirmToCancel()
    }

    private fun confirmToCancel() {
        AlertDialog.Builder(this)
            .setTitle("Title")
            .setMessage("Do you want to cancel?")
            .setCancelable(false)
            .setPositiveButton("Yes") {
                dialog: DialogInterface, _: Int ->
                dialog.dismiss()
                // for sending data to previous activity use
                // setResult(response code, data)
                finish()
            }
            .setNegativeButton("No") {
                dialog: DialogInterface, _: Int ->
                dialog.dismiss()
            }
            .show()
    } 
Partha Paul
la source
0

Implémentation de Kotlin.

Vous pouvez créer une fonction simple comme celle-ci:

fun dialogYesOrNo(
        activity: Activity,
        title: String,
        message: String,
        listener: DialogInterface.OnClickListener
    ) {
        val builder = AlertDialog.Builder(activity)
        builder.setPositiveButton("Yes", DialogInterface.OnClickListener { dialog, id ->
            dialog.dismiss()
            listener.onClick(dialog, id)
        })
        builder.setNegativeButton("No", null)
        val alert = builder.create()
        alert.setTitle(title)
        alert.setMessage(message)
        alert.show()
    }

et appelez-le comme ceci:

dialogYesOrNo(
  this,
  "Question",
  "Would you like to eat?",
  DialogInterface.OnClickListener { dialog, id ->
    // do whatever you need to do when user presses "Yes"
  }
})
Christian
la source