0

I am trying to understand javascript bind method. I have read this other SO post about bind method and learned a great deal. One of the posts linked to javascripture where I played around with bind.

To my understanding, and according to mozilla's site, bind "creates a new function that 'binds' this to the bound object."

var Button = function(content) {  
  this.content = content; //stores content into this.content property
};

Button.prototype.click = function() { //adds click method
  console.log(this.content + ' clicked');
}

var myButton = new Button('OK');
console.log(myButton.content);        //OK
myButton.click();                     //OK clicked

var looseClick = myButton.click; 
console.log(looseClick.content);      //undefined
looseClick();                         //undefined clicked

var notLooseClick = myButton.click.bind(myButton);
console.log(notLooseClick.content);   //undefined
notLooseClick();                      //OK clicked

My confusion is the last var, notLooseClick. I don't understand why notLooseClick.content returns undefined while notLooseClick(); returns 'OK clicked'. I had expected 'OK' to be bound to notLooseClick.content.

How can I bind notLooseClick so when I call notLooseClick.content, it is bound to Button's this.content, so when I type notLooseClick.content it returns 'OK'? Why does bind() behave this way?

Community
  • 1
  • 1
Iggy
  • 5,129
  • 12
  • 53
  • 87
  • Unclear what you are asking. Your tests prove what `bind` does, that is, if you bind the function to the object it needs, you don't need to call it using `obj.func`, you can do `var func = obj.func.bind(obj);` and call `func()` and your `obj` will still be the `this` in that call. – Ruan Mendes Oct 25 '16 at 17:44
  • Because in `notLooseClick.content` you're trying to get attribute `content` from function and not from `button`. – Zakaria Acharki Oct 25 '16 at 17:44
  • 1
    `content` is never going to be a property of the `function` it's a property of the `this` in the function – Ruan Mendes Oct 25 '16 at 17:44
  • `content` stays a property of `myButton` (or `this`): `console.log(myButton.content);`. It does not become a property of `myButton.click`, `looseClick` or `notLooseClick`. – Bergi Oct 25 '16 at 17:58

1 Answers1

1

You are misunderstanding what Function.bind does. It makes sure that when a function is called, this will be whatever you pass in. It does not copy any properties of the object to the function that you've bound.

var Button = function(content) {  
  this.content = content; //stores content into this.content property
};

Button.prototype.click = function() { //adds click method
  console.log(this.content + ' clicked');
}

var okButton = new Button('OK');

// This calls click using okButton as its `this`
okButton.click();

var looseClick = okButton.click;
// This calls the same click function without specifying a `this`
// It will be window or null if on strict mode
looseClick();


// Here you are saying:
// No matter how this function is called, it will always use okButton as its `this`
var boundClick = okButton.click.bind(okButton);
boundClick();

You seem to be under the impression that the bind function would make your function inherit properties from the object that you bind it to. But that is not what it does, it binds the this within the call.

var notLooseClick = myButton.click.bind(myButton);
// It's undefined, you didn't copy properties of myButton to notLooseCLick
console.log(notLooseClick.content);   //undefined
// Here it works because you've set `this` in calls to notLooseClick to be myButton
notLooseClick(); 
Ruan Mendes
  • 90,375
  • 31
  • 153
  • 217