ref (reference) 에 대해 알아보자
ref 는 React에서 사용할 때, useRef 로 변수에 담아 사용이 가능하다.
ref 기본기능을 간단하게 설명하자면 다른 DOM에 접근해서 작업이 가능하도록 해준다. ( 이외에도 활용되는 기능이 매우 많지만 input에 관해서만 적어내리도록 하겠다) useState 는 우리 모두가 알고 있듯이 React에서 상태를 관리할 수 있도록 도와주는 기능이다.
// ref
const ref = useRef();
// useState
const [state, setState] = useState(null);
useState는 이런식으로 상태가 관리된다
입력 > 상태함수 실행 > 함수로 인한 state값 업데이트 > input 필드 값 변경 ( ref에서 삭제가능 )
물론 useState를 사용하면 DOM에 접근하지 않고 React 고유의 방식을 사용하여 상태를 안정적으로 업데이트하는것이 가능하다. 이런 보편적인 방법이 마냥 좋을때도 있지만 상태를 업데이트 하고 input요소에 업데이트 해주는식의 방식은 form 요소에서도 좋은 선택일까 하는 것에 대한 의문이 들 수도 있다.
form 요소의 경우, 서버로 전송하기 전까진 입력할때마다 input 상태가 업데이트된다. 렌더링이 지속적으로 일어나는 것은 기본이고, input 요소마다 업데이트 되는 코드를 짜줘야하기 때문에 생각보다 코드가 길어질 수 밖에 없다. 사실 form에서 중요한건 입력된 값을 보내주는것이라고 생각한다. 입력 중간과정을 필요없다 (물론 필요할때도 있겠지만?)
이런 경우 useRef 를 사용해 제어가 가능하다.
useRef 는 기본적으로 상태가 업데이트되지 않는다. 해당 참조 DOM의 값을 form을 서버로 보내기 직전에 입력값을 꺼내서 넣어준다면 useState를 사용했을 때 가지게되는 상태 업데이트에 대한 불필요한(?) 코드를 줄일 수 있다.
또한 렌더링이 감지되지 않기때문에 상태를 계속 업데이트하지 않아도 된다.
한가지 걸리는것은 form 전송 후 ref 참조값을 빈값으로 돌리기 위해 DOM에 직접적으로 접근할 수밖에 없다는 것이다.
하지만 이런부분은 코드를 짜는 개발자들의 선택이라 생각한다.
> useRef 활용한 코드 예시
const AddUser = (props) => {
const nameInputRef = useRef();
const ageInputRef = useRef();
const addUserHandler = (event) => {
event.preventDefault();
const enteredName = nameInputRef.current.value; //ref 상태값 가져오기
const enteredAge = ageInputRef.current.value; //ref 상태값 가져오기
if (enteredName.trim().length === 0 || enteredAge.trim().length === 0) {
setError({
title: "Invalid input",
message: "Please enter a valid name and age (non-empty values).",
});
return;
}
if (+enteredAge < 1) {
setError({
title: "Invalid age",
message: "Please enter a valid age (> 0).",
});
return;
}
props.onAddUser(enteredName, enteredAge);
nameInputRef.current.value = ""; // DOM에 접근해 상태 비워주기
enteredAge.current.value = ""; // DOM에 접근해 상태 비워주기
};
return (
<div>
{error && (
<ErrorModal
title={error.title}
message={error.message}
onConfirm={errorHandler}
/>
)}
<Card className={classes.input}>
<form onSubmit={addUserHandler}>
<label htmlFor="username">Username</label>
<input id="username" type="text" ref={nameInputRef} />
<label htmlFor="age">Age (Years)</label>
<input id="age" type="number" ref={ageInputRef} />
<Button type="submit">Add User</Button>
</form>
</Card>
</div>
);
};
'쬬의 React' 카테고리의 다른 글
[React] next-i18next error / i18next Text content did not match. Server: "introMessage" Client: (0) | 2023.06.28 |
---|---|
[React] useEffect 와 CleanUp 작동방식 이해하기 + input 입력완료 후 감지 코드예시 (0) | 2023.04.09 |
[React] 렌더링 상태 체크하기 (크롬 익스텐션 활용) (0) | 2023.04.09 |
[React] createPortal 사용해 효율적으로 모달 관리해주기 (0) | 2023.04.08 |
[React] 클릭(click)이벤트 기초정리 (0) | 2022.12.04 |