[적용 상황]
어떤 자식요소의 트리거를 위해 부모요소에서 특정 상태 또는 값을 업데이트 하니,
다른 자식요소(형제요소)까지 불필요하게 리렌더링 되는 현상 발생
= > 이를 해결하기 위해 "자식요소의 트리거를 자식요소 내부에서 선언하고 그 트리거만 외부로 전달하도록 함"
[사용방법]
1. 자식요소에서 컴포넌트를 forwardRef()로 감싼 후, props 옆에 ref를 넣는다.
(ref는 임의의 명칭이 아니며, 다른 이름으로 바꿀 수 없다. 즉, 반드시 'ref'라고 기재해야 complile이 가능하다)
2. useImperativeHandle을 이용하여 필요한 트리거 함수를 선언한다.
( useImperativeHandle: ref로 노출할 메서드나 값을 사용자 정의할 수 있게 해줌, 보통 ref를 붙이면 DOM 노드만 참조되지만, 이 훅을 사용하면 원하는 메서드를 직접 노출하는 것이 가능!)
// 참고: forwardRef의 타입 선언시 ref의 타입을 무조건 먼저 선언해야 함!
export const ChildrenComponent = forwardRef(
({ title }, ref) => {
const [currentTime, setCurrentTime] = useState(getDateHHMMss());
useImperativeHandle(ref, () => ({
updateTime: () => setCurrentTime(getDateHHMMss())
}));
return (
<article>
<h3>{title}-{currentTime}</h3>
</article>
);
}
);
3. 부모요소에서 해당 ref를 받을 ref를 생성한다.
4. 자식요소의 'ref' 속성의 값으로 전달한다.
5. 필요한 부분에서 선언해둔 함수를 호출한다.
export const ParentComponent = () => {
const titleRef = useRef(null);
useEffect(() => {
const timer = setInterval(() => {
titleRef.current?.updateTime(); // ref의 속성으로 호출!
}, 5000);
return () => clearInterval(timer);
}, []);
return (
<div>
<SectionTitleComponent
ref={titleRef} // ref의 속성값으로 전달(실은 받는 것)
title="매장 리스트"
/>
</div>
);
};
[참고]
- 이번에는 useImperativeHandle를 사용하여 함수(트리거)만 넘겼지만, DOM요소에 접근하도록 ref에 실어서 보낼 수도 있다.
- 외부에서 input에 포커스를 주거나 값을 가져오고 싶을 때 매우 유용하다고 한다.
// Children.tsx
// ref를 input 태그에 직접 연결
const InputComponent = forwardRef<HTMLInputElement>((props, ref) => {
return (
<input
type="text"
ref={ref}
placeholder="입력하세요"
className="border p-2 rounded"
/>
);
});
export default InputComponent;
// Parents.tsx
const ParentComponent = () => {
const inputRef = useRef<HTMLInputElement>(null);
const handleFocus = () => {
inputRef.current?.focus(); // 내부 input DOM에 접근 가능
};
const handleSetValue = () => {
if (inputRef.current) {
inputRef.current.value = "Hello from Parent!";
}
};
return (
<div>
<InputComponent ref={inputRef} />
<button onClick={handleFocus}>포커스 주기</button>
<button onClick={handleSetValue}>값 설정</button>
</div>
);
};
export default ParentComponent;
'React' 카테고리의 다른 글
배열의 요소마다 await 적용 시, for ~ of 사용(.map과 비교) (0) | 2025.05.14 |
---|---|
Promise 함수 (resolve, reject) (1) | 2025.04.22 |
React에서 동기 / 비동기, async / await (0) | 2025.04.22 |
함수 선언 방식에 따른 차이 (0) | 2025.03.06 |