GSAP에서 Remotion까지: 고정형 HTML5 배너가 모션 시스템이 되기까지

– ArtXTech

GSAP에서 Remotion까지

고정형 HTML5 배너가 모션 시스템이 되기까지

내가 웹 애니메이션의 세계에 본격적으로 발을 들인 순간은 대학 시절의 사이드 프로젝트도, 최신 프론트엔드 프레임워크도 아니었다. 2018–2019년 광고 에이전시에서 HTML5 배너를 만들던 시절이었다.

당시 내 손에 들어오는 것은 대체로 다음과 같았다.

  • 포토샵으로 만들어진 스토리보드
  • 디자이너가 export한 이미지와 로고 에셋
  • 정해진 광고 규격과 파일 용량 제한
  • 몇 초 안에 메시지를 전달해야 하는 미디어 슬롯
  • 브랜드·미디어·클라이언트의 피드백
  • 특정 브라우저와 광고 플랫폼에서 반드시 작동해야 한다는 조건

그 에셋들을 고정된 크기의 배너 창 안에 배치하고, 스프라이트 시트로 묶고, GSAP timeline으로 등장·퇴장·반복을 조율했다. 겉으로는 작은 광고였지만, 실제로는 디자인·코드·미디어 규격·비즈니스 요구사항을 한 번에 만족시켜야 하는 작은 프로덕션 시스템이었다.

시간이 지나며 같은 사고방식은 웹사이트 랜딩 페이지, 패럴랙스 스크롤, 100DaysOfUI 모션 실험, WebGL과 Canvas, 그리고 Remotion 영상 제작으로 이동했다.

Photoshop storyboard
    ↓
Sprite sheet / optimised assets
    ↓
Fixed-size HTML5 banner
    ↓
GSAP timeline
    ↓
Landing page / parallax interaction
    ↓
React + TypeScript motion components
    ↓
Remotion frame-based composition

이 글은 GSAP 사용법을 처음부터 설명하는 튜토리얼이 아니다. 광고 에이전시에서의 고생과 클라이언트 커뮤니케이션, 웹 애니메이션의 여러 적용 사례, 그리고 그 경험이 어떻게 영상 시스템으로 확장되었는지를 기록하는 기술·프로덕션 회고다.


1. 시간대별 여정

시기 작업 환경 핵심 작업 얻은 감각
2018–2019 광고 에이전시 HTML5 배너, 스프라이트 시트, GSAP 제한된 슬롯 안에서 시간과 용량을 설계하기
2019–2023 기업·웹 프로젝트 랜딩 페이지, 캠페인 UI, 인터랙션 브랜드 요구와 기술 제약 번역하기
2024 R&D 재시작 React, TypeScript, GSAP, WebGL 오래된 모션 감각을 현대 런타임에 이식하기
2024–2025 100DaysOfUI 매일 UI·모션 컴포넌트 실험 패턴을 수집하고 재사용 단위로 분류하기
2025 Figma·Jitter·Remotion JSON, 레이어, 타이밍 파싱 디자이너의 시안을 코드 기반 씬으로 변환하기
2025–2026 Lyrics MV MIDI, SRT, 셰이더, 씬 타임라인 오디오·텍스트·이미지를 프레임으로 오케스트레이션하기

이 여정에서 GSAP은 하나의 라이브러리로만 남지 않았다. 나에게 GSAP은 시간을 명시하고, 요소 간 관계를 정의하고, 반복 가능한 결과를 만드는 사고방식에 가까워졌다.


2. 2018–2019 — 광고 배너라는 작은 화면의 큰 제약

처음 받은 과제: 스토리보드를 시간축으로 옮기기

광고 작업은 보통 포토샵 스토리보드와 함께 시작됐다. 디자이너가 프레임별 화면을 구성하면 개발자는 그 장면을 실제 광고 슬롯에서 재생되는 시간 기반 인터랙션으로 변환해야 했다.

Storyboard frame 01 → logo / headline
Storyboard frame 02 → product image enters
Storyboard frame 03 → offer appears
Storyboard frame 04 → CTA remains visible

