$ (document) .on ("click" ... funktioniert nicht?


81

Gibt es einen bekannten Fehler, den ich hier machen könnte?

Ich habe ein Skript, das .on () verwendet, weil ein Element dynamisch generiert wird und nicht funktioniert. Um es auszuprobieren, habe ich den Selektor durch den Wrap des dynamischen Elements ersetzt, der statisch ist und immer noch nicht funktioniert hat! Als ich zu einfachem altem .click für den Wrap wechselte, funktionierte es jedoch.
(Dies funktioniert offensichtlich nicht für das dynamische Element, das wichtig ist.)

Das funktioniert:

$("#test-element").click(function() {
    alert("click");
});

Das geht nicht:

$(document).on("click","#test-element",function() {
    alert("click");
});

AKTUALISIEREN:

Ich habe mit der rechten Maustaste geklickt und "Element überprüfen" in Chrome ausgeführt, um nur etwas zu überprüfen. Danach hat das Klickereignis funktioniert. Ich habe mich aktualisiert und es hat nicht funktioniert, das Element inspiziert und dann hat es funktioniert. Was bedeutet das?


1
Erstellen Sie mehr als ein Element mit derselben ID?
Adeneo

Wenn Sie nur die jQuery ohne den entsprechenden HTML-Code veröffentlichen, ist die Unterstützung schwierig.
jmoerdyk

3
Hiya OP, bitte überprüfen Sie die Version von Jquery, die Sie verwenden, :)oder schnippen Sie eine Geige, die ich Ihnen helfen könnte,
Tats_innit

Ihr Code soll funktionieren. Die onFunktion wurde in jquery 1.7 hinzugefügt. Stellen Sie sicher, dass Sie eine aktuelle Version haben. Bearbeiten: Beweis für Sie, dass es auf Geige funktioniert
Phil-R

Ihr zweites Beispiel funktioniert mit der neuesten 1.x-Version von jQuery: jsfiddle.net/AJPdS
Wookai

Antworten:


152

Sie verwenden die richtige Syntax für die Bindung an das Dokument, um auf ein Klickereignis für ein Element mit id = "test-element" zu warten.

Es funktioniert wahrscheinlich nicht aufgrund einer der folgenden Ursachen:

  • Keine aktuelle Version von jQuery verwenden
  • Wickeln Sie Ihren Code nicht in DOM ein
  • oder Sie tun etwas, das dazu führt, dass das Ereignis nicht zum Listener im Dokument sprudelt.

Um Ereignisse für Elemente zu erfassen, die NACH dem Deklarieren Ihrer Ereignis-Listener erstellt wurden, sollten Sie an ein übergeordnetes Element oder ein Element in einer höheren Hierarchie binden.

Zum Beispiel:

$(document).ready(function() {
    // This WILL work because we are listening on the 'document', 
    // for a click on an element with an ID of #test-element
    $(document).on("click","#test-element",function() {
        alert("click bound to document listening for #test-element");
    });

    // This will NOT work because there is no '#test-element' ... yet
    $("#test-element").on("click",function() {
        alert("click bound directly to #test-element");
    });

    // Create the dynamic element '#test-element'
    $('body').append('<div id="test-element">Click mee</div>');
});

In diesem Beispiel wird nur die Warnung "An Dokument gebunden" ausgelöst.

JSFiddle mit jQuery 1.9.1


Leider verwende ich eine aktuelle Version von Jquery, mein Code ist ordnungsgemäß verpackt, befindet sich in $ (document) .ready und das Ereignis, auf das geklickt wird, ist das Element der untersten Ebene im Dokument. Das ist verwirrend.
Herr Lavalamp

Ich würde sagen, dass "der Listener auf das übergeordnete Element gesetzt werden muss" nicht unbedingt erforderlich ist, obwohl ich es auch empfehle. Durch Blasen kann .on () funktionieren. Wenn wir uns nicht darauf verlassen könnten, dass das Sprudeln an den unmittelbaren Eltern vorbeigeht, wäre dies keine großartige Lösung.
iGanja

@iGanja - guter Punkt und wie Sie vorschlagen, ist "Bedürfnis" nicht das richtige Wort, da es andere weniger ideale Möglichkeiten gibt, dies zu erreichen. Ich habe meine Antwort überarbeitet.
itsmejodie

Wenn ich "this" verwende, um auf ein Elementobjekt zu verweisen, wie kann ich dann das Ereignis mit dem Dokument
verknüpfen?

1
@JasonGlisson Ich vermute, während Sie einen Listener für das Dokument haben, gibt es entweder ein Problem mit dem nicht sprudelnden Ereignis (durch Klicken auf die Schaltfläche) oder den Unterschied zwischen event.targetund event.currentTargetirgendwo in Ihrem Code, aber es gibt viele Dinge, die es sein könnte, einschließlich
Zeigerereignisse, die

11

Ihr Code sollte funktionieren, aber mir ist bewusst, dass die Antwort Ihnen nicht hilft. Sie können hier ein funktionierendes Beispiel sehen (jsfiddle) .

Jquery:

$(document).on('click','#test-element',function(){
    alert("You clicked the element with and ID of 'test-element'");
});

