스크롤 기반 애니메이션 우수사례

Swetha Gopalakrishnan
Swetha Gopalakrishnan
Saurabh Rajpal
Saurabh Rajpal

스크롤 기반 애니메이션은 웹의 일반적인 UX 패턴입니다. 스크롤 기반 애니메이션은 스크롤 컨테이너의 스크롤 위치에 연결됩니다. 즉, 위 또는 아래로 스크롤하면 연결된 애니메이션이 직접적으로 앞뒤로 스크러빙됩니다. 시차 배경 이미지나 스크롤할 때 움직이는 읽기 표시기와 같은 효과가 여기에 해당합니다.

개발자는 일반적으로 JavaScript를 사용하여 기본 스레드의 스크롤 이벤트에 응답하는 방식으로 스크롤 기반 애니메이션을 만듭니다. 따라서 스크롤 이벤트가 비동기식으로 전송되므로 스크롤과 동기화되는 성능이 우수한 스크롤 기반 애니메이션을 만들기가 어렵고 기본 스레드에 있으므로 자주 버벅거립니다.

하지만 이제 브라우저에 제공되는 새로운 CSS 및 UI 기능의 일환으로 선언적 스크롤 기반 애니메이션을 만들 수 있습니다. 기존 Web Animations API (WAAPI)CSS Animations API와 통합되는 새로운 개념인 스크롤 타임라인과 뷰 타임라인을 사용하면 단 몇 줄의 코드로 기본 스레드에서 매끄러운 스크롤 기반 애니메이션을 실행할 수 있습니다. 이 사례에서는 Tokopedia, redBus, Policybazaar에서 이 새로운 기능을 통해 어떤 혜택을 얻고 있는지 알아보세요.

브라우저 지원

  • Chrome: 115.
  • Edge: 115.
  • Firefox: 플래그 뒤에 있습니다.
  • Safari: 지원되지 않음

소스

Tokopedia

Tokopedia는 이전의 맞춤 JavaScript 구현을 스크롤 기반 애니메이션으로 대체하여 페이지 성능을 최적화하고 전자상거래 전환 유입경로 전반에서 전반적인 탐색 환경을 개선했습니다.

기존 JavaScript 스크롤 이벤트를 사용할 때보다 코드 줄을 최대 80% 줄일 수 있었고 스크롤하는 동안 평균 CPU 사용량이 50% 에서 2% 로 감소했습니다.— 앤디 위할림, Tokopedia 선임 소프트웨어 엔지니어

사용자 스크롤 위치에 따라 상단 고정 막대의 표시 상태를 애니메이션으로 변경

코드

다음 구현은 scroll() 함수를 사용하여 CSS 애니메이션의 진행률을 제어하기 위한 익명의 스크롤 진행률 타임라인을 설정합니다. 상단 고정 막대의 표시 여부는 정의된 animationRange 내의 스크롤 위치에 따라 달라집니다.

const toggleBar = keyframes({
  to: { height: 48 },
});

export const cssWrapper = css({
  position: 'fixed',
  left: 0,
  width: '100vw',
  pointerEvents: 'none',
  marginTop: 120,
  height: 0,
  overflow: 'hidden',
  display: 'flex',
  flexDirection: 'column',
  justifyContent: 'flex-end',
  animation: `${toggleBar} linear both`,
  animationTimeline: 'scroll()',
  animationRange: '20px 70px',
});

redBus

redBus는 전환 유입경로 초기에 모든 사용자에게 표시되는 할 일 방문 페이지에서 모바일과 데스크톱에 서로 다른 애니메이션을 사용합니다. 스크롤 기반 애니메이션을 사용하면 이러한 맞춤 JavaScript 구현을 CSS로 대체하여 동일한 효과를 얻을 수 있었습니다.

사용 사례

이미지 공개 (모바일용) 및 커버 플로우 (데스크톱용)가 적용된 사진 갤러리

redBus '할 일' 사진 갤러리에 이미지를 로드하기 위한 스크롤 기반 애니메이션 이미지 공개 효과

코드 (모바일)

이전 예에서 Tokopedia는 익명의 스크롤 진행률 타임라인을 사용했습니다. 다음 코드에서 redBus는 이름이 지정된 뷰 진행률 타임라인을 사용합니다. 애니메이션은 요소의 가장 가까운 상위 요소 스크롤러(이 경우 사진 갤러리 스크롤러) 내에서 정의된 animation-range 내의 <img> 요소의 opacityclip-path를 변경합니다.

const reveal = keyframes`
   from {
       opacity: 0;
       clip-path: inset(45% 20% 45% 20%);
   }
   to {
       opacity: 1;
       clip-path: inset(0% 0% 0% 0%);
   }`

const CardImage = styled.div`
   width: 100%;
   height: 100%;
   img {
       border-top-left-radius: 0.75rem;
       border-top-right-radius: 0.75rem;
       height: 100%;
       width: 100%;
       object-fit: cover;
       view-timeline-name: --revealing-image;
       view-timeline-axis: block;
  
       /* Attach animation, linked to the  View Timeline */
       animation: linear ${reveal} both;
       animation-timeline: --revealing-image;
  
       /* Tweak range when effect should run*/
       animation-range: entry 25% cover 50%;
   }
`;