문제는 스토리보드가 곧바로 실행 가능한 설계도는 아니라는 점이었다. 그림에는 자연스러운 움직임처럼 보이는 장면도 실제 코드에서는 다음 질문을 필요로 했다.

  • 어떤 요소가 먼저 등장하는가?
  • 이전 요소는 사라지는가, 남아 있는가?
  • 이동 거리는 px 기준인가, 퍼센트 기준인가?
  • easing은 무엇인가?
  • 애니메이션이 끝난 뒤 CTA는 몇 초 동안 유지되는가?
  • 사용자가 배너를 보지 않고 지나가도 핵심 메시지가 남는가?
  • 파일 용량이 광고 플랫폼 제한을 넘지 않는가?

이 질문들을 답하는 일이 HTML5 배너 개발의 실제 작업이었다.

고정된 광고 창 안에서 설계하기

배너는 화면이 작고, 규격이 고정되어 있고, 사용자가 머무르는 시간이 짧았다. 일반적인 웹 페이지처럼 스크롤을 전제로 하거나 사용자가 충분히 탐색해 줄 것이라고 기대할 수 없었다.

┌──────────────────────────────┐
│                              │
│       Visual / Product       │  fixed viewport
│                              │
│  Headline                    │
│                  CTA         │
└──────────────────────────────┘
          300 × 250 / 728 × 90 / ...

따라서 모션은 장식이 아니라 정보 구조였다.

  • 첫 프레임: 브랜드와 캠페인 맥락
  • 중간 프레임: 제품 또는 혜택의 강조
  • 마지막 프레임: 행동 유도와 브랜드 회수

작은 화면에서 너무 많은 요소를 동시에 움직이면 메시지가 읽히지 않았다. 반대로 너무 정적인 화면은 광고가 로드되었는지조차 전달하지 못했다. 이 균형을 맞추는 일이 디자이너와 개발자 사이의 반복적인 대화가 되었다.


3. 스프라이트 시트: 에셋을 움직임으로 바꾸는 전처리

당시 자주 사용한 방식 중 하나는 여러 프레임 이미지를 하나의 스프라이트 시트로 묶는 것이었다. 개별 이미지 파일을 매번 요청하는 대신, 하나의 이미지에서 background-position을 이동시켜 프레임을 바꾸는 방식이다.

목적

  • HTTP 요청 수 줄이기
  • 이미지 에셋을 한 번에 관리하기
  • 광고 플랫폼의 로딩 시간과 용량 제한에 대응하기
  • 프레임 기반 그래픽을 브라우저에서 재생하기

기술 방식

.sprite-sheet {
  width: 300px;
  height: 250px;
  background-image: url('./product-frames.jpg');
  background-repeat: no-repeat;
}
const frameWidth = 300;
const frameIndex = 3;

TweenMax.set(spriteElement, {
  backgroundPosition: `${-frameWidth * frameIndex}px 0`
});

실제 프로젝트에서는 포토샵 아트보드의 간격, export 해상도, 투명 영역, 이미지 압축 정도까지 확인해야 했다. 프레임이 정확히 맞지 않으면 애니메이션 중간에 옆 프레임이 비치거나, 배너 경계 밖으로 이미지가 튀어나왔다.

스프라이트 시트 아키텍처

Photoshop layers
    ↓ export
Frame images
    ↓ packing / compression
Sprite sheet
    ↓ background-position mapping
DOM element
    ↓ GSAP timeline
Frame animation

아카이브 아이템

  • 포토샵 스토리보드 프레임
  • 스프라이트 시트 원본과 압축본
  • 프레임별 background-position 표
  • 고정형 배너 규격별 캔버스
  • 로딩 전후 비교 GIF
  • 광고 플랫폼 업로드 검수 캡처
[이미지 후보: Photoshop storyboard → sprite sheet 변환 과정]
[이미지 후보: 300×250 배너의 프레임별 background-position map]
[이미지 후보: 로딩 전후와 용량 최적화 결과 비교]

4. GSAP Timeline: 광고를 순서가 있는 시스템으로 만들기

