Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to add an Eventlistener to an instance method

I have a class in which I want to run a function whenever an event occurs. Whenever the function calls, the function of the instance of the class does not run.

class Player {
    constructor() {
        window.addEventListener('keypress', this.key_press);
        this.keys_pressed = 0;
    }

    key_press(key_press) {
        if(key_press.key == "w") {
            console.log(key_press);
            this.keys_pressed += 1;
        }
        console.log(this.keys_pressed);
    }
}

Whenever this.key_press is called, it logs out NaN. It seems as though the method of the class isn't being run, but rather a copy(?). I've also tried running another instance function inside key_press() but it says that the function is undefined.

Any help is appreciated.

like image 635
Sealestr Avatar asked Oct 31 '25 21:10

Sealestr


1 Answers

When you are adding an event listener to the window or any element of the DOM, the this value points to that element instead of the Player instance.

So you are getting NaN as the window does not have the keys_pressed property and keys_pressed += 1 is treated as keys_pressed = undefined + 1 which is NaN.

To fix this we need to bind to the Player instance explicitly:

const input = document.querySelector("#input");
class Player {
    constructor() {
        input.addEventListener('keypress', this.key_press.bind(this));
        this.keys_pressed = 0;
    }

    key_press(key_press) {
        if(key_press.key == "w") {
            this.keys_pressed += 1;
        }
        console.log(this.keys_pressed);
    }
}
let p = new Player();
Type here: <input type="text" id="input">

We can also use an arrow ( => ) function which captures the this from the current context and would point to the current instance of the Player object:

const input = document.querySelector("#input");
class Player {
    constructor() {
        input.addEventListener('keypress', (event) => this.key_press(event));
        this.keys_pressed = 0;
    }

    key_press(key_press) {
        if(key_press.key == "w") {
            this.keys_pressed += 1;
        }
        console.log(this.keys_pressed);
    }
}
let p = new Player();
Type here: <input type="text" id="input">
like image 84
Fullstack Guy Avatar answered Nov 03 '25 11:11

Fullstack Guy