Communitygithub.com

Pryne 前端除錯手冊

當 Pryne 展示頁面出現行為異常時使用,例如動畫在區塊可視前觸發、顯現效果裁切錯誤、作業系統游標消失、WebGL 殘影或混色錯誤、滾輪編排失靈、所有動畫對某使用者失效、不同裝置滾動感受不一致、缺少懸停/動態效果、滾動卡頓或緩慢、音訊靜默,或任何主控台錯誤。涵蓋設計展示中的 vanilla-JS window.Roll 模組建構 (roll-*.js)。

Pryne 前端除錯手冊 是什麼?

此技能專為 Pryne 的 vanilla-JS 展示建構 (design-demos 目錄下的 v4-a 到 v4-d) 提供系統化除錯指引。這些單一 HTML 頁面由 window.Roll 模組核心 (design-demos/js/roll-*.js)、WebGL 顆粒著色器 (附 2D 備援)、單一 rAF 渲染循環、自行維護的 Lenis 平滑滾動,以及從 CDN 非同步載入的 GSAP (作為漸進增強) 驅動。技能提供從症狀到初步診斷的對照表,涵蓋動畫閘門控制、裁切路徑位置、游標消失、WebGL 上下文遺失、滾輪編排中斷、偏好減少動畫、滾動感受不一致、GSAP 載入失敗、音訊靜默及頁尾重疊等常見問題。它也包含識別用的實驗指令碼,並強調遵循先閱讀檔案頭部註解 (head comment) 與 systematic-debugging 規則的重要性,以避免對已記錄的修正或預期行為進行重複診斷。技能支援所有相關平台與工具,並明確指出何時不應使用它 (例如通用除錯、瀏覽器操作、架構決策等)。

相容平台✓Claude Code~Codex CLI✓Cursor
npx skills add https://github.com/prynetopg777/claude-skills-bundle/tree/HEAD/skills/pryne-frontend-debugging

在你喜歡的 AI 中提問

開啟一個已預先載入此 Agent Skill 的新對話。

說明文件

Pryne 前端除錯手冊 是做什麼的?

針對 Pryne 的 vanilla-JS 展示建構提供症狀→初步診斷:由 window.Roll 模組核心 (design-demos/js/roll-*.js) 驅動的單一 HTML 頁面,包含 WebGL 顆粒著色器 (附 2D 備援)、一個 rAF 渲染循環、自行維護的 Lenis 平滑滾動,以及從 CDN 非同步載入作為漸進增強的 GSAP。

必要背景: superpowers:systematic-debugging 擁有通用根本原因排查規則 (未經調查不得修復)。請遵循該規則;此技能僅提供專案特定的症狀對照表與常見陷阱。

工具: 關於如何驅動瀏覽器、擷取主控台、模擬減少動畫模式以及取得追蹤記錄,請使用 pryne-browser-lab。此技能假設您已能執行這些指令。

先讀取檔案頭部註解

每一個 v4 展示 (design-demos/ 中的 v4-a 至 v4-d) 在其檔案最頂端以 HTML 註解的形式攜帶稽核歷史紀錄 — 記錄了什麼被發現損壞、什麼已修復以及原因。此慣例於 2026-07-22 在所有四個檔案中驗證通過。在重新診斷任何問題之前,請對您正在除錯的展示執行 head -30。 您會發現許多「錯誤」實際上已記錄為已修復的回歸;如果某個問題再次出現,您要尋找的是導致其回滾的原因,而非一個新的根本原因。

另外請注意建構佈局 (截至 2026-07-22):僅 v4-d-hybrid.html 使用共用的 roll-*.js 模組。v4-a/b/c 是範圍縮小的比較建構,使用各自獨立的內嵌 JS — 此對照表中針對 Roll 的檢查不適用於它們,但相同的錯誤類別仍然適用。

零主控台錯誤是默認狀態