GSAP을 처음 깊이 사용하며 배운 핵심은 to()나 fromTo()의 문법이 아니었다. 중요한 것은 여러 요소의 움직임을 하나의 시간축 안에서 설계하는 일이었다.

const tl = gsap.timeline({
  defaults: {
    ease: 'power2.out'
  }
});

tl.from(logo, {
  opacity: 0,
  y: -20,
  duration: 0.4
});

tl.from(title, {
  opacity: 0,
  x: -24,
  duration: 0.5
}, '-=0.2');

tl.from(ctaButton, {
  opacity: 0,
  scale: 0.8,
  duration: 0.35
}, '+=0.1');

타임라인이 생기면 “이 요소를 0.3초 뒤에 보여준다”는 지시가 “인트로가 끝난 뒤 제목이 들어오고, 제목의 강조가 끝난 뒤 CTA가 나타난다”는 구조로 바뀐다.

당시 자주 조정하던 변수

변수 의미 광고에서의 역할
duration 움직임이 걸리는 시간 메시지 노출 속도
delay 시작 전 대기 정보 계층과 호흡
ease 속도 변화 브랜드의 인상과 자연스러움
x, y 이동 거리 시선의 방향
scale 크기 변화 제품·CTA 강조
opacity 노출 정도 장면 전환
repeat 반복 횟수 배너의 루프 구조
repeatDelay 반복 사이 간격 피로도 조절

반복 배너의 함정

광고 배너는 사용자가 보고 있는 동안 계속 반복될 수 있었다. 첫 번째 loop에서는 자연스러워 보이던 모션도 두 번째, 세 번째 loop에서는 피로하게 느껴질 수 있다.

그래서 다음을 확인했다.

  • 반복 시 요소의 초기 상태가 정확히 복원되는가?
  • timeline이 중복 생성되지 않는가?
  • CTA가 매번 너무 강하게 튀어나오지 않는가?
  • 마지막 프레임이 첫 프레임과 연결되는가?
  • 애니메이션이 끝나도 클릭 영역은 유지되는가?

이때의 경험은 훗날 React의 useEffect cleanup, GSAP context, Remotion의 deterministic rendering을 이해하는 바탕이 되었다.


5. 클라이언트와의 대화: “그냥 더 화려하게 해주세요”의 실제 의미

광고 에이전시에서 어려운 것은 코드만이 아니었다. 클라이언트의 피드백을 실행 가능한 모션 규칙으로 번역하는 일이 더 어려웠다.

자주 등장했던 피드백

  • “조금 더 눈에 띄게 해주세요.”
  • “제품이 더 고급스럽게 보였으면 좋겠어요.”
  • “첫 화면에서 브랜드가 바로 보여야 합니다.”
  • “너무 빨라서 안 읽혀요.”
  • “모바일에서도 같은 느낌이어야 합니다.”
  • “파일 사이즈는 더 줄여야 합니다.”
  • “CTA를 조금 더 세게 보여주세요.”

이 말들은 하나의 기술 요구사항이 아니었다. 각각 다음과 같은 설계 문제로 다시 해석해야 했다.

“더 눈에 띄게”
    → contrast / scale / timing / repetition 중 무엇인가?

“고급스럽게”
    → slower easing / restrained movement / spacing / opacity?

“바로 보여야”
    → first-frame content / load strategy / fallback state?

“더 세게”
    → CTA size / color / motion / copy hierarchy?

내가 배운 번역 레이어

graph LR
    A[Client feedback] --> B[Creative intent]
    B --> C[Motion rule]
    C --> D[Technical constraint]
    D --> E[GSAP implementation]
    E --> F[Preview / QA]
    F --> A

디자이너는 시각적 의도를 말하고, 클라이언트는 비즈니스 목적을 말하고, 개발자는 플랫폼의 제약을 말한다. 그 사이에서 개발자가 해야 할 일은 “안 됩니다”라고 끝내는 것이 아니라, 요구사항을 구현 가능한 변수로 번역하는 것이다.

