11

[JavaScript] Scope (Context) of Event Handler Function

 2 years ago
source link: http://siongui.github.io/2012/10/01/javascript-scope-context-of-event-handler/
Go to the source link to view the article. You can view the picture content, updated content and better typesetting reading experience. If the link is broken, please click the button below to view the snapshot at that time.
neoserver,ios ssh client

[JavaScript] Scope (Context) of Event Handler Function

Updated: March 07, 2015

The scope (context) of event handler is headache for new JavaScript developers (at least for me when I try to write JavaScript web application in the beginning). Look at the following code snippet:

contact = function() {
  this.name = 'Bob';

  window.addEventListener("click", this.AddName, false);
};

contact.prototype.AddName = function() {
  alert(this.name);
};

The problems in references [3] and [5] are basically the same as the above. When JavaScript interpreter runs the line 8 of above code, error will be raised. The JavaScript interpreter will tell you that this.name does not exist. You may wonder that this.name is already assigned in line 2, why does the JavaScript interpreter raise error?

The problem is that this keyword in line 8 refers to JavaScript built-in object window, not refers to the contact function object. In line 2, you assign the value 'Bob' to the variable name in the scope (context) of contact function object. As a result, the JavaScript interpreter raises the error.

So how to make the this keyword in line 8 refer to contact function object?

For recent browsers which support Function.prototype.bind natively, you can replace line 4:

window.addEventListener("click", this.AddName, false);

with the following line:

window.addEventListener("click", this.AddName.bind(this), false);

If you want to support old browsers like IE8, you can implement custom Function.prototype.bind, or you can use closures to change the scope (context): line 4 can be replaced with the following code:

var self = this;
window.addEventListener("click", function() {self.AddName();}, false);

Anonymous function and closures are used to make the this keyword in AddName function refer to contact function object.

Other variant of the above problem is described in references [4]. In summary, there are two ways to solve the above problem:

  1. Function.prototype.bind: Only provided in recent browsers, for old browsers, implement custom Function.prototype.bind. See reference [1] for more details.
  2. Closures: See references [2] and [6] for more details.

The questions on Stack Overflow in references [3], [4], [5] are very helpful. Please read carefully.


References:


About Joyk


Aggregate valuable and interesting links.
Joyk means Joy of geeK