Ist es möglich, ein Popup mit Javascript zu öffnen und dann zu erkennen, wann der Benutzer es schließt?

73

Die Frage ist so ziemlich alles im Titel.

Ist es möglich (und wie?), Ein Popup mit Javascript zu öffnen und dann zu erkennen, wann der Benutzer es schließt?

Ich verwende jquery innerhalb des Projekts, daher wäre eine jquery-Lösung gut. Prost!

Pablo
quelle
Definieren Sie "Popup". Sprechen wir über eine Art gerenderte Modalbox auf der Seite? Ein Javascript-Alarm? Ein neues Browserfenster?
DA.
1
Ein neues Browserfenster ... Entschuldigung für meine Unklarheit
Pablo

Antworten:

98

Wenn Sie die Kontrolle über den Inhalt des Popups haben, behandeln Sie das unloadEreignis des Fensters dort und benachrichtigen Sie das ursprüngliche Fenster über die openerEigenschaft. Überprüfen Sie zunächst, ob der Öffner geschlossen wurde. Beachten Sie, dass dies in Opera nicht immer funktioniert.

window.onunload = function() {
    var win = window.opener;
    if (!win.closed) {
        win.someFunctionToCallWhenPopUpCloses();
    }
};

Da das unloadEreignis immer dann ausgelöst wird, wenn der Benutzer von der Seite im Popup weg navigiert und nicht nur, wenn das Fenster geschlossen ist, sollten Sie überprüfen, ob das Popup tatsächlich geschlossen wurde someFunctionToCallWhenPopUpCloses:

var popUp = window.open("popup.html", "thePopUp", "");
function someFunctionToCallWhenPopUpCloses() {
    window.setTimeout(function() {
        if (popUp.closed) {
            alert("Pop-up definitely closed");
        }
    }, 1);
}

Wenn Sie keine Kontrolle über den Inhalt des Popups haben oder wenn einer Ihrer Zielbrowser das unloadEreignis nicht unterstützt , werden Sie im Hauptfenster auf eine Art Abfragelösung reduziert. Passen Sie das Intervall an.

var win = window.open("popup.html", "thePopUp", "");
var pollTimer = window.setInterval(function() {
    if (win.closed !== false) { // !== is required for compatibility with Opera
        window.clearInterval(pollTimer);
        someFunctionToCallWhenPopUpCloses();
    }
}, 200);
Tim Down
quelle
3
Ich empfehle die Polling-Lösung anstelle des unloadEreignisses, da sie mit mehr Browsern kompatibel ist (siehe opera-bugs.jottit.com ).
Jonathon Hill
@ JonathonHill: Einverstanden. Ich habe früher in der Antwort auf das Opera-Problem hingewiesen, aber ich hätte den Punkt klarer machen sollen. Danke für die Bearbeitung. Übrigens, was ist der Grund für die Anforderung window.closed !== falsein Opera?
Tim Down
Es ist eine Problemumgehung für einen Fehler in Opera. Ich habe es von opera-bugs.jottit.com entdeckt .
Jonathon Hill
@ JonathonHill: Ja, ich habe die Seite gelesen. Ich hatte auf mehr Details gehofft. Mach dir keine Sorgen, ich werde es nachschlagen.
Tim Down
1
Wenn Sie die Abrufoption verwenden, sollten Sie den window.clearInterval()Anruf auf keinen Fall vergessen . Wenn es nicht enthalten ist, wird die ursprüngliche Seite weiterhin
abrufen
11

Es gibt eine sehr einfache Lösung für Ihr Problem.

Erstellen Sie zuerst ein neues Objekt, das einen Pop wie folgt öffnet:

var winObj = window.open('http://www.google.com','google','width=800,height=600,status=0,toolbar=0');

Um zu wissen, wann dieses Popup-Fenster geschlossen ist, müssen Sie dies nur mit einer Schleife wie der folgenden überprüfen:

var loop = setInterval(function() {   
    if(winObj.closed) {  
        clearInterval(loop);  
        alert('closed');  
    }  
}, 1000); 

Jetzt können Sie die Warnung durch einen beliebigen Javascript-Code ersetzen.

Habe Spaß! :) :)

Kshitij Mittal
quelle
7