물론 모든 요구가 그대로 구현되는 것은 아니었다. 광고의 트래픽과 클릭 노출은 곧 비용이었고, 파일 용량과 로딩 성능을 무시한 화려함은 실제 캠페인에 부담이 되었다.

광고에서 최종 산출물은 가장 화려한 애니메이션이 아니라, 제한된 비용과 시간 안에서 메시지를 전달하는 실행 가능한 패키지다.


6. 배너에서 랜딩 페이지로: GSAP의 화면이 커지다

광고 작업 이후 GSAP은 고정형 배너를 넘어 웹사이트 랜딩 페이지에 적용되었다. 화면의 크기가 커지고 스크롤이 추가되면서, 시간축은 사용자의 입력과 결합되었다.

적용한 케이스

  • Hero 입장 애니메이션
  • 텍스트 split과 character reveal
  • 이미지 trail과 hover transition
  • 패널 기반 landing page
  • ScrollTrigger 기반 section reveal
  • 이미지 그리드와 3D parallax
  • infinite scroll과 velocity 기반 텍스트
  • 페이지 전환과 pixel transition

패럴랙스 스크롤

패럴랙스는 여러 레이어가 서로 다른 속도로 이동하도록 만들어 깊이감을 주는 방식이다. 중요한 것은 단순히 scrollY에 값을 곱하는 것이 아니라, 각 레이어의 역할과 기준점을 정의하는 것이다.

gsap.to(backgroundLayer, {
  yPercent: 20,
  ease: 'none',
  scrollTrigger: {
    trigger: section,
    start: 'top bottom',
    end: 'bottom top',
    scrub: true
  }
});

gsap.to(foregroundLayer, {
  yPercent: -8,
  ease: 'none',
  scrollTrigger: {
    trigger: section,
    start: 'top bottom',
    end: 'bottom top',
    scrub: true
  }
});
scroll input
    ├── background: slow movement
    ├── content: reference layer
    ├── foreground: faster movement
    └── text: independent reveal timing

ScrollTrigger에서 생긴 문제

  • 이미지가 로드되기 전에 trigger 위치가 계산됨
  • smooth scroll 라이브러리와 실제 scroll position이 어긋남
  • 리사이즈 후 pin과 spacer가 잘못 계산됨
  • React rerender 때 timeline이 중복 생성됨
  • 모바일 viewport에서 100vh가 달라짐
  • 너무 많은 transform이 프레임을 떨어뜨림

광고 배너에서 “고정된 창을 지키는 일”이 중요했다면, 웹에서는 “변하는 viewport와 사용자의 입력을 지키는 일”이 중요했다.


7. 100DaysOfUI: 잊었던 모션 감각을 다시 훈련하기

기업용 웹 프로젝트를 오래 다루며 한동안 모션 구현에서 멀어져 있었다. React와 TypeScript가 익숙해졌지만, 오히려 예전의 순수한 모션 감각은 녹슬어 있었다.

그래서 100DaysOfUI를 시작했다. 매일 하나의 UI 또는 모션 패턴을 만들고, 결과를 Day별 컴포넌트로 격리했다.

주요 실험의 계보

작업 핵심 실험 GSAP과의 연결
Day16–20 글리치, 왜곡, 이미지 분해 timeline, refs, block movement
Day21 Hero와 스크롤 ScrollTrigger, smooth scroll
Day22–30 갤러리와 패널 image layer, reveal, parallax
Day35–36 Circular/Falling Text text layout, Canvas, physics
Day38 Infinite Scroll Observer, RAF, wrap logic
Day41–49 trail, grid, pixel, text pointer, reveal, transition
Day51–59 velocity, ASCII, Silk scroll progress, texture layer
Day61–62 Card Swap, video mask slot, refs, media timeline

각 Day는 독립적인 미니 프로젝트였지만, 반복되는 구조는 점차 공통 모듈 후보가 되었다.

Day experiment
    ↓ isolate
Visual pattern
    ↓ compare
Reusable motion primitive
    ↓ document
Component / token
    ↓ reinterpret
Web UI / video scene

100DaysOfUI는 100개의 화면을 완성했다는 인증서라기보다, 어떤 모션이 다시 사용할 만한 시스템이 되고 어떤 모션이 한 번의 실험으로 남는지를 분류한 장기 리서치였다.

