Ereignisse waren schon immer eines der mächtigsten Objekte in JavaScript. JavaScript bietet zwei Methoden, addEventListener und attachmentEvent, um Ereignisse an DOM-Knoten zu binden. JQuery kapselt sie weiter und stellt eine mit verschiedenen Browsern kompatible Bindungsmethode bereit. Nun weist diese traditionelle Ereignisbindungsmethode die folgenden Mängel auf:
1. Möglicherweise müssen Sie viele EventHander binden.
Wenn eine Tabelle auf der Seite 100 Zeilen enthält, muss an jede Zeile ein Klickereignis gebunden werden. Dann müssen 100 EventHandler gebunden werden, was die Seitenleistung enorm belastet, da mehr Speicher zum Speichern dieser Handler geschaffen werden muss.
2. Das Ereignis kann nach der Bindung an den DOM-Knoten nicht hinzugefügt werden.
Wenn der Code auf der Seite wie folgt lautet:
Kopieren Sie den Codecode wie folgt:
$("#dv").bind('click',function(){alert('test');});
$(body).append('<div id="dv">test</div>')
Das später hinzugefügte Div kann keine Klickereignisse auslösen.
Um diese beiden Probleme zu lösen, führte JavaScript einen Ereignis-Proxy (Ereignis-Proxy) ein. Lassen Sie uns zunächst den Blasenmechanismus in js verstehen.
Grundsätzlich unterstützen alle Browser das Event-Bubbling. Wenn ein Ereignis auf einem DOM-Knoten ausgelöst wird, wird das Ereignis bis zum Stammknoten des Dokuments weitergegeben. Da alle Knotenereignisse schließlich an den Dokumentstammknoten übermittelt werden, wird es viel reduzieren, wenn wir das Ereignis direkt an den Dokumentstammknoten (Dokumentknoten) binden und dann event.target verwenden, um zu bestimmen, welcher Knoten das Ereignis ausgelöst hat EventHandler? Was ist mit der Bindung?
Die Live-Methode in JQuery basiert offiziell auf diesem Prinzip. Lassen Sie uns eine einfache Version von Live implementieren:
Kopieren Sie den Codecode wie folgt:
$.fn.mylive=function(eventType,fn){
var that=this.selector;
$(document).bind(eventType,function(event){
var match=$(event.target).closest(that)
if(match.length !== 0){
fn.apply($(event.target),[event]);
}
})
}
$("#tb td").mylive('click',function(event){
alarm(event.target.innerHTML);
});
var tb='<table id="tb"> /
<tr> /
<td>die erste Spalte</td>/
<td>die zweite Spalte</td>/
<td>die dritte Spalte</td>/
</tr>/
</table>';
$("body").append(tb);
In der Live-Methode ist das Ereignis an den Dokumentknoten gebunden und $(event.target).closest(that) stimmt mit dem Element überein, das das Ereignis tatsächlich ausgelöst hat. In der Demo haben wir das Klickereignis für jedes später hinzugefügte TD gebunden. Wenn wir auf verschiedene TDs klicken, werden die entsprechenden Textaufforderungsfelder angezeigt.
Die Live-Methode gleicht die beiden zuvor erwähnten Mängel der herkömmlichen Ereignisbindungsmethode aus. Aber die Live-Methode hat immer noch ihre Mängel. Schauen Sie sich diesen Code an:
Kopieren Sie den Codecode wie folgt:
$("#tb td").mylive('click',function(event){
alarm(event.target.innerHTML);
});
Es durchläuft zunächst das gesamte Dokument basierend auf dem JQuery-Selektor, findet alle #tb td-Elemente und speichert sie als Objekte. In der Live-Implementierungsmethode werden diese Objekte jedoch nicht verwendet, sondern nur „#td td“ als Zeichenfolge zur Übereinstimmung mit der Ereignisquelle. Dadurch erhöht sich der unnötige Verbrauch enorm.
Gibt es also eine Möglichkeit, diese Situation zu verbessern? Die Delegate-Proxy-Methode wird in jQuery bereitgestellt, die das Binden von Ereignissen an bestimmte Elemente und nicht nur an Dokumente unterstützt. Um das Prinzip zu verstehen, implementieren wir eine einfache Version von Delegate:
Kopieren Sie den Codecode wie folgt:
$(body).append('<div id="dv"></div>');
$.fn.mydelegate=function(selector,eventType,fn){
$(this).bind(eventType,function(event){
var match=$(event.target).closest(selector);
if(match.length !== 0){
fn.apply($(event.target),[event]);
}
});
}
$("#dv").mydelegate('td','click',function(event){
alarm(event.target.innerHTML);
});
var tb='<table id="tb"> /
<tr> /
<td>die erste Spalte</td>/
<td>die zweite Spalte</td>/
<td>die dritte Spalte</td>/
</tr>/
</table>';
$("dv").append(tb);
Die Methode mydeletage muss nicht alle td-Objekte abrufen, sondern nur die div-Objekte, an die das Ereignis gebunden ist. Dies ist hinsichtlich der Ausführungseffizienz besser als die Live-Methode.
Dies ist nur eine Einführung, damit jeder das Prinzip des Ereignis-Proxys verstehen kann. Die Implementierung von Live und Delegate in JQuery ist viel komplizierter.