React - Ref와 DOM

Noma·2021년 4월 14일
0

Ref

Ref는 render 메서드에서 생성된 DOM 노드나 React 엘리먼트에 접근하는 방법을 제공한다.

함수 컴포넌트에는 ref 어트리뷰트를 사용할 수 없으므로, 이번 포스팅에서는 클래스 컴포넌트만 다루겠다.

Ref 사용 시기

  • 포커스, 텍스트 선택영역, 혹은 미디어 재생을 관리할 때
  • 애니메이션을 직접적으로 실행시킬 때
  • 서드 파티 DOM 라이브러리를 React와 같이 사용할 때

...등이 있다. 이외에 선언적으로 해결될 수 있는 문제에서는 ref 사용을 지양하는 것이 좋다.

Ref 생성하기

Ref는 React.createRef()로 생성하고, ref어트리뷰트를 통해 React 엘리먼트에 부착할 수 있다. 이로써 컴포넌트의 인스턴스의 어느 곳에서도 Ref를 접근할 수 있게 된다.

class MyComponent extends React.Component {
  constructor(props) {
    super(props);
    this.inputRef = React.createRef();
  }
  render() {
    return <input 
             ref={this.inputRef} 
             type="text"
           />;
  }
}

보통 네이밍은 input에 붙일 거면 inputRef, form에 붙일 거면 formRef와 같이 정의하는 것이 좋지만, 원하는 이름으로도 가능하다.

Ref에 접근하기

render메서드 안에서 ref가 엘리먼트에 전달되었다면, 그 노드의 참조값은 ref의 current어트리뷰트에 담기게 된다.

const value=this.inputRef.current.value;

ref값은 노드의 유형에 따라 다르다.

  • ref가 HTML 엘리먼트에 쓰였다면,
    생성자에서 React.createRef()로 생성된 refcurrent값으로 DOM 엘리먼트를 받는다.

📍 예시

class CustomTextInput extends React.Component {
  constructor(props) {
    super(props);
    this.textInput = React.createRef();
  } // textInput DOM 엘리먼트를 저장하기 위한 ref를 생성

  focusTextInput=()=>{
    this.textInput.current.focus();
  } // DOM API를 사용하여 input 엘리먼트를 포커스

  render() {
    return (
      <div>
        <input
          type="text"
          ref={this.textInput} />
        <input
          type="button"
          onClick={this.focusTextInput}
        />
      </div>
    );
  }
}

컴포넌트가 마운트될 때 current에 DOM 엘리먼트를 대입하고, 언마운트될 때 current을 다시 null로 돌려 놓는다.

  • ref가 커스텀 클래스 컴포넌트에 쓰였다면,
    current값으로 마운트된 컴포넌트의 인스턴스를 받는다.

📍 예시

class AutoFocusTextInput extends React.Component {
  constructor(props) {
    super(props);
    this.textInput = React.createRef();
  }
  componentDidMount() {
    this.textInput.current.focusTextInput();
  }
  render() {
    return (
      <CustomTextInput ref={this.textInput} />
    );
  }
}

부모 컴포넌트에 DOM ref 공개하는 방법

자식 컴포넌트의 DOM노드에 접근하는 것은 컴포넌트의 캡슐화를 파괴하기 때문에 권장되지 않는다. 하지만 가끔

  • 자식 컴포넌트의 DOM 노드를 포커스하는 일이나,
  • 크기 또는 위치를 계산하는 일 등을 할 때

효과적인 방법이 될 수 있다. React 16.3 이후 버전의 React를 사용한다면 Forwarding Refs을 권장한다.

📚 reference

https://ko.reactjs.org/docs/refs-and-the-dom.html

profile
Frontend Web/App Engineer

0개의 댓글