이 기능은 실적과 더 나은 환경을 완벽하게 조합하여 SEO를 위한 페이지 환경 신호를 개선해 주므로 매우 기쁩니다. 게다가 학습 곡선이 최소화되어 모든 전자상거래 웹사이트의 필수품이 되었습니다. 또한 더 많은 사용자 여정에 SDA를 활용하기 위한 다른 팀의 긍정적인 의견과 지원을 받았습니다.— 아미트 쿠마르, redBus 선임 엔지니어링 관리자

Policybazaar

보험 계획 비교는 사용자가 의사결정 과정을 안내하기 위해 반복적으로 취하는 주요 액션입니다. Policybazaar는 스크롤 기반 애니메이션을 사용하여 사용자가 표를 스크롤할 때 우선순위가 낮은 요소의 크기를 줄였습니다. 이에 따라 가독성이 개선되는 동시에 원활한 스크롤 환경이 구현되었습니다.

스크롤 기반 애니메이션을 사용하면 사용자가 계획을 비교할 수 있는 뷰포트 공간을 최대화하여 방해받지 않고 집중할 수 있는 독서 환경을 제공할 수 있었습니다.—Rishabh Mehrotra, PolicyBazaar, 생명보험 BU 디자인 책임자

투자 및 생명보험 LOB (사업 부문)의 요금제 비교 표에서 스크롤 기반 애니메이션 animate-timeline

코드

Tokopedia의 이전 예와 마찬가지로 Policybazaar에서는 scroll() 함수를 사용하여 CSS 애니메이션의 진행률을 제어하기 위한 익명의 스크롤 진행률 타임라인을 설정합니다. 이 경우 정의된 animation-range 내의 스크롤 위치를 기반으로 글꼴 크기를 줄이고 헤더를 페이드 처리합니다.

@supports (animation-timeline: scroll()) {
.plan-comparison .inner-header {
animation: move-and-fade-header linear both;
}
.plan-comparison .left-side {
animation: shrink-name linear both;
}
.plan-comparison .inner-header, .plan-comparison .left-side {
animation-timeline: scroll();
animation-range: 0 150px;
}
}

@keyframes move-and-fade-header {
  to {
    translate: 0% -5%;
    top:103px;
}
}

@keyframes shrink-name {
  to {
    font-size: 1.5rem;
  }
}

사용자 여정 전반에서 일반적인 패턴으로 스크롤 기반 애니메이션 사용

추천 전자상거래 회사는 모두 카드가 있는 페이지에서 스크롤 기반 애니메이션을 사용하여 카드에 애니메이션을 적용하여 사용자의 관심을 끌었습니다 . 다음 예는 사용자 여정의 여러 부분에 있는 카드의 스크롤 효과를 보여줍니다. 이렇게 하려면 일반적으로 다음 CSS 스니펫과 같이 맞춤 CSS 애니메이션의 진행률을 제어하는 익명 뷰 진행률 타임라인을 사용합니다.

@keyframes animate-in {
 0% { opacity: 0; transform: translateY(10%); }
 100% { opacity: 1; transform: translateY(0); }
}

@keyframes animate-out {
 0% { opacity: 1; transform: translateY(0); }
 100% { opacity: 0; transform: translateY(-10%); }
}

.flyin_animate {
   animation: animate-in linear forwards;
   animation-timeline: view();
   animation-range: entry;
}

redBus (홈페이지)

redBus '할 일' 방문 페이지에서 제품 카드를 로드하기 위한 스크롤 기반 애니메이션 플라이인 효과

Policybazaar (제품 등록정보 페이지)

Investment and Life LOB(Line of Business)의 제품 카드 카드인 스크롤 기반 애니메이션 페이드 인 및 페이드 아웃입니다.

Tokopedia (제품 세부정보 페이지)

나열된 제품을 스크롤하는 동안 표시되는 페이드 인, 페이드 아웃 애니메이션

Scroll-driven Animations API를 사용할 때 고려해야 할 사항

지원하지 않는 브라우저의 경우 스크롤 기반 애니메이션을 폴리필할 수 있습니다(예: 스크롤 타임라인 폴리필 사용). 이 경우 프레임워크와 함께 잘 작동하는지, 폴리필을 사용하는 브라우저에서 애니메이션 실패나 버벅거림이 발생하지 않는지 확인하기 위한 추가 테스트가 필요합니다.

CSS에서 @supports를 사용하여 스크롤 기반 애니메이션을 사용하기 전에 animation-timeline 지원을 테스트할 수 있습니다. 예를 들면 다음과 같습니다.

@supports (animation-timeline: scroll()) {

}

리소스

뷰 전환, 팝오버, 컨테이너 쿼리, has() 선택기와 같은 새로운 CSS 및 UI 기능을 사용하여 이커머스 기업이 어떤 이점을 얻었는지 설명하는 이 시리즈의 다른 도움말을 살펴보세요.