Skip to content Skip to sidebar Skip to footer

Javascript: Class Properties Becoming Undefined During Drag Events

I'm pretty new with classes in Javascript and I've been stuck for a few days trying to understand why my properties are becoming undefined in all of my methods... I was trying to

Solution 1:

This is a common issue in webapp development, especially when you're trying to use instance methods as event handlers.

Normally, when you call something like

instance.method(foo);

The function method is called, with this pointing to instance and foo as the sole parameter. This is how most people expect this code to behave.

However, instance.method (without the invocation) is just a reference to a function. If you did:

const bar = instance.method;
bar(foo);

You would see different behavior. In this case, bar is called with this pointing to nothing and foo as the sole parameter. This is because the function is no longer bound to instance in the way it was when you called instance.method(foo);

This is precisely what is happening when you call

this.container.addEventListener("mousedown", this.dragStart, false);

You pass in a reference to the function that this.dragStart points to, but the connection to your class is lost.

There are a number of ways around this. They all do the same thing, effectively, which is to bind the event handlers to an instance of your class:

Arrow function expressions You could use arrow function expressions to bind the value of this to your class:

constructor() {
  this.container.addEventListener("mousedown", (e) =>this.dragStart(e), false);
  this.container.addEventListener("mouseup", (e) =>this.dragEnd(e), false);
  this.container.addEventListener("mousemove", (e) =>this.drag(e), false);
}

bind method You could also use the bind method to explicitly bind this to the function reference

constructor() {
  this.container.addEventListener("mousedown", this.dragStart.bind(this), false);
  this.container.addEventListener("mouseup", this.dragEnd.bind(this), false);
  this.container.addEventListener("mousemove", this.drag.bind(this), false);
}

ES6 method definition You can also change how you define your class methods so that the functions are bound to an instance of the class:

classDragEvents {

    /* ... */

    drag = () => { /* ... */ }

    dragStart = () => { /* ... */ }

    dragEnd = () => { /* ... */ }

}//End Class

Post a Comment for "Javascript: Class Properties Becoming Undefined During Drag Events"