관련 기록:


8. React와 TypeScript: GSAP을 다시 이식하는 과정

예전의 배너 코드는 DOM 요소와 timeline을 직접 연결하는 방식이었다. React에서는 컴포넌트의 생명주기, 상태, ref, cleanup을 함께 고려해야 했다.

const containerRef = useRef<HTMLDivElement>(null);

useLayoutEffect(() => {
  const ctx = gsap.context(() => {
    const tl = gsap.timeline();

    tl.from('.title', {
      opacity: 0,
      y: 24,
      duration: 0.6
    });

    return () => tl.kill();
  }, containerRef);

  return () => ctx.revert();
}, []);

배너 시절과 React 시절의 차이

항목 HTML5 배너 React 기반 웹 애니메이션
DOM 생성 정적 마크업·직접 조작 컴포넌트 렌더링·조건부 구조
상태 timeline 중심 React state와 timeline 결합
생명주기 페이지 로드와 loop mount, rerender, unmount
에셋 스프라이트·고정 경로 props, data, dynamic asset
검증 플랫폼·브라우저 QA responsive·runtime·accessibility
기준 시간 초 단위 timeline scroll·pointer·state·frame

문법은 달라졌지만 핵심은 같았다. 요소가 언제 나타나고, 어떤 순서로 움직이며, 종료 시 어느 상태에 있어야 하는지를 명시하는 것.

GSAP을 만능으로 사용하지 않기

GSAP이 모든 문제의 정답은 아니다. CSS transition이 더 적합한 단순한 상태 변화도 있고, React state로 충분히 표현되는 인터랙션도 있다. 반대로 여러 요소의 상대적 타이밍과 복잡한 sequence가 필요하면 GSAP timeline이 훨씬 명확하다.

CSS transition       → 단순 상태 변화
React state          → UI 상태와 조건
GSAP timeline        → 정밀한 sequence와 choreography
Canvas/WebGL         → 픽셀·셰이더·대량 입자
Remotion frame       → 결정론적 영상 시간축

도구의 이름보다 중요한 것은 문제의 시간 모델을 선택하는 일이다.


9. Figma·Jitter에서 Remotion으로: 시안을 프레임으로 변환하기

웹 애니메이션을 다시 익힌 뒤에는 Figma와 Jitter의 디자인을 코드로 옮기는 문제를 만났다. 처음 목표는 간단했다.

Figma/Jitter JSON
    ↓ parse
Layer / transform / keyframe
    ↓ map
GSAP timeline
    ↓ render
Remotion composition

하지만 실제 JSON은 컴포지션, 레이어, 트랜스폼, 키프레임이 중첩된 구조였다. 레이어의 위치와 스케일을 읽는 것보다 더 어려운 일은, 그것을 Remotion의 프레임 시간과 GSAP의 초 단위 시간으로 일관되게 변환하는 것이었다.

레이어 스택과 가시성

상위 레이어가 하위 레이어를 가려야 하는데 텍스트의 투명한 부분으로 뒤의 화면이 비치는 문제가 있었다. 해결에는 불투명한 배경과 명시적인 z-index가 필요했다.

Composition
 ├── background
 ├── layer 01: opaque mask
 ├── layer 02: text / image
 ├── layer 03: overlay
 └── CTA / final frame

set()과 to()의 차이

영상에서 정확한 프레임에 즉시 상태를 바꾸어야 할 때는 부드러운 tween보다 명시적인 set이 필요했다.

// 시간 동안 사라지는 변화
 timeline.to(layer, { opacity: 0, duration: 0.1 }, exactTime);

// 특정 시점에 즉시 숨김
 timeline.set(layer, { visibility: 'hidden' }, exactTime);

이 문제는 광고 배너에서 마지막 CTA를 정확한 시점에 유지하던 경험과 닮아 있었다. 다만 이제 대상은 브라우저의 짧은 배너가 아니라 프레임 단위로 렌더링되는 영상이었다.

관련 기록:


