IntersectionObserver 활용하기
IntersectionObserver
랜딩페이지 작업 중 특정 색션에 접근 시 애니메이션이 발생하도록 구현해야 했습니다.
`Scroll` 이벤트를 활용해 구현을 할 수 있지만,
사용해본 경험이 있는 `IntersectionObserver` 을 활용해 구현했습니다.
과정
먼저 ref 객체를 만들어 관찰해야할 요소에 바인딩 해줍니다.
<CompanySection ref={companySectionRef}>
<InfoBox>
<h2>안심업체</h2>
<p className="desc">
소중한 우리 집,
<br />
안심하고 맡겨보세요.
</p>
</InfoBox>
</CompanySection>
IntersectionObserver 객체를 생성하고, observer 콜백 함수와 옵션 객체를 인자로 넘겨줍니다.
콜백 함수의 매개변수로 entries 를 받을 수 있습니다.
entries 는 IntersectionObserverEntry 객체의 배열인데, 해당 객체는 관찰하기로 한 타겟과 루트가 교차되는 정보를 담고 있습니다.
> IntersectionObserverEntry
https://developer.mozilla.org/en-US/docs/Web/API/IntersectionObserverEntry
IntersectionObserverEntry - Web APIs | MDN
The IntersectionObserverEntry interface of the Intersection Observer API describes the intersection between the target element and its root container at a specific moment of transition.
developer.mozilla.org
저는 교차되는 순간을 감지하여 애니메이션이 발현되기를 원했습니다.
하여 `entries` 배열을 돌아 entry 의 `isIntersecting` 값을 체크했고,
해당 값이 `true` 일 때 애니메이션이 발현되도록 코드를 작성했습니다.
해당 컴포넌트가 마운트 되는 시점부터 해당 ref 를 감시해야 하므로 `useEffect` 내부에 코드를 작성했습니다. `IntersectionObserver` 객체를 생성한 후 `observe` 메서드를 통해 ref 감시를 시작합니다.
컴포넌트의 생명주기가 끝나 unmount 된다면 해당 옵저버도 감시를 그만둬야합니다.
하여 `useEffect` 의 cleanup 함수를 통해 `disconnect` 시켜줍니다.
`disconnect` 해주지 않으면 메모리를 계속 잡아먹게 됩니다!
useEffect(() => {
const observer = new IntersectionObserver(
(entries) => {
entries.forEach(({ isIntersecting }) => {
setIsCompanyAnimationOn(isIntersecting);
});
},
{ threshold: 0.5 },
);
if (companySectionRef?.current) {
observer.observe(companySectionRef.current);
}
return () => observer.disconnect();
}, []);
자세한 내용은 MDN 을 참고하시면 좋습니다.
> https://developer.mozilla.org/en-US/docs/Web/API/IntersectionObserver/IntersectionObserver
예전에 Intersection Observer 을 활용해 무한 스크롤을 구현해본 코드도 첨부해봅니다.