使用ES6类:如何从事件处理程序中调用方法?

时间:2017-03-14 21:41:56

标签: javascript class addeventlistener

以下代码

<button type="button" id="btnLogMsg">Press me</button>

<script>
class Logger {

    constructor() {     
        this.log("msg 1");          // logs 'msg 1': OK

        this.btnLogMsg = document.getElementById("btnLogMsg");
        this.btnLogMsg.addEventListener("click", function (evt) {
            console.log("msg 2");       // logs 'msg 2': OK
            log("msg 3");               // ERROR
            this.log("msg 3");          // ERROR
        });
    }  // ctor

    log(msg) {
        console.log(msg);
    }           
} // class Logger

var logger = new Logger();

加载html文件时,输出为

msg 1

按下按钮时,输出

msg 2

但不是

msg 2

msg 3

也不     log(“msg 3”);
也不     this.log(“msg 3”);
工作

检查this.log(“3”);   我知道'this'指的是点击按钮,因此btnLogMsg。   因此,无法调用this.log()。

但是怎么样?

谢谢 克里斯

1 个答案:

答案 0 :(得分:2)

你有很多选择。您的问题是,您的函数范围与函数范围之外的范围不同,这就是函数中this与函数外的this不同的原因。

正如你提到的es6,最简单的方法是使用arrow-function,如下所示:

this.btnLogMsg.addEventListener("click", (evt) => {
    console.log("msg 2");       // logs 'msg 2': OK
    this.log("msg 3");          // should now work
});

另一种实现这项工作的方法是保存指向外部this的指针,然后使用它:

var self = this;
this.btnLogMsg.addEventListener("click", function(evt) {
    console.log("msg 2");       // logs 'msg 2': OK
    self.log("msg 3");          // should now work
});

应该工作的第三种方法是将外部范围绑定到内部函数(这与使用箭头函数具有相同的效果):

this.btnLogMsg.addEventListener("click", function(evt) {
    console.log("msg 2");       // logs 'msg 2': OK
    this.log("msg 3");          // should now work
}.bind(this));

你应该阅读一些关于范围和this in different contexts

的内容