对于事件处理,react提供了一系列的属性。解决方案几乎和标准的DOM一样,但也有不同的地方,比如:驼峰式命名。
通常处理事件的写法
export default class App extend React.Component {
render() {
return (
<button onClick={ this.handleButtonClick }>
click me
</button>
);
}
handleButtonClick() {
console.log('Button is clicked');
}
}
存在问题
但这样写 会有一个问题,就是上下文不一致,handleButtonClick函数里通过this来获取 App组件的引用,会报错;
handleButtonClick() {
console.log(`Button is clicked inside ${ this.state.num }`);
// 导致
// Uncaught TypeError: Cannot read property 'state' of null
}
解决方案
1、利用bind 来绑定this
tips:bind和call,apply区别;三种都可以改变函数执行的上下文,call和apply会立即执行该函数,bind不会立即执行
<button onClick={ this.handleButtonClick.bind(this) }>
click me
2、利用constructor
但是1中这样做,会导致当 button 一遍遍被渲染的时候,bind函数会一遍遍被调用;优化方式,利用constructor;
export default class App extends React.Component{
constructor(props) {
super(props);
this.state = { num: 1 };
this.buttonClick = this.handleButtonClick.bind(this);
}
handleButtonClick() {
const { num } = this.state
console.log(`Button is clicked inside ${ num }`);
this.setState({num: num+1 })
}
render() {
return (
<button onClick={ this.buttonClick }>
click me {this.state.num}
</button>
);
}
3、箭头函数
export default class App extends React.Component{
constructor(props) {
super(props);
this.state = { num: 1 };
}
buttonClick = () => {
const { num } = this.state
console.log(`Button is clicked inside ${ num }`);
this.setState({num: num+1 })
}
render() {
return (
<button onClick={ this.buttonClick }>
click me {this.state.num}
</button>
);
}
}
tips:箭头函数不能用new。不能使用arguments(火狐36可以)
var fn1 = () => {console.log(arguments)}
fn1(11) // Uncaught ReferenceError: arguments is not defined
var fn2 = function(){console.log(arguments)}
fn2(22) // Arguments [22, callee: ƒ, Symbol(Symbol.iterator): ƒ]