Home > Enterprise >  Understanding variable scope with regard to anonymous functions in EventListeners
Understanding variable scope with regard to anonymous functions in EventListeners

Time:12-18

In the example below, it's the green square I'm interested in.

I get that clicking on the red square returns the value of the variable set higher up.

I get that clicking on the blue square returns the parameter's default value.

I get that clicking on the orange square simply returns the event object.

But why does clicking on the green square not pass in the value from the variable set higher up?

Why is the value returned as undefined?

Is it possible to pass the value from the variable set higher up into the anonymous function in the EventListener method? Or is this simply impossible?

Example:

const square1 = 'red';
const square2 = 'orange';
const square3 = 'green';
const square4 = 'blue';

document.querySelector('.square.one').addEventListener('click', () => console.log(square1));

document.querySelector('.square.two').addEventListener('click', (square2) => console.log(square2));

document.querySelector('.square.three').addEventListener('click', (e, square3) => console.log(square3));

document.querySelector('.square.four').addEventListener('click', (e, square4 = 'blue') => console.log(square4));
.square {
  float: left;
  width: 100px;
  height: 100px;
  margin-right: 12px;
  line-height: 100px;
  text-align: center;
  color: rgb(255, 255, 255);
  font-family: sans-serif;
  cursor: pointer;
}

.square.one {
  background-color: rgb(255, 0, 0);
}

.square.two {
  font-size: 14px;
  line-height: 40px;
  background-color: rgb(255, 127, 0);
}

.square.three {
  background-color: rgb(0, 127, 0);
}

.square.four {
  background-color: rgb(0, 0, 255);
}
<div >Click Me</div>
<div >Probably don't click me</div>
<div >Click Me</div>
<div >Click Me</div>

CodePudding user response:

You get 'undefined' because the call back function is expecting a 'square3' parameter which you are not passing.

Basically the square3 that you have defined above is not the same defined within the function scope

The call back function is only passing the event object

You can view the function parameter like variables definitions, which values are defined when we call the function

CodePudding user response:

Why is the value returned as undefined?

Your callback is accepting 2 parameters, e and square3. The square3 parameter overrides the square3 global variable in the callback scope. Since addEventListener only passes one parameter (the event) to the callback, the second parameter is undefined.

To fix this, just remove it from the parameter list. So, use (e) => //... instead of (e, square3) => //...

const square1 = 'red';
const square2 = 'orange';
const square3 = 'green';
const square4 = 'blue';

document.querySelector('.square.one').addEventListener('click', () => console.log(square1));

document.querySelector('.square.two').addEventListener('click', (square2) => console.log(square2));

document.querySelector('.square.three').addEventListener('click', (e) => console.log(square3));

document.querySelector('.square.four').addEventListener('click', (e, square4 = 'blue') => console.log(square4));
.square {
  float: left;
  width: 100px;
  height: 100px;
  margin-right: 12px;
  line-height: 100px;
  text-align: center;
  color: rgb(255, 255, 255);
  font-family: sans-serif;
  cursor: pointer;
}

.square.one {
  background-color: rgb(255, 0, 0);
}

.square.two {
  font-size: 14px;
  line-height: 40px;
  background-color: rgb(255, 127, 0);
}

.square.three {
  background-color: rgb(0, 127, 0);
}

.square.four {
  background-color: rgb(0, 0, 255);
}
<div >Click Me</div>
<div >Probably don't click me</div>
<div >Click Me</div>
<div >Click Me</div>

CodePudding user response:

Is it possible to pass the value from the variable set higher up into the anonymous function in the EventListener method? Or is this simply impossible?

It's probably not needed very often, but for the sake of clarity, one might occasionally wish to explicitly include a parameter with a clearly stated value within an anonymous function within an EventListener.

In the course of asking the question and experimenting with various approaches, I've realised that this is possible, but you need to reference the already declared variable via a parameter default value.

e.g.

document.querySelector('.square.three').addEventListener('click', (e, mySquare3 = square3) => console.log(mySquare3));

Working Example:

const square1 = 'red';
const square2 = 'orange';
const square3 = 'green';
const square4 = 'blue';

document.querySelector('.square.one').addEventListener('click', () => console.log(square1));

document.querySelector('.square.two').addEventListener('click', (square2) => console.log(square2));

document.querySelector('.square.three').addEventListener('click', (e, mySquare3 = square3) => console.log(mySquare3));

document.querySelector('.square.four').addEventListener('click', (e, square4 = 'blue') => console.log(square4));
.square {
  float: left;
  width: 100px;
  height: 100px;
  margin-right: 12px;
  line-height: 100px;
  text-align: center;
  color: rgb(255, 255, 255);
  font-family: sans-serif;
  cursor: pointer;
}

.square.one {
  background-color: rgb(255, 0, 0);
}

.square.two {
  font-size: 14px;
  line-height: 40px;
  background-color: rgb(255, 127, 0);
  opacity: 0.5;
  pointer-events: none;
}

.square.three {
  background-color: rgb(0, 127, 0);
}

.square.four {
  background-color: rgb(0, 0, 255);
}
<div >Click Me</div>
<div >I've been disabled</div>
<div >Click Me</div>
<div >Click Me</div>

  • Related