標準是零主控台錯誤 (design-demos/DECISIONS.md 中的 CRITIQUE 評分標準要求如此)。根據專案狀態日誌,v3 已驗證為零錯誤;v4 系列則在方向決策活動 (pryne-design-direction-decision) 完成前尚未認證。任何主控台錯誤都是需要處理的缺陷,絕非可以忽略的環境雜訊。

症狀 → 初步診斷對照表

症狀可能原因區分性檢查
動畫/開發面板在其區塊被滾動至可視區域前就執行(或完成)可視性閘門控制回歸。v4-d 的頭部註解記錄此為最高優先級的稽核修復:功能面板「從頁面載入時即無條件觸發,並在任何人滾動到它們之前就完成解析。」開發必須以面板的 .in 類別作為閘門控制。下方的實驗 1
顯現動畫裁切錯誤、跳動或從未觸發clip-path 被應用在 IntersectionObserver 所監聽的元素上,而非一個內層的包裝元素。概念 C 的修復(已帶入 v4-d,根據其頭部註解):clip-path 顯現效果位於內層包裝元素上,絕不在監聽的元素上。檢查元素:監聽的節點與套用裁剪的節點是否為同一個?
作業系統游標消失,且無自訂游標取代不應再次發生 — 已於 2026-07-22 修復(經冷測試稽核查出,同日修復):每個事件處理器 (roll-cursor.js:17-20) 及其 pointermove 呼叫點 (roll-core.js:26-29) 現在都會在原有設定時期的捕捉之外,額外進行捕捉與還原 (設定 null Roll.cursorUpdate,移除 .custom-cursor);#cur/#ring 的 z-index 從 50 提高至 70,高於 #flash (60),以使高潮脈衝無法覆蓋游標。如果症狀再次出現,表示其中一個防護措施發生回歸,或有新程式碼在此合約之外隱藏了游標。document.body.classList.contains('custom-cursor') 對比 Roll.cursorUpdate — true/null 同時存在是故障狀態;如果兩者看起來都正常,檢查 getComputedStyle(cur).opacity,以及是否僅在高潮閃光時消失
WebGL 殘影/軌跡,或顏色與頁面混合錯誤缺少逐影格清除 (per-frame clear),或預乘 alpha 設定不匹配 (premultiplied-alpha mismatch)。roll-shader.js 每影格呼叫 gl.clear(gl.COLOR_BUFFER_BIT),並以 { alpha: true, premultipliedAlpha: false } 建立 context (兩者皆為稽核修復,根據 v4-d 的頭部註解)。比對 roll-shader.js 與 git:git diff HEAD -- design-demos/js/roll-shader.js
著色器畫布空白,完全沒有顆粒效果(a) 減少動畫模式 — GL 故意永不初始化 (useGL = !Roll.reduced && setupGL());(b) WebGL context 遺失 — webglcontextlost 處理器將畫布透明度設為 0 並靜默失敗;(c) 在 WebGL 有機會前就已取得 2D context (每個畫布只能有一個 context — 於 roll-shader.js 頂部有文件說明)。優先檢查 Roll.reduced。針對 context 遺失,檢查處理器的可觀察效果:getComputedStyle(document.getElementById('tone')).opacity === '0'。注意:Roll.shader.useGL 是設定時的快照 (roll-shader.js:120-121) — webglcontextlost 處理器僅翻轉閉包變數 (roll-shader.js:130-132),因此 context 遺失後 Roll.shader.useGL 仍為 true;不要用它來排除 context 遺失的可能性
滾輪編排失靈,但頁面仍正常渲染與滾動腳本載入順序或 window.Roll 命名空間中斷。腳本順序至關重要 — 其鏈結與檢查指令位於 pryne-frontend-architecture。每個模組都是一個 IIFE,僅透過 window.Roll 共享狀態;早期模組中發生一個錯誤就會導致其後所有模組因無法執行而停止。下方的實驗 2;主控台會顯示 Roll.X is undefined,指出是哪個模組被影響而無法執行
單一使用者回報所有動畫失效,但在您的機器上正常他們啟用了 prefers-reduced-motion。這是正確行為,非錯誤:roll-core.js 從媒體查詢設定 Roll.reduced,且每個模組都以此為閘門 (封面移除、面板立即完成渲染、跳過 Lenis、關閉著色器)。請勿「修復」它。下方的實驗 3
觸控板/滑鼠滾輪/觸控的滾動感受不一致原始滾動 Delta 值變異 — 這是自行維護 Lenis 的記錄原因 (參見 design-demos/DECISIONS.md)。Lenis 包裝了原生滾動,因此 window.scrollY 仍然有效;它僅是感受上的升級,在減少動畫模式下為 null。typeof Lenis (是否已載入?),然後檢查展示是否在其滾動模組中建構了它
基礎功能正常,但缺少懸停/動態/游標效果GSAP CDN 載入失敗或被阻擋。GSAP 從 jsdelivr 非同步載入 (固定 SRI),並僅在成功載入後透過 Roll.upgradeMotion() 將 Roll.enhanced = true。漸進增強是設計使然:基礎編排仍必須在沒有 GSAP 的情況下正常運作。如果基礎功能也同樣損壞,則此非本次原因。下方的實驗 4
音訊靜默靜音是默認狀態:roll-audio.js 以靜音啟動,將選擇持久化儲存在 localStorage['ch001_muted'] 中,且僅在點擊 #mute-toggle (使用者手勢,滿足自動播放政策) 後才開始播放環境背景音。所有合成邏輯都已用 try/catch 包裹且無需資產檔案。在懷疑程式碼之前,請先檢查靜音切換按鈕的狀態。Roll.audio.muted,以及 localStorage.getItem('ch001_muted')
固定的 HUD 重疊/遮擋了頁尾頁尾淡出修復的回歸:一個監聽 footer 的 IntersectionObserver 在節拍計量器和靜音按鈕上切換 .faded 類別 (roll-scroll.js)。滾動到頁尾;檢查 #beatmeter 上是否出現了 .faded 類別

