스크롤을 내릴 때마다 사진이 스르륵 떠오르게 하려고, 스크롤 위치를 자바스크립트로 밤새 감시한다 — 스크롤 기반 애니메이션(scroll-driven animation)이 그 일을 CSS 한 곳에 넘기는 시대

스크롤을 내릴 때마다 사진이 스르륵 떠오르게 하려고, 스크롤 위치를 자바스크립트로 밤새 감시한다 — 스크롤 기반 애니메이션(scroll-driven animation)이 그 일을 CSS 한 곳에 넘기는 시대
스크롤 기반 애니메이션 대표 이미지

스크롤을 한 칸 내릴 때마다 사진이 아래에서 스르륵 떠오르고, 숫자가 또르르 올라가고, 진행 막대가 화면 위쪽에서 스윽 차오른다. 요즘 잘 만든 홈페이지에서 흔히 보는 이 '움직임'은, 얼마 전까지 대부분 자바스크립트가 스크롤 위치를 쉬지 않고 감시해서 만들어 낸 결과였다. 손님이 마우스 휠을 굴릴 때마다 코드가 "지금 몇 픽셀 내려왔지? 이 사진이 화면에 들어왔나?"를 초당 수십 번 되물었다. 이제는 그 일을 브라우저가, CSS 몇 줄로 대신해 준다.

스크롤에 맞춰 움직이는 화면은 왜 늘 무거웠나

'화면에 들어오면 부드럽게 나타나는 효과'는 작은 회사 홈페이지에서도 인기가 많다. 밋밋한 소개 페이지에 생기를 불어넣고, 시선을 아래로 끌어내리기 때문이다. 그런데 이 효과를 만들려면 예전에는 스크롤을 감시하는 자바스크립트가 필요했다. 라이브러리를 하나 더 얹고, 스크롤할 때마다 요소의 위치를 계산하고, 조건이 맞으면 클래스를 붙였다.

문제는 이 감시가 메인 스레드, 그러니까 브라우저가 화면을 그리는 바로 그 일손 위에서 돌아간다는 데 있었다. 스크롤은 빠른데 계산이 밀리면 화면이 뚝뚝 끊긴다. 특히 성능이 넉넉지 않은 손님의 휴대폰에서 이 끊김이 도드라진다. 부드럽게 보이라고 넣은 효과가 오히려 '버벅이는 사이트'라는 인상을 남기는 셈이다.

animation-timeline — 스크롤을 하나의 '타임라인'으로 본다

스크롤 기반 애니메이션(scroll-driven animation)의 발상은 단순하다. 그동안 애니메이션의 진행을 정하는 기준은 오직 시간이었다. "2초에 걸쳐 서서히 나타나라"처럼. 여기에 시간 대신 스크롤을 진행 기준으로 꽂는 것이 핵심이다. 스크롤을 0%에서 100%까지 흐르는 하나의 타임라인으로 취급하고, 애니메이션을 그 위에 얹는다.

view() — 요소가 화면에 들어오는 만큼

가장 많이 쓰는 방식이다. 어떤 요소가 화면 안으로 들어오기 시작해 완전히 지나갈 때까지를 0%에서 100%로 잡는다. 사진이 아래에서 떠오르며 또렷해지는 그 흔한 효과가, 자바스크립트 한 줄 없이 animation-timeline: view() 한 줄로 끝난다. 손님이 스크롤을 멈추면 애니메이션도 멈추고, 위로 되감으면 효과도 되감긴다. 스크롤과 화면이 한 몸처럼 붙어 움직인다.

scroll() — 페이지 전체의 진행률에 맞춰

페이지 맨 위에 '지금 어디까지 읽었나'를 보여 주는 진행 막대. 이건 개별 요소가 아니라 페이지 전체 스크롤을 기준으로 삼는다. animation-timeline: scroll()이 그 역할을 한다. 스크롤이 절반쯤 내려가면 막대도 절반 차오른다. 예전 같으면 스크롤 이벤트를 붙들고 퍼센트를 계산했을 일이다.

작은 회사 웹사이트에서 이게 왜 반가운가

첫째, 더 가볍다. 스크롤 효과 하나 넣자고 무거운 애니메이션 라이브러리를 통째로 불러오지 않아도 된다. 페이지가 그만큼 빨리 뜨고, 로딩 속도는 검색 노출과 이탈률에 직접 영향을 준다.

둘째, 더 부드럽다. 이 애니메이션은 화면을 그리는 일손과 별개로 처리되도록 설계돼 있어, 스크롤이 빨라도 잘 끊기지 않는다. 손님의 오래된 휴대폰에서도 매끄럽게 넘어갈 가능성이 높다.

셋째, 고치기 쉽다. 효과의 세기와 시점이 CSS 한 곳에 모여 있으니, 나중에 '조금 더 은은하게'를 주문해도 자바스크립트를 헤집을 필요가 없다. 유지보수 비용이 줄어든다는 뜻이다.

아직은 조심할 점

모든 브라우저가 이 기능을 지원하는 것은 아니다. 그래서 실무에서는 이 효과가 없어도 내용은 멀쩡히 보이도록 만드는 것이 원칙이다. 지원하는 브라우저에서는 스르륵 떠오르고, 지원하지 않는 곳에서는 그냥 처음부터 또렷하게 보이면 된다. 효과는 어디까지나 덤이어야지, 그것이 사라졌다고 사진이나 글이 통째로 안 보이는 일은 없어야 한다. 또 하나, 움직임에 예민한 손님을 위해 '모션 줄이기' 설정을 켠 사람에게는 효과를 얌전히 꺼 주는 배려도 함께 넣는 것이 좋다.

결국 중요한 건 '왜 움직이는가'

기술이 쉬워졌다고 해서 화면 곳곳을 움직이게 만들 이유는 없다. 좋은 움직임은 손님의 시선을 봐야 할 곳으로 안내하고, 다음으로 넘어가라고 부드럽게 등을 민다. 반대로 아무 데나 튀는 움직임은 눈을 피곤하게 하고 정작 중요한 문의 버튼을 가린다. CYAN에서 홈페이지를 만들 때도, 새 CSS 기술을 '넣을 수 있어서'가 아니라 '손님의 길을 매끄럽게 하려고' 쓰는지를 늘 먼저 따진다. 도구가 가벼워질수록, 그 도구를 어디에 쓸지 고르는 안목이 더 값지다.