내부 요소 스크롤 위치 도달 시 부모 요소 스크롤 방지하기

2024. 5. 28. 09:59·Frontend/Development
728x90
SMALL
이 글에서는 화면 흔들림을 방지하고, 자연스러운 스크롤 경험을 제공하기 위한 방법을 설명합니다.

 

웹 페이지를 만들다 보면 종종 컴포넌트 내에 스크롤이 필요한 경우가 있습니다. 컴포넌트 안에서 스크롤을 최대로 내리면 부모 컴포넌트의 스크롤이 함께 움직이는 문제가 발생할 수 있습니다. 이를 방지하기 위해 HTML 및 Body 태그에 `overflow: hidden` 속성을 적용할 수 있지만, 이로 인해 스크롤바가 사라지면서 화면 크기가 변동되어 사용자에게 불편함을 줄 수 있습니다. 이 글에서는 이러한 문제를 해결하기 위한 방법을 소개합니다.

 

overflow: hidden으로 처리하였을 때

 

아래 코드는 리액트(React)에서 이 문제를 해결하기 위한 예제입니다. useEffect 훅을 사용하여 조건에 따라 바디의 패딩을 조정하여 화면 흔들림을 방지합니다.

const TestPage: React.FC = () => {
  const [isChildHovered, setChildHovered] = React.useState(false);

  React.useEffect(() => {
    const isScrollbarExist =
      document.body.scrollHeight > document.body.clientHeight;

    const applyStyles = () => {
      document.body.style.overflow = 'hidden';

      if (isScrollbarExist) {
        document.body.style.paddingRight = '15px';
      }
    };

    const removeStyles = () => {
      document.body.style.removeProperty('overflow');
      document.body.style.removeProperty('padding-right');
    };

    if (isChildHovered) {
      applyStyles();
    } else {
      removeStyles();
    }

    return () => {
      removeStyles();
    };
  }, [isChildHovered]);

  return (
    <StyledParentElement>
      <StyledChildWrapper
        onMouseEnter={() => setChildHovered(true)}
        onMouseLeave={() => setChildHovered(false)}
      >
        <StyledChildElement>Child</StyledChildElement>
      </StyledChildWrapper>
    </StyledParentElement>
  );
};


스크롤바 존재 여부 확인: 

  • isScrollbarExist 변수를 통해 문서의 스크롤 높이와 클라이언트 높이를 비교하여 스크롤바가 존재하는지 확인합니다.
  • isScrollbarExist가 있는 이유는 부모 엘리먼트에 스크롤이 없는 경우가 있을 수 있기 때문입니다. 부모 엘리먼트에 스크롤바가 없는데, 패딩을 주었을 때 반대로 화면이 밀리는 현상이 발생할 수 있습니다.

부모의 scrollbar가 없을 때, padding이 있으면 오히려 레이아웃이 깨짐

 

 

스타일 적용 함수:

  • applyStyles 함수는 바디에 overflow: hidden 스타일을 적용하여 스크롤을 비활성화합니다.
  • 스크롤바가 존재하는 경우 바디에 padding-right: 15px 스타일을 추가합니다.
    • 기본 스크롤바 너비가 15px이기 때문에 15px로 설정합니다. 이는 브라우저마다 다를 수 있습니다.
    • 브라우저마다 스크롤바 사이즈가 다를 수 있기 때문에, CSS로 모든 브라우저의 너비를 통일한 후 패딩을 추가하는 것이 좋은 방법입니다.

이벤트 핸들러:

  • onMouseEnter/onMouseLeave이벤트가 발생하면 isChildHovered를 상태를 변경하여 스타일을 설정합니다.

 

padding을 추가하여 레이아웃이 변하는 것을 방지

 

컴포넌트 내부에서 스크롤할 때 발생하는 부모 컴포넌트의 스크롤 문제는 사용자 경험에 큰 영향을 미칠 수 있습니다. 이 글에서 소개한 방법을 사용하면 화면 흔들림을 방지하고, 자연스러운 스크롤 경험을 제공할 수 있습니다.

저작자표시 (새창열림)

'Frontend > Development' 카테고리의 다른 글

React 18, 19: 새롭게 나온 Hook 소개  (0) 2025.01.19
javascript 이미지 색상 추출하기  (0) 2024.08.11
useLoaderData와 useRouteLoaderData의 사용법과 차이점  (2) 2023.12.31
FontFace를 활용하여 웹사이트의 글꼴을 동적으로 로딩하기  (0) 2023.12.17
React에서 한글 두 번 입력되는 오류, isComposing로 해결하기  (0) 2023.10.29
'Frontend/Development' 카테고리의 다른 글
  • React 18, 19: 새롭게 나온 Hook 소개
  • javascript 이미지 색상 추출하기
  • useLoaderData와 useRouteLoaderData의 사용법과 차이점
  • FontFace를 활용하여 웹사이트의 글꼴을 동적으로 로딩하기
끄적끄적 개발자
끄적끄적 개발자
생각나는 대로 끄적끄적, 코드 노트
  • 끄적끄적 개발자
    코딩을 끄적끄적
    끄적끄적 개발자
  • 전체
    오늘
    어제
    • 분류 전체보기 (43)
      • Backend (0)
      • Frontend (39)
        • Development (19)
        • Dev Notes (9)
        • React Hook Form (3)
        • Module Federation (3)
        • Clone coding (5)
      • UIUX (2)
      • ETC (2)
  • 인기 글

  • 태그

    개발/기술
    회고
    개발/코드품질
    UI/UX
    개발/정보
    개발/언어
  • 최근 댓글

  • 최근 글

  • hELLO· Designed By정상우.v4.10.3
끄적끄적 개발자
내부 요소 스크롤 위치 도달 시 부모 요소 스크롤 방지하기
상단으로

티스토리툴바