區分性實驗

在頁面主控台中或透過 evaluate_script (參見 pryne-browser-lab) 執行這些指令。每個指令能在您碰觸程式碼前回答一個問題。

1 — 面板開發是否正確地以可視性為閘門?

({ workVisible: document.getElementById('work').classList.contains('in'),
   plate1: { d: Roll.featurePlate.d, done: !!Roll.featurePlate.done },
   plate2: { d: Roll.featurePlate2.d, done: !!Roll.featurePlate2.done } })

在新載入後,滾動至工作區塊前:workVisible: false 且兩個 d 值應接近 0。如果 d 在上升 (或 done: true) 但 workVisible 為 false,則表示閘門控制發生回歸。

2 — Roll 核心是否完整?

({ core: !!window.Roll, reduced: Roll?.reduced, enhanced: Roll?.enhanced,
   shader: !!Roll?.shader, audio: !!Roll?.audio, plates: !!Roll?.plates,
   cursorUpdate: Roll?.cursorUpdate === null ? 'null' : typeof Roll?.cursorUpdate })

關於 cursorUpdate:它初始化為 null (roll-core.js:23),且在 GSAP 載入前以及非 pointer: fine 裝置上也是 null — 僅 null 本身不能證明任何事。「安全失敗」僅在 document.body.classList.contains('custom-cursor') 為 true 且 cursorUpdate 為 null 時才成立 (參見對照表中的游標行)。

任何 false/undefined 指出了未完成載入的模組 — 請檢查主控台中該模組拋出的錯誤,並檢查 HTML 中的腳本順序是否符合上述的載入順序。

3 — 「所有動畫失效」是否只是減少動畫模式?

({ mediaQuery: matchMedia('(prefers-reduced-motion: reduce)').matches, roll: Roll.reduced })

兩者皆 true → 符合設計;透過模擬減少動畫模式 (pryne-browser-lab) 重現使用者回報。mediaQuery: true 但 roll: false (或相反) → 某個模組讀取了錯誤的資訊來源。

