Verhindern Sie, dass der Android-Aktivitätsdialog bei Berührung von außen geschlossen wird

228

Ich habe eine Aktivität, die den Theme.Dialog-Stil verwendet, sodass es sich um ein schwebendes Fenster über einer anderen Aktivität handelt. Wenn ich jedoch außerhalb des Dialogfensters (auf die Hintergrundaktivität) klicke, wird das Dialogfeld geschlossen. Wie kann ich dieses Verhalten stoppen?

Fergusmac
quelle
1
Warum würdest du das übrigens tun? Wenn das gewünschte Verhalten ein Dialog ist, warum nicht einen Dialog verwenden? Ich komme zu Ihrer Frage und glaube nicht, dass es dafür eine Lösung gibt.
Kumar Bibek
@ KumarBibek-Dialoge sind begrenzt, wenn es um Layoutanpassungen geht ... deshalb eine Aktivität. Sogar die Entwicklerdokumentation empfiehlt diesen Ansatz für eine flexible Anpassung
Leo
1
Was das OP möchte, ist ein modaler Dialog, dh ein Dialog, der den Benutzer zur Antwort zwingt, z. B. OK oder Ja / Nein. Der Benutzer sollte nicht einfach wegklicken können.
Scott Biggs

Antworten:

33

Dies könnte Ihnen helfen. Es ist eine Möglichkeit, die Berührung außerhalb des Ereignisses zu handhaben:

Wie kann ich einen Dialog mit dem Thema Aktivität abbrechen, wenn ich ihn außerhalb des Fensters berühre?

Ich denke, Sie können das Schließen verhindern, indem Sie das Ereignis einfangen und nichts tun. Was jedoch seltsam ist, ist, dass das Standardverhalten Ihres Aktivitätsdialogs nicht darin bestehen sollte, sich selbst zu schließen, wenn Sie nach draußen berühren.

(PS: Der Code verwendet WindowManager.LayoutParams)

Michel-F. Portzert
quelle
1
Das Objekt ist jedoch kein Dialogfeld, sondern eine Aktivität, die den Dialogstil verwendet. Aktivität verfügt nicht über diese Methode und kann nicht in Dialog umgewandelt werden.
Fergusmac
Ihr Beitrag ist das genaue Gegenteil von dem, was gefragt wurde. er fragte, wie man das Schließen verhindert und nicht wie man es verursacht.
ChuckKelly
4
Welches ist, was er mit "Indem Sie das Ereignis fangen und nichts tun, denke ich, können Sie das Schließen verhindern" erklärte.
Metter
4
Aus irgendeinem Grund werden nach dem Ausführen des gesamten FLAG_NOT_MODAL, WATCH_OUTSIDE_TOUCH durch die äußere Berührung die Aktivitäten nicht geschlossen, sondern auf die Schaltfläche hinter der Aktivität geklickt. Hast du eine Idee dafür?
NJZK2
Beachten Sie, dass Dialoge einen Schatten haben (zumindest bis jetzt (8.0)): Wenn Sie auf den Schatten klicken, interpretiert Android diesen Klick so, wie er im Dialog war. Ich wollte das nur mit der Welt teilen, ich habe 10 Minuten gebraucht, um es zu bekommen.
Lorenzo Von Matterhorn
458

Verwenden Sie diese Option, um zu verhindern, dass das Dialogfeld beim Drücken der Zurück-Taste geschlossen wird

dialog.setCancelable(false);

Verwenden Sie diese Option, um zu verhindern, dass das Dialogfeld bei Berührung von außen geschlossen wird

 dialog.setCanceledOnTouchOutside(false);
Singhak
quelle
4
Diese Antwort ist hilfreich, aber bei dieser Frage geht es um Aktivitäten mit dem Attribut Theme.Dialog.
Paresh Mayani
15
Ich weiß, wenn ich merke, dass es zu spät ist, da es vielen Menschen hilft und es nicht gelöscht hat.
Singhak
12
Ich weiß, dass dies nicht wirklich mit der Frage zu tun hatte, aber das hat mir geholfen. Vielen Dank!
Dennis zog
5
Dies ist die beste Antwort. Ich vermute, dass die meisten Leute, die diese Frage finden, nach einer Möglichkeit suchen, zu verhindern, dass der Standard AlertDialogbei Berührung im Freien geschlossen wird, und genau das bietet diese Antwort.
aroth
20
In neueren Versionen von AlertDialog müssen Sie nursetCancelable(false)
Kobi Tate
120