Versuchen Sie, die Ereignisse unloadund beforeunloadFenster zu untersuchen. Wenn Sie diese überwachen, sollten Sie die Möglichkeit haben, zurückzurufen, wenn das DOM entladen wird, wenn das Fenster über Folgendes geschlossen wird:

var newWin = window.open('/some/url');
newWin.onunload = function(){
  // DOM unloaded, so the window is likely closed.
}
ajm
quelle
Danke ajm sieht toll aus. Gibt es überhaupt eine Möglichkeit, die URL eines Popups zu erhalten?
Pablo
Dies funktioniert nicht browserübergreifend. Sie müssen das unloadEreignis im Popup behandeln.
Tim Down
Entladen Sie Brände bei jeder neuen Anforderung, nicht nur beim Schließen des Fensters.
Josh Stodola
Ja, YMMV mit Entladung. Wahrscheinlich benötigen Sie eine Kombination aus Entladen und Vorentladen, um die IEs abzudecken. @Josh - Unload sollte immer dann ausgelöst werden, wenn das Dokument des untergeordneten Fensters unabhängig von Anforderungen aus dem Browser entladen wird. Welches Verhalten sehen Sie?
Ajm
Wenn sich beispielsweise im Popup-Fenster Hyperlinks befinden, wird ein Klick darauf ausgelöst unload.
Josh Stodola
6

Wenn Sie das jQuery-UI-Dialogfeld verwenden können , hat es tatsächlich ein closeEreignis.

eje211
quelle
11
jQuery ist nicht die Lösung für jedes Problem :).
s4y
11
Wahr, wahr. Ich hätte meine Antwort mit dem Wort "if" wie in "If you use the jQuery UI Dialog" beginnen sollen und nicht nur davon ausgehen sollen, dass dies möglich ist. Hallo! Warten Sie eine Sekunde ...
eje211
3
Und wenn es um JavaScript geht, ist jQuery nie wirklich eine Lösung für Probleme, sondern oft eine riesige, RIESIGE, RIESIGE Verknüpfung zur Lösung, was auch immer es sein mag. Sie lernen mehr, indem Sie die landschaftlich reizvolle Route wählen, aber in vielen Fällen bevorzugen ich und die meisten Menschen die (riesige, RIESIGE, RIESIGE ) jQuery-Verknüpfung.
eje211
3

So öffnen Sie einen neuen Fensteraufruf:

var wnd = window.open("file.html", "youruniqueid", "width=400, height=300");

Wenn Sie nur wissen möchten, wann dieses Fenster geschlossen wird, verwenden Sie onunload.

wnd.onunload = function(){
    // do something
};

Wenn Sie eine Bestätigung vom Benutzer wünschen, bevor der Benutzer sie schließen kann, verwenden Sie onbeforeunload .

wnd.onbeforeunload = function(){
    return "are you sure?";
};
jAndy
quelle
1
Dies funktioniert nicht browserübergreifend. Sie müssen das unloadEreignis im Popup-Dokument behandeln.
Tim Down
1
Entladen Sie Brände bei jeder neuen Anforderung, nicht nur beim Schließen des Fensters.
Josh Stodola
3

Wir machen das in einem meiner Projekte bei der Arbeit.

Der Trick besteht darin, eine JS-Funktion auf Ihrer übergeordneten Seite zu haben, die Sie beim Schließen des Popups aufrufen möchten, und dann das Entladeereignis in das Popup einzubinden.

Das window.opener Eigenschaft bezieht sich auf die Seite, auf der dieses Popup erstellt wurde.

Wenn ich beispielsweise eine callingPageFunctionauf meiner Originalseite benannte Funktion geschrieben hätte, würde ich sie im Popup folgendermaßen aufrufen:

$(window).unload(function() {
    window.opener.callingPageFunction()
});

Zwei Anmerkungen:

  1. Dies sollte in eine Bereitschaftsfunktion eingewickelt werden.
  2. Ich habe eine anonyme Funktion, weil Sie dort möglicherweise andere Logik wünschen
Powerlord
quelle
1

Ich denke, der beste Weg ist:

const popup = this.window.open(url.toString());
popup.addEventListener('unload', ()=> console.log('closed'))
Serginho
quelle
0

Ja, behandeln Sie das Ereignis onbeforeUnload für das Popup-Fenster und rufen Sie dann eine Funktion im übergeordneten Fenster auf, indem Sie:

window.opener.myFunction()
TimS
quelle