채팅 서비스를 만드는 중, 버튼을 클릭하면 채팅의 맨 아래로 내려가는 기능이 필요해졌다.
채팅이 추가되면 자동으로 스크롤이 아래로 이동하는 기능은 만들어보았어도..
맨 아래로 보내는 기능은 처음이라.. 두근두근..!
가장 먼저 해야할 것.
스크롤이 맨 아래에 있는지(제일 하단에 있는지) 확인해야한다.
스크롤이 맨 아래에 있는지 감지하려면, scrollTop
이 scrollHeight
와 clientHeight
를 뺀 값이 크거나 작은지 확인하면 된다.
e.target.scrollTop >= e.target.scrollHeight - e.target.clientHeight
이러면 스크롤이 맨 아래에 있는지 감지할 수 있다.
function ChatList(props) {
const [ScrollY, setScrollY] = useState(0); // 스크롤값을 저장하기 위한 상태
// ... 코드생략
const handleFollow = (e) => {
setScrollY(
// 스크롤이 맨 아래에 있는지 감지
e.target.scrollTop >= e.target.scrollHeight - e.target.clientHeight
);
};
return (
// ... 코드생략
<Grid
onScroll={handleFollow}
sx={{
// ... 코드생략
handleFollow
함수를 통해 스크롤 위치를 감지하고,
스크롤이 맨 아래에 있는지에 대한 여부를 ScrollY
라는 State 에 저장해주면된다.
참고로 스크롤이 되야하는, 그러니까 채팅 리스트가 띄워지는 채팅 박스(?)에 onScroll
이벤트를 걸어야지 정확하고,
아닐 경우 스크롤이 잘못 감지될 수 있으니 주의해야한다.
초기화 단계에서 window
객체에 scroll 이벤트 리스너를 추가하고,
컴포넌트가 언마운트될 때 이벤트 리스너를 제거하도록 추가했다.
useEffect(() => {
const watch = () => {
window.addEventListener("scroll", handleFollow);
};
watch(); // addEventListener 함수 실행
return () => {
window.removeEventListener("scroll", handleFollow); // addEventListener 함수 삭제
};
});
효율적인 scroll
이벤트 관리를 위해 꼭 useEffect
를 사용해주자!
자 이제 클릭했을 때 채팅 맨 아래로 이동시키는 버튼만 추가하면되는데,
나는 이 버튼이 계속 보이는 것이 아니라
위의 3가지 조건에 부합할 때만 버튼이 보이도록 설정해 주었다.
{/* 맨 아래로 이동시키는 버튼 */}
{chatList?.length > 0 && ScrollY !== 0 && !ScrollY && (
<Button
variant="plan"
sx={{ position: "absolute", bottom: "10%", right: "1%" }}
onClick={() =>
messageEndRef.current.scrollIntoView({ behavior: "smooth" })
}
>
<img src={downbtn} alt={"scroll down btn"} />
</Button>
)}
and
연산자를 통해 조건을 추가해주었고,
클릭 시 제일 하단으로 슝 ~ 잘 내려간다 ~ 💨
기능을 직접 만들기 전, react-scroll-to-bottom
이라는 npm 라이브러리를 사용할까 했었는데,
이게.. 내리는 버튼이 그냥 회색 동그라미 버튼이다.. 진짜 걍 이럼 -> ⚫ ㅋㅋ
화살표라도 있음 좋겠는데 싶어서 커스텀을 하려는데..
여간 힘든게 아니더라.......🤔 ㅋ 이걸로 시간 보낼바에야 직접 만들겠다 싶어서 만들었다.
npm 으로 설치만하고 높이만 지정해주면 위에서 만든 기능을 바로 사용할 수 있는데,
버튼이 못생겨서 그냥 피그마에서 직접 아이콘 만들어서 넣고 스크롤 기능 만들어버렸다.
그래도 만들어서 뿌듯 :)
혹시나 버튼이 뭐 어떻게 생겨도 상관이 없다면.. 여기 참고!!!