Was Sie tatsächlich haben, ist eine Aktivität (auch wenn sie wie ein Dialog aussieht). Daher sollten Sie setFinishOnTouchOutside(false)von Ihrer Aktivität aus anrufen, wenn Sie sie beim Klicken auf die Hintergrundaktivität geöffnet lassen möchten.

BEARBEITEN: Dies funktioniert nur mit Android API Level 11 oder höher

Artex
quelle
4
Dies hindert Sie nicht daran, in Ihrer Aktivität die "Zurück" -Taste zu drücken. Sie müssen also auch außer Kraft setzen onBackPressed(), nichts in seinem Körper zu tun
Alex Bonel
Es verhindert nicht die Schaltfläche "Zurück" in diesem Dialogfeld Aktivität ohne onBackPressed (). Funktioniert perfekt mit this.setFinishOnTouchOutside (false).
Kunalxigxag
68

Was für mich funktioniert hat, war, DialogFragmentein Set zu erstellen , das nicht stornierbar ist:

dialog.setCancelable(false);
Petr
quelle
1
Nicht hilfreich. Diese Frage bezieht sich auf Aktivitäten, nicht auf Dialoge.
Scott Biggs
20

Wenn Sie den Dialog als Aktivität in onCreate verwenden, fügen Sie dies hinzu

setFinishOnTouchOutside(false);
Ronny Shibley
quelle
17

Bei einer höheren API 10 verschwindet der Dialog, wenn er außerhalb berührt wird, während bei einer niedrigeren als API 11 der Dialog nicht verschwindet. Um dies zu verhindern, müssen Sie Folgendes tun:

In styles.xml:<item name="android:windowCloseOnTouchOutside">false</item>

ODER

onCreate()Verwenden Sie in der Methode:this.setFinishOnTouchOutside(false);

Hinweis: Für API 10 und niedriger hat diese Methode keine Wirkung und wird nicht benötigt.

ilw
quelle
14

Es reicht aus, das Dialogfeld abzubrechen auf "falsch" zu setzen. Wenn Sie entweder außerhalb des Warnungsdialogs berühren oder auf die Schaltfläche "Zurück" klicken, wird das Warnungsdialogfeld ausgeblendet. Also benutze dieses:

setCancelable(false)

Und die andere Funktion ist nicht mehr notwendig: dialog.setCanceledOnTouchOutside(false);

Wenn Sie einen temporären Dialog erstellen und sich fragen, ob Sie diese Codezeile einfügen möchten, finden Sie hier ein Beispiel:

new AlertDialog.Builder(this)
                        .setTitle("Trial Version")
                        .setCancelable(false)
                        .setMessage("You are using trial version!")
                        .setIcon(R.drawable.time_left)
                        .setPositiveButton(android.R.string.yes, null).show();
BillOverFlow
quelle
12

Verwenden Sie diesen Code, der für mich funktioniert

 AlertDialog.Builder alertDialog = new AlertDialog.Builder(this);
 alertDialog.setCancelable(false);

Aslam Patel
quelle
Dies sollte die richtige Antwort sein, wenn er die richtige Frage stellen könnte!
Alijunior
2
Dies wäre die richtige Antwort, wenn das OP nach Dialogen fragen würde ! Aber die Frage betrifft Aktivitäten - ein ganz anderer Fall.
Scott Biggs
11
Dialog dialog = new Dialog(context)
dialog.setCanceledOnTouchOutside(true); 
//use this to dismiss the dialog on outside click of dialog

dialog.setCanceledOnTouchOutside(false);
//use this for not to dismiss the dialog on outside click of dialog.

Weitere Informationen zum Dialog finden Sie unter diesem Link .

dialog.setCancelable(false);
//used to prevent the dismiss of dialog on backpress of that activity

dialog.setCancelable(true);
//used to dismiss the dialog on onbackpressed of that activity
anand krish
quelle
Bitte beachten Sie, dass sich die Frage auf Aktivitäten bezieht, die als Dialoge verwendet werden, NICHT auf die Dialogklasse.
Scott Biggs
8

Einfach,

alertDialog.setCancelable(false);

Verhindern, dass der Benutzer außerhalb des Dialogfelds klickt.


quelle
6

Der Warnungsdialog ist veraltet. Verwenden Sie daher Dialog dialog = new Dialog (this);

Zur Vermeidung von Berührungen von außen

dialog.setCanceledOnTouchOutside(false);
Muhammed Fasil
quelle
5

Verwenden Sie setFinishOnTouchOutside(false)für API> 11 und machen Sie sich keine Sorgen, da das Standardverhalten des Android, dass der Dialog zum Thema Aktivität bei API <11 nicht von außen ausgeführt wird, nicht beendet wird :) !! Prost !!