10. Remotion: GSAP의 시간축을 영상으로 확장하기

Remotion을 사용하면서 GSAP 경험은 새로운 의미를 갖게 되었다. 웹에서는 timeline이 브라우저의 현재 상태를 바꾸지만, Remotion에서는 컴포지션이 각 프레임에서 어떤 결과를 출력해야 하는지 결정해야 한다.

두 시간 모델의 비교

GSAP
  timeline time → DOM transform / opacity / style

Remotion
  frame + fps   → deterministic visual state

GSAP은 여러 장면의 상대적인 순서를 설계하는 데 강했고, Remotion은 동일한 입력에서 동일한 프레임을 재현하는 데 강했다. 그래서 둘을 함께 사용할 때는 역할을 분리해야 했다.

  • Remotion: 전체 영상 길이, Sequence, 현재 frame
  • GSAP: 복잡한 요소의 상대적인 모션 규칙
  • React: 컴포넌트 구조와 props
  • TypeScript: 씬과 애셋의 계약
  • WebGL/Canvas: 픽셀·질감·대량 시각 처리

영상 제작용 아키텍처

graph TD
    A[Creative brief] --> B[Storyboard / Figma]
    B --> C[Asset and layer schema]
    C --> D[React component]
    D --> E[GSAP motion choreography]
    E --> F[Remotion frame timeline]
    F --> G[Canvas / WebGL effects]
    G --> H[Preview and render]
    H --> I[QA and revision]
    I --> C

이 구조에서는 광고 배너 시절의 “스토리보드 → 에셋 → 타임라인 → QA”가 그대로 남아 있다. 달라진 것은 출력물이 광고 플랫폼의 고정 슬롯에서 MP4와 Shorts, Lyrics MV로 바뀐 점이다.


11. Lyrics MV: 광고의 타임라인이 음악의 구조를 만났을 때

Lyrics MV 작업에서 GSAP은 더 이상 단순히 제품과 CTA를 등장시키는 도구가 아니었다. 가사와 비트, 보컬의 피치, 배경 텍스처, 장면 전환을 하나의 시간축에 배치하는 조율 도구가 되었다.

오디오 기반 씬 구성

Audio / MIDI / SRT
    ↓ parse and normalise
Beat / lyric / pitch / energy events
    ↓
Scene timeline
    ├── typography reveal
    ├── image / video layer
    ├── background shader
    ├── transition
    └── audio spectrum
    ↓
Remotion render

광고에서 CTA가 특정 프레임에 맞춰야 했다면, Lyrics MV에서는 가사가 특정 비트와 보컬의 호흡에 맞아야 했다. 결국 요구사항은 동일한 질문으로 돌아왔다.

  • 무엇이 기준 시간인가?
  • 어느 요소가 주인공인가?
  • 어떤 레이어가 남아 있고 어떤 레이어가 사라지는가?
  • 전환이 콘텐츠를 돕는가, 가리는가?
  • 반복되는 모션을 프리셋으로 만들 수 있는가?

씬을 컴포넌트로 만들기

후대의 Lyrics MV 시스템에서는 다음과 같은 층을 분리했다.

Scene config
    ↓
SceneTimelineManager
    ↓
SceneSequencePlayer
    ├── Typography renderer
    ├── Background component
    ├── Media slot
    ├── MIDI trigger
    ├── Transition
    └── Audio spectrum

이것은 광고 배너의 컴포넌트화와 같은 원리다. 텍스트·이미지·CTA를 하드코딩하는 대신, 콘텐츠와 모션 규칙을 분리하면 다른 캠페인이나 다른 곡에도 재사용할 수 있다.

관련 기록:


12. 광고 에셋 시스템에서 모션 디자인 시스템으로

광고 배너를 만들 때의 스프라이트 시트는 단순한 이미지 묶음이 아니었다. 반복되는 장면을 효율적으로 관리하기 위한 에셋 시스템이었다. 이후 이 생각은 디자인 토큰과 모션 프리셋으로 확장되었다.

Primitive

  • 색상
  • typography scale
  • spacing
  • 이미지 프레임
  • easing
  • duration
  • opacity
  • transform

