通过innerHTML渲染后无法访问ES6类方法的问题及解决
问题:点击按钮报错“TypeError: this.setChange is not a function”
代码示例
HTML代码
<html lang="en"> <body> <div id="placeholder"></div> <script type="module"> import { WriteReview } from "./src/script.js" var inputElement = new WriteReview(document.getElementById("placeholder")); inputElement.render(); </script> </body> </html>
script.js代码
export class WriteReview{ constructor(element){ this.rating ="5" this.element=element; } setChange(){ this.rating = "3"; } render(){ console.log("inside render"); this.element.innerHTML = `<input type="button" onclick="this.setChange()" value ="Click here" />` } }
错误原因
通过innerHTML给按钮添加onclick="this.setChange()"时,这里的this指向按钮DOM元素本身,而非WriteReview类的实例。按钮元素并没有setChange方法,因此会抛出找不到函数的错误。
解决方案
方案1:保存实例引用绑定this
在render方法里提前保存类实例的引用,让内联事件调用实例的方法:
render(){ console.log("inside render"); const self = this; this.element.innerHTML = `<input type="button" onclick="self.setChange()" value ="Click here" />` }
方案2:使用事件监听绑定(推荐)
避免内联事件,通过DOM方法添加事件监听,确保this指向类实例:
render(){ console.log("inside render"); const button = document.createElement('input'); button.type = 'button'; button.value = 'Click here'; // 用bind绑定实例this,或直接用箭头函数 button.addEventListener('click', this.setChange.bind(this)); // 箭头写法:button.addEventListener('click', () => this.setChange()); this.element.innerHTML = ''; this.element.appendChild(button); }
方案3:构造函数内绑定方法
提前把setChange的this绑定到类实例,内联事件即可正常调用:
export class WriteReview{ constructor(element){ this.rating ="5" this.element=element; // 绑定方法的this到实例 this.setChange = this.setChange.bind(this); } setChange(){ this.rating = "3"; } render(){ console.log("inside render"); this.element.innerHTML = `<input type="button" onclick="this.setChange()" value ="Click here" />` } }
内容的提问来源于stack exchange,提问作者Nest
相关产品推荐
相关产品推荐

