본문 바로가기

Study/React

useRef

What is ref?

ref는 reference(참조)를 뜻한다. useRef는 리액트가 제공하는 tool 중 하나로 많은 일을 처리할 수 있는 도구이지만, 이것의 가장 기본적인 역할은 어떤 DOM 요소를 참조하고, 이를 이용해서 어떤 일을 수행하는 것이다. 

How to use ref? 

ref는 모든 내장 html 요소에서 사용될 수 있지만, input 요소를 참조하는 것이 가장 흔한 경우 중 하나이다.

예를 들어 사용자가 어떤 값을 입력하고 그 값을 리스트 형식으로 렌더링 한다고 해 보자. 이 때 input의 값이 변할 때 마다 실행되는 onChange에서 state를 업데이트한다면 어떨까? 최종적으로 필요한 것은 사용자가 제출 버튼을 클릭했을 때의 input 값이므로, 사용자가 키를 누를 때마다 state를 업데이트 하는 것은 과하다(unnecessary work). 이럴 때 state 대신 사용할 수 있는 것이 ref이다. 

 

+) 사용자가 리스트를 추가할 때 마다 re-rendering이 일어나야 하는데, 상위 컴포넌트에서 리스트를 state로 관리하고 있다면 input 컴포넌트에서도 state를 사용할 필요는 없다. 

 

import {useRef} from 'react';

const AddUser = (props) => {
 const userName = useRef(); // 초기값은 설정되어있지 않지만, 컴포넌트가 실행되면 값이 설정된다.
 
 const addUserHandler = (e) => {
   e.preventDefault();
   props.setUserList(userName.current.value);
   userName.current.value = '';
 }

  return (
    <form onSubmit={addUserHandler}>
      <label htmlFor="username">Username</label>
      <input
        id="username"
        type="text"
        ref={userName}
      />
      <button type="submit">Add User</button>
    </form>
  );
};

 

  1. 다른 react hooks 처럼 함수형 컴포넌트 내부에서 사용할 수 있다(컴포넌트 밖 X, nested braces X).
  2. 컴포넌트 함수가 실행되면, useRef의 실행 결과(userName)를 연결되어있는 실제 html element로 설정한다. 
  3. 참조하고 싶은 element에 ref라는 속성을 사용하고, 그 값으로 useRef 함수의 실행 결과를 전달한다. 
  4. useRef 함수는 object를 반환한다.
    • 이 객체에는 current라는 프로퍼티가 있고, 참조하고 있는 DOM 요소 자체를 값으로 가지고 있다. => DOM 요소를 직접 조작하기 위해 사용하는 것이 아니라, 값을 읽기 위해 사용한다. 
    • ex) | userName.current.value와 같이 유용한 값에 접근할 수 있다. 
  5. state로 관리할 때 value를 양방향 바인딩하는 것이 가능했지만, ref를 이용하면 불가능 하다. 

un-controlled component

useRef가 참조하고 있는 DOM 요소를 uncotrolled component라고 하는데, 말 그대로 리액트가 해당 요소를 제어하지 않기 때문이다. 리액트가 하는 역할은, 단지 그 요소를 참조할 수 있게 해주는 것 뿐이다. 

 

+) state를 이용해서 관리하는 component는 controlled component라고 부른다. 

 

+) React.forwardRef & useImperativeHandle

명령형 패턴으로 컴포넌트를 사용할 수 있다. 일반적인 리액트의 패턴과는 거리가 멀기 때문에 자주 사용하는 것은 좋지 않지만, 유용하게 사용할 수 있는 경우가 있다. => custom component를 ref로 참조할 수 있게 만들어 준다. 

 

// UI/Input
const Input = React.forwardRef((props,ref) => { // 두번째 인자로 ref를 전달받는다
  return (
    <div>
      <label htmlFor={props.id}>{props.label}</label>
      <input ref={ref} type={props.type} id={props.id} {...props.input}/>
    </div>
  );
})

 

import Input from '...'; 

const Form = (props) => {
  const inputRef = useRef();
  const submitHandler = (e) => {
    e.preventDefault();
    console.log(inputRef.current.value);
  }
  
  return (
    <form onSubmit={submitHandler}>
      <Input ref={inputRef} type="text"... />
    </form>
  );
}

 

  • inputRef.current.focus() | 참조하고 있는 input element에 focus를 주는 브라우저 내장 함수

'Study > React' 카테고리의 다른 글

useReducer  (0) 2022.06.19
useEffect  (0) 2022.06.19
Fragment & Portal  (0) 2022.06.18
Component Styling  (0) 2022.06.18
Conditional contents  (0) 2022.06.17