Semantic motion

  • fade reveal
  • slide in
  • glitch displacement
  • pixel transition
  • image trail
  • card swap
  • text mask
  • parallax layer

Scene component

  • Hero scene
  • Gallery scene
  • Kinetic typography scene
  • Texture background scene
  • Lyrics MV scene
  • Personalised video scene
Sprite frame
    ↓
Motion primitive
    ↓
Semantic animation
    ↓
Reusable component
    ↓
Scene / composition
    ↓
Campaign / website / video

이렇게 보면 GSAP의 무한한 활용성은 “어디에나 쓸 수 있다”는 뜻이 아니다. 같은 시간 기반 사고를 서로 다른 출력 환경에 적용할 수 있다는 뜻에 가깝다.

  • 고정형 광고: 제한된 viewport와 짧은 노출 시간
  • 랜딩 페이지: 스크롤과 반응형 viewport
  • 100DaysOfUI: 독립적인 모션 패턴 실험
  • WebGL: 픽셀과 셰이더의 시간 변화
  • Remotion: 결정론적인 프레임 출력
  • Lyrics MV: 오디오와 서사를 기준으로 한 씬 오케스트레이션

13. 작업별 아카이브 인덱스

작업 목적 기술 방식 도입 방식 아키텍처 아카이브 아이템
HTML5 banner 짧은 시간에 광고 메시지 전달 HTML5, CSS, JS, GSAP 스토리보드 프레임을 sequence로 변환 fixed viewport → layers → timeline storyboard, banner capture
Sprite sheet 에셋 요청과 용량 절감 Photoshop export, CSS background-position 여러 프레임을 하나의 이미지로 패킹 sheet → frame map → DOM sprite sheet, frame map
Banner QA 플랫폼 제약 대응 browser QA, ad platform spec 용량·브라우저·loop 검증 asset → build → preview → QA size report, QA checklist
Landing animation 첫 화면의 계층과 흐름 설계 GSAP, React, SCSS mount 후 timeline 실행 section → refs → timeline hero storyboard
Parallax scroll 스크롤을 깊이감으로 변환 ScrollTrigger, smooth scroll 레이어별 progress 매핑 scroll → trigger → layers scroll diagram
Grid / gallery 이미지 리듬과 탐색성 실험 GSAP, React, data array 콘텐츠와 레이아웃 분리 data → cards → transitions gallery contact sheet
100DaysOfUI 모션 패턴 수집 React, GSAP, Canvas, WebGL Day별 독립 실험 day component → shared utility Day archive
Figma/Jitter conversion 시안을 코드로 이식 JSON, TypeScript, GSAP layer/keyframe parser JSON → config → component JSON sample, layer map
Remotion 모션을 영상으로 렌더링 React, TypeScript, Remotion frame-based composition composition → sequence → render frame capture, render log
Lyrics MV 오디오·가사·화면 조율 MIDI, SRT, GSAP, WebGL event data를 scene trigger로 사용 audio → events → scenes → frames beat map, MV storyboard
Personalised video 데이터에 따른 영상 변형 Remotion, schema, API props와 schema로 콘텐츠 주입 data → template → render schema, template map

14. 무엇을 자동화하고 무엇을 사람이 해야 하는가

광고 배너부터 Remotion까지 작업 범위가 커질수록 자동화에 대한 질문도 반복되었다. 모든 것을 코드로 만들면 더 빠를 것 같지만, 실제 창작에서는 그렇지 않다.

자동화하기 좋은 것

  • 반복되는 프레임 계산
  • 에셋 파일명과 경로 매핑
  • 동일한 easing과 duration 적용
  • 여러 사이즈의 배너 생성
  • 데이터에 따른 텍스트·이미지 교체
  • SRT·MIDI·CSV 파싱
  • 렌더링과 결과 파일 생성
  • 기본적인 품질 검사와 메타데이터 기록

