안녕하세요!
이번 포스팅은 리액트에서 이벤트핸들링하는 방법들을 알아보겠습니다.
이벤트핸들링하는 방법들의 중심에는 함수바인딩과 성능문제 이슈가 있었습니다.
이벤트 처리 메서드가 컴포넌트 인스턴스에 접근할 필요가 없다면 클래스 바깥에서 정의할 수 있습니다. 반대로, "this" 를 이용할 때처럼 컴포넌트 인스턴스에 접근하는 경우에는 클래스 내부에 작성해야 합니다.
클래스 바깥에서 구현하면 테스트코드를 작성하기 쉽다는 장점이 있습니다.
"this"에 접근해야 한다면 함수 바인딩을 사용해야 하는데,
컴포넌트 인스턴스에 접근하기 위해 바인딩하는 두 가지방법
이 두가지 방법을 먼저 살펴보겠습니다.
이렇게 세 종류의 버튼이 있고 상탯값 count를 증가시키거나 감소시키는 기능을 하는 이벤트를 만들어보겠습니다.
import React from 'react'
export default class MyComponent extends React.Component {
constructor(props) {
super(props)
this.state = {
count : 0
}
this.onClickInc = this.onClickInc.bind(this)
}
onClickInc() {
const {count} = this.state;
this.setState({count : count +1 })
}
onClickDec() {
const {count} = this.state;
this.setState({count : count -1 })
}
onClickHello(e) {
e.preventDefault();
alert('hello')
}
componentDidUpdate() {
console.log(this.state.count)
}
render () {
return (
<div>
<button onClick={this.onClickDec.bind(this)}>Decrease</button>
<button onClick={this.onClickInc}>Increase</button>
<button onClick={this.onClickHello}>Alert</button>
</div>
)
}
}
렌더링 하는 부분을 보면 세 개의 button이 있고 각각 다른 onClick 이벤트 메서드를 갖고 있습니다.
this객체와 무관한 onClickHello 메서드는 함수 바인딩이 필요없습니다.
나머지 두 개의 함수
onClickDec는 render 메서드 내부에서 바인딩하고있고,
onClickInc는 constructor에서 바인딩을 하고 있습니다.
둘 중 더 나은 방법은 constructor에서 바인딩하는 것 입니다.
render메서드 내에서 바인딩을 하게되면 렌더링할 때마다 바인딩하므로 새로운 함수가 생성됩니다.
constructor에서 첫 렌더링시에만 바인딩을 생성하는 방법이 더 낫습니다.
클래스필드는 거~의 정식문법으로 확정된 문법입니다. 바벨을 이용하면 정식문법이 아니지만 사용할 수 있습니다. 지금까지 본 모든 책이나 문서에서 안심하고 사용하라고 합니다.
이 클래스필드는 함수에 바인딩을 적용하면서 렌더링성능과 가독성까지 높힐 수 있습니다.
방금 살펴봤던 constructor내 에서 바인딩하는 방법이나 render함수 내에서 바인딩 하는 것 보다 낫습니다.
render함수에서 바인딩할 때의 성능상의 문제도 없고, constructor에서 바인딩할 때의 번거로움도 없습니다.
코드를 수정해보겠습니다.
import React from 'react'
export default class MyComponent extends React.Component {
state = {
count : 0
}
onClickInc = () => {
const {count} = this.state;
this.setState({count : count +1 })
}
onClickDec = () => {
const {count} = this.state;
this.setState({count : count -1 })
}
onClickHello = (e) => {
e.preventDefault();
alert('hello')
}
componentDidUpdate() {
console.log(this.state.count)
}
render () {
return (
<div>
<button onClick={this.onClickDec}>Decrease</button>
<button onClick={this.onClickInc}>Increase</button>
<button onClick={this.onClickHello}>Alert</button>
</div>
)
}
}
constructor가 없어지고, 클래스 내의 함수들은 화살표 함수로 생성합니다. 화살표함수가 자동으로 바인딩을 해줍니다.
클래스형으로 컴포넌트를 작성한다면, 간편하고 성능상으로도 이점이 있는 클래스필드가 좋은 선택지가 될 것 같습니다.
읽어주셔서 감사합니다!