2009-09-02 4 views
11

Ich versuche auf die Member-Variablen einer Prototyp-Klasse in JavaScript in einem Event-Handler zuzugreifen - etwas, das ich normalerweise verwenden würde das "this" -Schlüsselwort für (oder "Das" [Kopie davon] im Falle von Ereignishandlern). Unnötig zu sagen, dass ich in Schwierigkeiten gerate."Dieses" Schlüsselwort in Ereignismethoden bei der Verwendung von JavaScript-Prototyp-Objekt

Nehmen wir zum Beispiel das HTML-Snippet:

<a id="myLink" href="#">My Link</a> 

Und das JavaScript-Code:

function MyClass() 
{ 
    this.field = "value" 
    this.link = document.getElementById("myLink"); 
    this.link.onclick = this.EventMethod; 
} 

MyClass.prototype.NormalMethod = function() 
{ 
    alert(this.field); 
} 

MyClass.prototype.EventMethod = function(e) 
{ 
    alert(this.field); 
} 

ein MyClass-Objekt instanzieren und NormalMethod Aufruf funktioniert genau wie ich es (Alarm sagen "erwarten value "), aber das Klicken auf den Link führt zu einem undefinierten Wert, da das Schlüsselwort" this "jetzt auf das Ereignisziel verweist (das HTML-Element anchor()).

Ich bin neu in dem Prototyp-Stil JavaScript, aber in der Vergangenheit, mit Verschlüssen, ich habe einfach eine Kopie von „this“ im Konstruktor gemacht:

var that = this; 

Und dann kann ich Mitglieder zugreifen Variablen in Ereignismethoden über das Objekt "that". Das scheint nicht mit Prototyp-Code zu funktionieren. Gibt es einen anderen Weg, dies zu erreichen?

Danke.

+0

Sie in die Prototype-Bibliothek beziehen, sind oder eher gerade JavaScript prototypische Klassen? –

+3

Reagieren drei Jahre später :) Aber für die Nachwelt: Ich bezog sich auf gerade JavaScript prototypische Klassen. – Michael

+0

Mögliches Duplikat von [Wie erreiche ich den richtigen 'this/Kontext innerhalb eines Callbacks?] (Http://stackoverflow.com/q/20279484/1048572)? – Bergi

Antwort

9

Ihre "that=this" Idiom Schließung ist noch anwendbar:

function MyClass() 
{ 
    ... 

    var that = this; 
    this.link.onclick = function() { 
     return that.EventMethod.apply(that, arguments); 

     // that.EventMethod() works too here, however 
     // the above ensures that the function closure 
     // operates exactly as EventMethod itself does. 

    }; 
} 
5

Sie sollten versuchen,

this.link.onclick = this.EventMethod.bind(this); 
13

Sie benötigen:

this.link.onclick = this.EventMethod.bind(this); 

... 'bind' Teil von Prototype ist, und gibt eine Funktion zurück, die Ihre Methode aufruft, wenn 'this' richtig gesetzt ist.

+0

Wie erhält 'onclick' Zugriff auf die Ereignisschnittstelle? – Karl

+0

@Karl Mit "Zugriff auf die Ereignisschnittstelle" meinst du "erhalte das Ereignisobjekt als Argument"? Die 'bind' Methode ** gibt eine Funktion ** (mit einem festen' this') zurück, also ist 'onclick = this.EventMethod' grundsätzlich dasselbe wie' onclick = this.EventMethod.bind (this) '.In beiden Fällen speichern Sie eine Funktion in der OnClick-Eigenschaft. Sie sind hinsichtlich der Behandlung ihrer Argumente identisch. Wenn Ihre Frage allgemeiner ist, wie Argumente an Listener-Funktionen übergeben werden, ist das eine ganz andere Frage als die, die hier gestellt wird, und Sie sollten eine neue Frage stellen. – apsillers

0

Wie oben erwähnt, ist die Verwendung von bind, das ein Teil der Prototype-Bibliothek ist, ein sauberer Weg, um dieses Problem zu lösen. Diese Frage ist ein Duplikat einer anderen SO Frage, die hier bei der Umsetzung der Methode bind beantwortet wird, ohne die gesamte Prototyp Bibliothek einschließlich:

https://stackoverflow.com/a/2025839/1180286

+0

Diese Frage verwendet JQuery. Ich würde viel lieber eine reine JavaScript-Frage/Antwort als Standard sehen. –

Verwandte Themen