Why do I have to .bind(this) for methods defined in React component class, but not in regular ES6 class

Solution 1:

The value of this primarily depends on how the function is called. Given d.speak();, this will refer to d because the function is called as an "object method".

But in <div>{this.renderElements}</div> you are not calling the function. You are passing the function to React which will call it somehow. When it is called, React doesn't know which object the function "belonged" to so it cannot set the right value for this. Binding solves that

I actually think what you really want is

<div>{this.renderElements()}</div>
//         call function ^^

i.e call the function as an object method. Then you don't have to bind it.


Have a look at MDN to learn more about this.

Solution 2:

Event handlers in the component will not be bound automatically to the component instance like other methods ( life cycle methods...).

class MyComponent extends React.Component {
   render(){
      return (
         <div onClick={this.renderElements}>
             {this.renderElements()} <-- `this` is still in side the MyComponent context
         </div>
      )
   }
}
//under the hood

var instance = new MyComponent();
var element = instance.render();
//click on div
element.onClick() <-- `this` inside renderElements refers to the window object now

Check this example to understand this more :

class Animal { 
    constructor(name) {
        this.name = name;
    }

    speak() {
        console.log(this.name + ' makes a noise.');
    }  
}

class Dog extends Animal {
    run(){
       console.log(this.name + ' runs');
    }
    speak() {
        console.log(this.name + ' barks.');
        this.run(); <-- `this` is still in the Dog context
        return {onRun : this.run};
    }
}

var d = new Dog('Mitzie');
var myDog = d.speak();
myDog.onRun() <-- `this` is now in the global context which is the `window` object

You can check this article for more information.