UIUX 學習筆記

用 Three.js 砌一個由頭 scroll 到尾嘅 3D 黑膠唱片店 landing

2026年6月21日 · 3 分鐘閱讀
WAX & SOUL 嘅三幕(真實 render)。左:Hero 自轉;右:New Arrivals 抽碟同最後跌落唱盤。

我想試吓:可唔可以淨係靠 scroll,帶一條由頭到尾連續嘅 3D 動畫?唔係一格格獨立 section,而係成頁得一隻黑膠 ── 你一路 scroll,佢一路自轉、滑位、跌落唱盤。揀咗一間虛構黑膠店「WAX & SOUL」做題目,用 Three.js 程序生成黑膠、封套同木框唱盤,Lenis 做 smooth scroll。

👉 撳呢度睇 live 版面 ── 由頭 scroll 到尾就見到成條動畫。

一條 scroll = 一條動畫

傳統 landing 係一節節砌落去,每節各有 entrance 動畫。我今次想要嘅啱啱相反:一個鏡頭、一條時間線。scroll 嘅進度(由 0 到 1)本身就係條時間線 ── 我冇用任何 timeline library,直接攞 scrollTop / maxScroll 出個 0→1 嘅 p,再用幾條 eased segment(smoothstep)切開三幕,每一幀按 p lerp 返物件嘅位置、旋轉同鏡頭。冇 keyframe、冇 GSAP,純數學。

好處係:scroll 去到邊,畫面就一定喺嗰個狀態,前後都對得返 ── 要 debug 一個 scroll 動畫,可以直接 jump 去任何 p 睇結果。

三幕

幕一 · Hero — 一隻黑膠置中(略偏上)持續自轉,下面一行店名標語同 scroll ↓。睇落淨係一個自轉,但要靠程序生成嘅 groove(同心坑紋)同 label 反光去到位,先似真。

幕二 · New Arrivals — Hero 嗰隻黑膠唔係消失,係滑落去 New Arrivals 第一張專輯個位、自轉減速停 ── 同一隻碟由幕一帶到幕二,個敘事先連得埋。之後 scroll = 鏡頭橫掃 5 張唔同封面色嘅專輯,中央嗰張拉近放大、兩旁退後縮細;中央仲會兩段式抽碟出嚟(盒打斜、碟滑出、移前置中)。

幕三 · 唱盤 — 最後一張嘅黑膠打橫(rotation.x → -90°)向下跌,落正一個復古木框唱盤;鏡頭同時下傾,唱臂由右上擺到外緣 cue down,碟喺轉盤上自轉。結尾出「Find your sound.」同一個 Browse CTA。

學到嘅嘢

1. scroll 進度直接驅動,慳好多嘢。 唔使 timeline library、唔使管 play / pause / reverse ── 你倒返 scroll 上去,動畫自然倒返。狀態完全由 p 決定,冇 hidden state,所以唔會出現「scroll 太快 trigger 唔到」嗰類 bug。

2. 程序生成 3D 慳 asset 又靈活。 黑膠嘅坑紋、label、封面色、木紋全部用 canvas texture 即時畫,冇下載任何 3D model 或者貼圖。想換一張專輯色,改個 hex 就得 ── 五張碟其實係同一個 geometry 換色。

3. 一定要有 fallback。 WebGL 開唔到(舊機 / 關咗硬件加速)就收起 canvas,顯示一個純 CSS 嘅靜態黑膠 + 店名,唔會白屏。窄螢幕就按 aspect 將鏡頭推遠,等成隻碟 fit 得入。

4. Smooth 同 snap 之間好難搵平衡。 最初我用硬性 snap(一 flick 就鎖去下一幕),但 scroll 中途會被搶走、好唔順。改完做 Lenis 自由 smooth scroll + 停低先輕輕 snap 去最近嘅 anchor ── 你想慢慢睇中間過渡都得,放手先幫你對位。

總結

由一句「淨用 scroll 帶一條連續 3D 動畫」,到一隻黑膠由自轉、滑位、carousel、跌落唱盤播放 ── 最大嘅體會係:當你將動畫嘅時間線同 scroll 綁實,個體驗就由「睇緊一頁嘢」變成「揸住一個鏡頭」。 觀眾控制節奏,但每一格你都對到位。