사람이 해야 하는 것

  • 어떤 장면이 필요한지 판단하기
  • 무엇을 강조하고 무엇을 덜어낼지 결정하기
  • 모션이 브랜드와 콘텐츠에 맞는지 평가하기
  • 클라이언트의 모호한 요구를 해석하기
  • artifact와 부자연스러움을 귀와 눈으로 확인하기
  • “더 화려하게”가 실제로 필요한지 거부하기
Human intent
    ↓ define
Schema / props / motion rules
    ↓ automate
Repeatable rendering
    ↓ review
Human judgement
    ↓ refine
Final output

코드는 창의성을 대신하지 않는다. 반복 가능한 구조를 제공하고, 내가 판단해야 하는 지점을 더 선명하게 만든다.


15. 가장 오래 남은 교훈

1. 고정된 크기는 제약이 아니라 설계 기준이다

배너의 작은 viewport와 파일 용량 제한은 모션의 우선순위를 명확하게 했다. 모든 것을 보여줄 수 없기 때문에 무엇이 중요한지 결정해야 했다.

2. 타임라인은 디자인 문서이기도 하다

timeline은 실행 코드인 동시에 장면의 우선순위와 관계를 설명하는 문서다. 잘 정리된 timeline은 클라이언트 피드백과 디버깅에도 도움이 된다.

3. 화려함보다 읽히는 속도가 먼저다

광고든 랜딩 페이지든 Lyrics MV든, 모션이 콘텐츠의 전달을 방해하면 실패다. 효과는 메시지의 계층과 리듬을 지원할 때 의미가 있다.

4. 스프라이트 시트에서 배운 것은 자산 관리였다

이미지를 하나씩 배치하는 일보다, 반복되는 자산을 규칙으로 묶는 일이 더 중요했다. 이 감각이 나중에 props, schema, token, scene config로 이어졌다.

5. 환경이 바뀌면 시간 모델도 바뀐다

배너는 짧은 loop, 웹은 scroll progress, WebGL은 render time, Remotion은 frame, Lyrics MV는 audio event가 시간의 기준이다. 같은 GSAP을 사용하더라도 기준 시간을 먼저 정의해야 한다.

6. 실패한 프로젝트가 다음 아키텍처의 문서가 된다

중복 timeline, 잘못된 초기 상태, 이미지 로딩 전 trigger 계산, React rerender, 모바일 viewport, Figma JSON의 레이어 문제는 모두 다음 시스템에서 피해야 할 조건으로 남았다.


에필로그: GSAP은 끝난 기술이 아니라 번역기였다

2018–2019년에 내가 만들던 것은 작은 HTML5 배너였다. 포토샵 스토리보드를 받고, 이미지를 스프라이트 시트로 묶고, 고정된 창 안에서 GSAP timeline을 조정했다. 그때는 이것이 나중에 랜딩 페이지, 100DaysOfUI, WebGL, Remotion, Lyrics MV까지 이어질 것이라고 생각하지 못했다.

하지만 구조는 계속 반복되었다.

의도된 화면
    ↓
움직이는 요소의 목록
    ↓
시간과 순서
    ↓
플랫폼 제약
    ↓
실행 가능한 컴포넌트
    ↓
검수와 반복

광고에서는 이 구조가 브랜드 메시지와 CTA를 전달했고, 웹에서는 스크롤과 인터랙션을 만들었고, 100DaysOfUI에서는 모션 패턴을 수집하게 했고, Remotion에서는 프레임 기반 영상으로 확장되었다. Lyrics MV에서는 오디오와 서사를 화면의 시간축으로 번역했다.

GSAP의 무한한 활용성은 효과의 종류가 무한하다는 뜻만은 아니다. 같은 시간 기반 사고가 서로 다른 창작 매체에서 계속 다시 쓰일 수 있다는 뜻이다.

나는 앞으로도 아마 스토리보드와 코드를 번역하는 일을 계속할 것이다. 고정된 배너 창이든, 반응형 랜딩 페이지든, WebGL 캔버스든, Remotion의 영상 프레임이든 결국 내가 다루는 것은 하나다.

디자인 의도를 시간과 구조로 번역하고, 그 구조를 다시 사람이 경험할 수 있는 움직임으로 만드는 일.

Related Articles