4 — GSAP 增強層是否已載入?

({ gsapLoaded: !!window.gsap, enhanced: Roll.enhanced, reduced: Roll.reduced })

gsapLoaded: false → CDN 被阻擋或載入失敗 (檢查網路面板中對 jsdelivr 的請求;SRI 不符也會導致此情況)。gsapLoaded: true, enhanced: false, reduced: false → upgradeMotion() 未執行 — 檢查 <script> 標籤的 onload 鉤子。

耗費大量時間的常見陷阱

陷阱故事 (一句話)防護措施
「驗證正常」≠ 方向正確v3 NIGHT DRIVE 完全建構完成,零主控台錯誤,通過驗證 — 然後被取代,因為其統一概念是錯誤的 (完整說明:pryne-failure-archaeology)。不要花費打磨/除錯精力來維護一個尚未被確認是目前方向的建構。請先檢查 DECISIONS.md 和文件庫狀態。
重新診斷已記錄的修復每個 v4 的頭部註解都是已找到、已修復缺陷的變更紀錄。在開啟開發者工具前,請先讀取頭部註解。如果列表中的某個修復看似損壞,請尋找導致回滾的原因,而非症狀本身。
「修復」減少動畫模式所有動畫關閉是針對 prefers-reduced-motion 使用者的設計行為,由一個地方 (Roll.reduced) 進行閘門控制。在將零動畫回報視為缺陷前,請先執行實驗 3。
為了「測試某個東西」而取得 2D context一個畫布永遠只能擁有一種 context 類型;先取得 2D context 會導致該畫布從此無法使用 WebGL (於 roll-shader.js 中有文件說明)。在主控台實驗中,絕對不要在 #tone 上呼叫 getContext('2d')。

何時不應使用此技能

  • 通用除錯規則 (提出假設、最小變更、先找根本原因再修復) → superpowers:systematic-debugging。
  • 如何驅動瀏覽器/進行測量 (MCP 工具結構、追蹤記錄、Lighthouse、螢幕截圖) → pryne-browser-lab。
  • 判斷行為是否違反設計不變量 (減少動畫閘門控制、低語級別個性、自行維護) → pryne-frontend-architecture。
  • 關於某個東西為何被建構/回滾的完整歷史 → pryne-failure-archaeology。
  • 其他技術棧 (React/框架建構、非 Pryne 專案):上述對照表專屬於 window.Roll 展示系列;僅通用除錯規則可轉移。

來源與維護

執行 scripts/verify.sh (在此技能的目錄中) 以一次檢查以下所有項目。

資訊截至 2026-07-22,已在儲存庫 ~/Documents/Coding Folder/Portfolio (test) 的提交 457868a 中驗證。在信任前請重新驗證:

  • 模組列表與大小:wc -l design-demos/js/*.js
  • 腳本載入順序:grep -n "<script" design-demos/v4-d-hybrid.html
  • 哪些展示使用了共用模組:grep -l "roll-core.js" design-demos/*.html
  • 頭部註解慣例仍然有效:for f in design-demos/v4-*.html; do echo "== $f"; head -5 "$f"; done
  • 減少動畫閘門:grep -n "prefers-reduced-motion\|Roll.reduced" design-demos/js/*.js
  • 面板可視性閘門控制:grep -n "classList.contains('in')" design-demos/js/roll-scroll.js
  • Lenis 是否自行維護並正確連接:ls design-demos/js/vendor/ && grep -n "new Lenis" design-demos/js/roll-scroll.js
  • GSAP 增強鉤子:grep -n "upgradeMotion" design-demos/js/roll-core.js design-demos/v4-d-hybrid.html
  • 音訊靜音默認值與儲存鍵值:grep -n "ch001_muted" design-demos/js/roll-audio.js
  • 零主控台錯誤標準:grep -n "console errors" design-demos/DECISIONS.md

Individual skills in this repo

This repo contains 1 individual skill — each has its own dedicated page.

相關技能