Wie bereits erwähnt, verwenden Sie anstelle einer Klasse eine ID. Wenn Sie mehr als ein Element auf der Seite mit einer ID haben, gibt jquery nur das erste Element mit dieser ID zurück . Es wird keine Fehler geben, denn so funktioniert es. Wenn dies das Problem ist, werden Sie feststellen, dass das Klickereignis für das erste, test-elementjedoch nicht für das folgende Ereignis funktioniert .

Wenn dies die Symptome des Problems nicht genau beschreibt, ist Ihr Selektor möglicherweise falsch. Ihr Update lässt mich glauben, dass dies der Fall ist, weil ich ein Element inspiziere, dann erneut auf die Seite klicke und den Klick auslöse. Dies könnte dazu führen, dass Sie den Ereignis-Listener auf den tatsächlichen documentanstatt auf den tatsächlichen setzen test-element. Wenn dies der Fall ist, wird das Ereignis ausgelöst, wenn Sie auf das Dokument klicken und es wieder aktivieren (z. B. vom Entwicklerfenster zurück zum Dokument). In diesem Fall werden Sie auch feststellen, dass das Klickereignis ausgelöst wird, wenn Sie zwischen zwei verschiedenen Registerkarten klicken (da es sich um zwei verschiedene Registerkarten handelt documentund Sie daher auf das Dokument klicken.

Wenn beides nicht die Antwort ist, trägt das Posten von HTML wesentlich dazu bei, dies herauszufinden.


4

Ein alter Beitrag, den ich aber gerne teile, da ich den gleichen Fall habe, aber endlich das Problem kannte:

Das Problem ist: Wir machen eine Funktion für die Arbeit mit einem bestimmten HTML-Element, aber das mit dieser Funktion verbundene HTML-Element ist noch nicht erstellt (da das Element dynamisch generiert wurde). Damit es funktioniert, sollten wir die Funktion gleichzeitig mit dem Erstellen des Elements erstellen. Element zuerst als Funktion damit verbunden machen.

Einfach gesagt, eine Funktion funktioniert nur mit dem Element, das vor ihr erstellt wurde (er). Alle Elemente, die dynamisch erstellt wurden, bedeuten nach ihm.

Bitte überprüfen Sie dieses Muster, das den obigen Fall nicht beachtet hat:

<div class="btn-list" id="selected-country"></div>

Dynamisch angehängt:

<button class="btn-map" data-country="'+country+'">'+ country+' </button>

Diese Funktion funktioniert gut, wenn Sie auf die Schaltfläche klicken:

$(document).ready(function() {    
        $('#selected-country').on('click','.btn-map', function(){ 
        var datacountry = $(this).data('country'); console.log(datacountry);
    });
})

oder Sie können Körper wie verwenden:

$('body').on('click','.btn-map', function(){ 
            var datacountry = $(this).data('country'); console.log(datacountry);
        });

Vergleiche damit, dass es nicht funktioniert:

$(document).ready(function() {     
$('.btn-map').on("click", function() { 
        var datacountry = $(this).data('country'); alert(datacountry);
    });
});

hoffe es wird helfen


Sie können die Verwendung von $ (Dokument) vermeiden. Sie müssen bereits darauf warten, dass das Element zum DOM hinzugefügt wird, wenn Sie stattdessen mit $ (Dokument) .on ("click" ... $ (document) .on ("click") beginnen. "# selected-country", function () {});
Loren

3

Das funktioniert:

<div id="start-element">Click Me</div>

$(document).on("click","#test-element",function() {
    alert("click");
});

$(document).on("click","#start-element",function() {
    $(this).attr("id", "test-element");
});

Hier ist die Geige


1
Das ist laut Frage kein dynamisch generiertes Element.
itsmejodie

@itsmejodie - stimmte zu, ist aber dynamisch an den Event-Handler gebunden. Das Ändern der ID unterscheidet sich im Wesentlichen nicht vom Anhängen eines DOM-Elements.
iGanja

1

Versuche dies:

$("#test-element").on("click" ,function() {
    alert("click");
});

Die Art und Weise, wie Dokumente erstellt werden, ist ebenfalls seltsam. Das wäre für mich sinnvoll, wenn es für einen Klassenselektor verwendet würde, aber im Fall einer ID haben Sie wahrscheinlich nur nutzloses DOM, das dort durchläuft. Im Fall des ID-Selektors erhalten Sie dieses Element sofort.


2
Wie unterscheidet sich das von $("#test-element").click(function() {?
Sushanth -

2
Sie müssen .on () verwenden, um Ereignisse an dynamisch generierte DOMs zu binden. Alles, was mit .click () gebunden ist, versucht zu binden, wenn das Dokument fertig ist, und wenn der Dom nicht vorhanden ist, passiert nichts.
JTravakh

2
Aber .onohne a zu verwenden selectorist dasselbe wie das Click-Ereignis direkt darauf anzuwenden
Sushanth -

1
Dies ist nicht die richtige Antwort auf die Frage. Dies wird direkt an das Element gebunden und ist daher nicht geeignet, wenn das Element dynamisch generiert wurde.
itsmejodie

1
Ich habe die Dokumente tatsächlich gelesen, aber der Abschnitt über die Leistung hat eigentlich nichts mit delegierten Ereignishandlern zu tun, und Ihr Code ist kein delegierter Ereignishandler.
Adeneo
Durch die Nutzung unserer Website bestätigen Sie, dass Sie unsere Cookie-Richtlinie und Datenschutzrichtlinie gelesen und verstanden haben.
Licensed under cc by-sa 3.0 with attribution required.