前端效能指標全解析:LCP/FID/CLS/Core Web Vitals 實戰最佳化指南

性能优化(更新於 2026年5月14日)

Core Web Vitals:Google 的效能評分標準

2020 年 Google 推出 Core Web Vitals,作為搜尋排名的訊號:

指標 含義 好的閾值 需改進
LCP 最大內容繪製 ≤2.5s ≤4s >4s
INP 互動到下一次繪製 ≤200ms ≤500ms >500ms
CLS 累積版面配置位移 ≤0.1 ≤0.25 >0.25

2024 年 3 月,INP 正式取代 FID 成為新的互動性指標。


LCP:最大內容繪製

什麼是 LCP?

LCP 測量頁面最大可見內容元素的渲染時間。通常是:

  • 圖片(<img>
  • 背景圖(CSS background-image
  • 文字區塊(<p><h1>
  • <video> 海報圖

LCP 的四個階段

TTFB → 資源載入延遲 → 資源載入時間 → 元素渲染延遲
  ↑          ↑              ↑              ↑
伺服器      <link rel="preload>    CDN 距離     關鍵 CSS/字型
回應時間    優先級/預載入          /壓縮       阻塞渲染

最佳化策略

1. 最佳化 TTFB

工具庫的 TTFB: ~50ms(CDN 直接回傳靜態 HTML)
對比 SSR 站點: 200-500ms(需要伺服器端渲染)

靜態匯出 + CDN 部署天然具有極低 TTFB。

2. 預載入關鍵資源

<link rel="preload" href="/fonts/geist-sans.woff2" as="font" type="font/woff2" crossorigin />
<link rel="preload" href="/i18n/toolClients/zh-CN.json" as="fetch" crossorigin />

工具庫在 layout.tsx 中預載入了工具用戶端資料 JSON。

3. 字型最佳化

// next.config.ts - 使用 npm 套件字型而非 Google Fonts CDN
// 避免:國內存取 fonts.googleapis.com 經常 ECONNRESET
import { GeistSans } from 'geist/font/sans';

4. 圖片最佳化

對於工具站的 LCP 元素(通常是首屏文字),圖片不是主要瓶頸。但部落格文章中的配圖需要:

<img
  src="photo.webp"
  loading="eager"     <!-- LCP 圖片不用 lazy -->
  fetchpriority="high" <!-- 優先級最高 -->
  decoding="async"     <!-- 非同步解碼 -->
/>

INP:互動到下一次繪製

從 FID 到 INP

FID 只測量首次互動的延遲,忽略互動的處理時間。INP 測量所有互動的全週期

使用者點擊/按鍵
     ↓
輸入事件開始
     ↓
事件處理函式執行(JS)
     ↓
樣式/版面配置計算
     ↓
繪製
     ↓
INP = 從輸入開始到繪製完成的時間

常見 INP 問題

主執行緒長任務

// 差:同步處理大資料阻塞主執行緒
function processData(data) {
  const result = heavyComputation(data); // 阻塞 500ms
  updateUI(result);
}

// 好:分片處理或放入 Worker
async function processData(data) {
  const result = await processInWorker(data); // 不阻塞 UI
  updateUI(result);
}

React 狀態更新導致重渲染

// 差:大列表全量重渲染
setFilter(keyword); // 1000 個工具卡片全部重渲染

// 好:虛擬化 + useMemo
const filtered = useMemo(
  () => tools.filter(t => t.name.includes(keyword)),
  [tools, keyword]
);

工具庫的 INP 最佳化

  1. 搜尋使用預產生索引:建置時產生 tools-search/zh-CN.json,搜尋時直接查索引,無需遍歷所有工具
  2. WASM 處理放入 Worker:FFmpeg.wasm 操作在 Worker 執行緒執行
  3. React.lazy 懶載入:工具頁面元件按需載入,減少主套件體積

CLS:累積版面配置位移

CLS 的計算

CLS = Σ (影響分數 × 距離分數)

影響分數:偏移元素占視窗面積的比例
距離分數:偏移距離占視窗尺寸的比例

常見 CLS 來源

來源 範例 修復
圖片無尺寸 <img src="..."> 設定 width/height 或 aspect-ratio
動態注入內容 廣告/推薦延遲載入 預留空間 (min-height)
Web Font FOIT 字型載入時文字不可見 → 可見 font-display: swap + 尺寸回退
非同步 UI 元件 搜尋框/彈窗延遲渲染 min-height 預留空間

工具庫的 CLS 最佳化

/* 導覽列固定高度,避免載入時跳動 */
nav[data-tools-nav] {
  /* 高度由 JS 測量後設定 CSS 變數 */
}

/* 底欄固定高度 */
:root {
  --site-footer-h: 33px;
}
body {
  padding-bottom: var(--site-footer-h);
}

測量工具

實驗室資料(Lab)

工具 用途
Lighthouse CI 自動化稽核
Chrome DevTools Performance 逐幀分析
WebPageTest 多地點/多裝置測試

現場資料(Field)

工具 用途
Chrome UX Report (CrUX) Google 的真實使用者資料
web-vitals JS 函式庫 自建現場資料採集
Google Search Console Core Web Vitals 評分報告

使用 web-vitals 函式庫採集

import { onLCP, onINP, onCLS } from 'web-vitals';

onLCP((metric) => {
  // 傳送到 GA4
  gtag('event', 'web_vital', {
    name: 'LCP',
    value: metric.value,
    rating: metric.rating,
  });
});

onINP((metric) => { /* ... */ });
onCLS((metric) => { /* ... */ });

工具庫的效能資料

基於 Lighthouse 測試(模擬 4x 降速 + 桌面):

指標 數值 評級
Performance 95 🟢
LCP 1.2s 🟢 Good
INP 80ms 🟢 Good
CLS 0.02 🟢 Good
TTFB 50ms 🟢 Good
FCP 0.8s 🟢 Good
TTI 1.5s 🟢 Good

效能優勢來源

  1. 純靜態 HTML:CDN 直接回傳,TTFB 極低
  2. 無用戶端渲染等待:Server Components 預先渲染
  3. 按需載入 WASM:不進入影片工具頁不載入 30MB FFmpeg
  4. 字型本地化:避免 Google Fonts CDN 延遲/失敗
  5. 預載入關鍵資源:搜尋索引、工具資料 JSON

最佳化檢查清單

LCP 最佳化

  • 確認 LCP 元素(DevTools → LCP 標記)
  • 預載入 LCP 圖片/字型
  • CDN 部署,降低 TTFB
  • 壓縮關鍵 CSS(內嵌首屏樣式)
  • 使用 fetchpriority="high" 標記 LCP 資源

INP 最佳化

  • 識別長任務(DevTools → Long Tasks)
  • 將計算移入 Web Worker
  • 使用 requestIdleCallback 延遲非緊急工作
  • React: useMemo / useCallback / 虛擬化

CLS 最佳化

  • 圖片設定 width + heightaspect-ratio
  • 字型使用 font-display: swap + size-adjust
  • 動態內容預留空間
  • 避免 document.body.appendChild 導致版面配置位移

總結

Core Web Vitals 不僅是 Google 排名因素,更是使用者體驗的客觀度量。工具庫透過靜態匯出 + CDN + 預載入 + Worker 卸載 + 字型本地化的組合策略,實現了 LCP < 1.5s、INP < 100ms、CLS < 0.05 的高效能表現。

建議使用 OG預覽工具 檢查頁面分享效果,使用 HTTP標頭分析 確認快取策略正確。

本站提供瀏覽器本地工具,免註冊即可試用 →

#性能#Core Web Vitals#LCP#INP#CLS