Vishal Pandey
quelle
5

Ich benutze dies in onCreate (), scheint auf jeder Version von Android zu funktionieren; Auf 5.0 und 4.4.x getestet, kann nicht auf Gingerbread getestet werden. Samsung-Geräte (Hinweis 1 mit GB) haben dies standardmäßig folgendermaßen:

    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.HONEYCOMB)
    {
        setFinishOnTouchOutside(false);
    }
    else
    {
        getWindow().clearFlags(LayoutParams.FLAG_WATCH_OUTSIDE_TOUCH);
    }

    super.onCreate(savedInstanceState);
3c71
quelle
4
        alert.setCancelable(false);
        alert.setCanceledOnTouchOutside(false);

Ich denke, das wird dir helfen. Es hat bei mir funktioniert

user2532065
quelle
1
Bitte versuchen Sie auch zu erklären, warum dies funktioniert ... Nur ein Code-Dump ist keine gute Antwort.
Codebender
3

Hier ist meine Lösung:

AlertDialog.Builder builder = new AlertDialog.Builder(this);
builder.setTitle("Select The Difficulty Level");
builder.setCancelable(false);
Akhter Al Amin
quelle
2

Es ist auch möglich, verschiedene Aktionen zuzuweisen, die onCancelListener implementieren:

alertDialog.setOnCancelListener(new DialogInterface.OnCancelListener(){                   
    @Override
    public void onCancel(DialogInterface dialogInterface) {
        //Your custom logic
    } 
});
Adae Rodríguez
quelle
Wie kann ich feststellen, ob der Abbruch aufgerufen wird, weil außerhalb des Warndialogs getippt wurde?
Cegprakash
Sehr hilfreich, um benutzerdefinierte Aktionen beim Tippen außerhalb eines Warndialogs zu erstellen!
Adam S.
1

Ich hatte das gleiche Problem. Um damit umzugehen, setze ich ein OntouchListenerauf den Dialog und mache nichts drinnen. Der Dialog wird jedoch auch beim Drehen des Bildschirms geschlossen. Um dies zu beheben, habe ich eine Variable festgelegt, die mir mitteilt, ob der Dialog normalerweise geschlossen wurde. Dann setze ich ein OnDismissListenerauf meinen Dialog und überprüfe darin die Variable. Wenn der Dialog normalerweise deaktiviert wurde, tue ich nichts, oder ich führe den Dialog erneut aus (und setze seinen Status wie beim Entlassen in meinem Fall).

Madara
quelle
1

builder.setCancelable (false);


public void Mensaje (Ansicht v) {

    AlertDialog.Builder builder = new AlertDialog.Builder(this);
    builder.setTitle("¿Quieres ir a el Menú principal?");
    builder.setMessage("Al presionar SI iras a el menú y saldras de la materia.");
    builder.setPositiveButton("SI", null);
    builder.setNegativeButton("NO", null);
    builder.setCancelable(false);
    builder.show();
}
Alex Skriivordemgentschenfelde
quelle
1
Hallo Alex. Willkommen bei StackOverflow und vielen Dank für Ihre Antwort. Könnten Sie bitte Ihre Antwort bearbeiten, um zu beschreiben, was Ihr Code tut und wie dies das Problem des OP löst? Nur-Code-Antworten werden nicht empfohlen, da sie das Warum nicht lehren oder erklären . Danke dir!
Tim Malone
-1

Dies ist die perfekte Antwort auf alle Ihre Fragen .... Ich hoffe, Sie genießen das Codieren in Android

new AlertDialog.Builder(this)
            .setTitle("Akshat Rastogi Is Great")
            .setCancelable(false)
            .setMessage("I am the best Android Programmer")
            .setPositiveButton("I agree", new DialogInterface.OnClickListener() {
                @Override
                public void onClick(DialogInterface dialog, int which) {
                    dialog.dismiss();

                }
            })
            .create().show();
Akshat Rasogi
quelle
Vielen Dank für dieses Code-Snippet, das möglicherweise nur begrenzte und sofortige Hilfe bietet. Eine richtige Erklärung würde ihren langfristigen Wert erheblich verbessern, indem sie zeigt, warum dies eine gute Lösung für das Problem ist, und es für zukünftige Leser mit anderen, ähnlichen Fragen nützlicher machen. Bitte bearbeiten Sie Ihre Antwort, um eine Erklärung hinzuzufügen, einschließlich der von Ihnen getroffenen Annahmen.
Maximilian Peters