javaScript "this" argument in closure [duplicate] - javascript

This question already has answers here:
How does the "this" keyword work, and when should it be used?
(22 answers)
How to access the correct `this` inside a callback
(13 answers)
Closed 5 years ago.
I'm now facing a js closure problem. In the code bellow, I'm trying to bind an event handler "getNum" to the button, the problem is that this handler is an attribute in an object, so I read it in a book it says I should put my handler in a closure function like bellow, the problem is that I don't really get it why "this" argument point to the correct object when I put the handler in an anonymous function; And why pass an "event" argument to that function, what does "event" argument referring to, is it the event object when I click the button?
this.num = 9;
var myObj = {
num : 81;
getNum : function(){return this.num;}
}
var btn = document.getElementById("my-btn");
// btn.addEventListener("click",myObj.getNum); this doesn't work cause "this" point to the btn object,which doesn't have num attribute.
btn.addEventListener("click",function(event){
myObj.getNum(event);
});//worked, but I don't know why.

Related

Javascript Behavior when Function.prototype.bind is called serially [duplicate]

This question already has answers here:
Can you rebind a rebound function using `bind`
(3 answers)
How to override 'this' parameter of a bound function in javascript
(3 answers)
Javascript function bind override (how to bind it to another object)
(2 answers)
Closed 4 months ago.
I have a question about Function.prototype.bind.
function f() {
return this;
}
const g=f.bind({foo:'foo'});
const h=g.bind({bar:'bar'});
console.log(h()); // expected {bar:'bar'} but get {foo:'foo'}
I was expecting the above snippet to produce either {foo,bar} or {bar} but instead I get {foo}.
Can you explain what is going on?
Using .bind() to create a function that "fixes" the value of this in the called function results in a function where this cannot be overridden.
What you get back from .bind() is a new function that will pass along arguments to the original target function, with a guarantee that in that called function the value of this will be what you ask for. Re-binding that function therefore does no good: you do get back a new function, but it calls a function (the first bound function) that explicitly ignores its own this value.

behavior of "this" in forEach and addEventListener method [duplicate]

This question already has answers here:
How does the "this" keyword work, and when should it be used?
(22 answers)
The value of "this" within the handler using addEventListener
(10 answers)
Closed 3 years ago.
Edit: This is not a question about general behavior of "this" keyword in different context. My question is whether there is a common underlying logic behind the 2 behaviors here - is it because "this" only binds to an object when the method of that object is called, but forEach() is a method of an array?
Why is it that when I use:
var tag = ["a","b","c"];
tag.forEach(function () {
console.log(this)
});
this refers to the global object since the function is bind to the global object, but when I use:
element.getElementById("id").addEventListener("click", function () {
console.log(this.value);
});
this refers to the id element even though it's within a function? Is it because forEach is a method of an array rather than a method of an object?
In DOM event handlers this is set to the element the event fired from:
https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Operators/this#As_a_DOM_event_handler

Event handler function as a method [duplicate]

This question already has answers here:
How does the "this" keyword work, and when should it be used?
(22 answers)
How does the "this" keyword in Javascript act within an object literal? [duplicate]
(4 answers)
Closed 6 years ago.
I am very new to OOP and attempting my first project with it. Here is my question:
var calculator = {
operationBar: document.getElementById('operation-bar'),
print: function(){
this.operationBar.innerHTML += 1;
}
}
var one = document.getElementById('number1');
one.addEventListener('click',calculator.print)
When I click on my HTML element with the id (number1) I get the following error:
Cannot read property 'innerHTML' of undefined.
It is not relating the this keyword to my calculator object.
However if I do this:
var calculator = {
operationBar: document.getElementById('operation-bar'),
print: function(num){
this.operationBar.innerHTML += 1;
}
}
calculator.print()
It works and the this keyword seems to be working correctly.
The reason I know the problem is with the this keyword is because if I perform the function in the first snippet and replace this with calculator then it will work, as my event handler function as well.
Why is it behaving this way?

Why(How) does value of 'this' changes when a callback is called from inside the function? [duplicate]

This question already has answers here:
How to access the correct `this` inside a callback
(13 answers)
How does the "this" keyword work, and when should it be used?
(22 answers)
Closed 6 years ago.
I understand that there are quite a few question similar to this one but I couldn't find any which answers why or may how the context(value) of this changes when a callback function is called from inside the object function
like this
var obj = {
objproperty: "this is a property of obj",
func1: function(x,cb){
console.log(this) // refers to obj
var output_value = x + 20;
cb(output_value);
}
};
obj.func1(123,function(output_value){
console.log(output_value);
console.log(this); // does this refers to window or undefined??
});
as far as I understand the value shouldn't 'this' in third console.log be referring obj? as it called on the obj Object ?
as it called on the obj Object ?
No, it isn't.
cb(output_value);
There is nothing to the left of cb so it is called in the default context.
Your callback is called like this:
cb(output_value);
There's no object context in that function call, so the value of this will be either window (or the global context) in non-strict mode, or undefined in strict mode.
If you want to make sure that the callback has a this value that matches that in the context in which it's called, you can use .call():
cb.call(this, output_value);

jQuery overwriting 'this' in prototype [duplicate]

This question already has answers here:
How to access the correct `this` inside a callback
(13 answers)
jQuery - trigger not produce the expected result
(1 answer)
Closed 7 years ago.
I have declared a JavaScript object:
function A(name){
this.name=name
}
A.prototype.test=function(){
console.log(this.name);
};
as a simple example I have set up a button that if it's clicked should output a variable to the local console log:
<button id='test'>test</button>
the script:
var t=new A('hello');
$('#test').click(t.test);
when I click the button I want this.name to show (in this case 'hello'), but instead this refers to the clicked button, and not to the object I created.
this is a debugging script of course. In real life I'm binding a function to the window.resize event which will re-build a window on resizing.
There is a JSFiddle that shows the problem.
I have one solution for this, that is declaring the resize (or click function) in the constructor of the object and using an alternative name for this, like so (Here's the JSFiddle):
function A(name){
this.name=name
var self=this;
$("#test").click(function(){
console.log(self.name);
});
}
but I'd rather use a prototype and bind the function in the object's constructor. How can I do this using prototypes?
You can use bind, which will set the value of this ahead of time:
var t=new A('hello');
$('#test').click(t.test.bind(t));

Categories

Resources