跳至主要內容

Responsive Design 斷點策略:打造真正適應各裝置的介面

Responsive Design 斷點策略:打造真正適應各裝置的介面

響應式設計(Responsive Design)已經是網頁開發的基本功,但「設幾個斷點」、「斷點要設在哪」這些問題卻常常讓人困惑。有人照搬框架的預設值,有人憑感覺設定,結果往往是在某些裝置上出現奇怪的顯示問題。這篇文章要從底層邏輯出發,帶你建立一套有根據的斷點策略。

斷點的本質

斷點不是「為了某種裝置而設」,而是「為了讓內容在特定寬度呈現最佳狀態而設」。

這個觀念的轉變很重要。如果你是因為「iPhone 是 375px,所以要設 375px 的斷點」,那你已經走偏了。裝置尺寸千變萬化,今天的主流裝置明天可能就過時了。正確的做法是:讓內容決定斷點

Mobile First vs Desktop First

在設計斷點策略之前,要先確定方向。

Mobile First(推薦)

/* 基礎樣式:手機 */
.container {
  padding: 1rem;
  flex-direction: column;
}

/* 平板以上 */
@media (min-width: 768px) {
  .container {
    padding: 2rem;
    flex-direction: row;
  }
}

/* 桌機以上 */
@media (min-width: 1200px) {
  .container {
    max-width: 1140px;
    margin: 0 auto;
  }
}

Desktop First

/* 基礎樣式:桌機 */
.container {
  max-width: 1140px;
  flex-direction: row;
}

/* 平板以下 */
@media (max-width: 1199px) {
  .container {
    padding: 2rem;
  }
}

/* 手機以下 */
@media (max-width: 767px) {
  .container {
    flex-direction: column;
    padding: 1rem;
  }
}

Mobile First 的優勢在於從最簡單的情境開始,逐步增加複雜度,效能也更好(手機不需要下載桌機版的樣式再覆蓋)。

常見斷點系統

Tailwind CSS 的斷點

// tailwind.config.js
module.exports = {
  theme: {
    screens: {
      'sm': '640px',   // 小型手機橫向 / 大型手機
      'md': '768px',   // 平板
      'lg': '1024px',  // 小型桌機 / 大型平板橫向
      'xl': '1280px',  // 桌機
      '2xl': '1536px', // 大型桌機
    }
  }
}

Bootstrap 的斷點

$grid-breakpoints: (
  xs: 0,      // 手機直向
  sm: 576px,  // 手機橫向
  md: 768px,  // 平板
  lg: 992px,  // 桌機
  xl: 1200px, // 大型桌機
  xxl: 1400px // 超大螢幕
);

以內容為導向的斷點策略

與其使用固定的斷點,不如根據實際內容調整:

/* 文章閱讀寬度:當行寬超過 70 字元時換版型 */
.article-content {
  width: 100%;
}

@media (min-width: 680px) {
  .article-content {
    max-width: 680px;
    margin: 0 auto;
    font-size: 1.125rem;
    line-height: 1.8;
  }
}

/* 卡片網格:讓卡片決定何時換行 */
.card-grid {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(280px, 1fr));
  gap: 1.5rem;
}
/* 這裡不需要任何斷點!Grid 會自動處理 */

使用 CSS 自訂屬性管理斷點

:root {
  --breakpoint-sm: 640px;
  --breakpoint-md: 768px;
  --breakpoint-lg: 1024px;
  --breakpoint-xl: 1280px;

  /* 間距比例 */
  --spacing-base: 1rem;
  --spacing-md: 1.5rem;
  --spacing-lg: 2rem;
}

/* 但注意:CSS 自訂屬性無法直接用在 @media 中 */
/* 需要搭配 Sass 或 CSS-in-JS */

Sass 斷點 Mixin

$breakpoints: (
  'sm': 640px,
  'md': 768px,
  'lg': 1024px,
  'xl': 1280px,
  '2xl': 1536px
);

@mixin respond-to($breakpoint) {
  @if map-has-key($breakpoints, $breakpoint) {
    @media (min-width: map-get($breakpoints, $breakpoint)) {
      @content;
    }
  } @else {
    @warn "找不到斷點 `#{$breakpoint}`。";
  }
}

// 使用方式
.hero-section {
  padding: 2rem 1rem;

  @include respond-to('md') {
    padding: 4rem 2rem;
  }

  @include respond-to('lg') {
    padding: 6rem 4rem;
  }
}

容器查詢(Container Queries)

CSS 容器查詢是現代響應式設計的重大突破,讓元件可以根據自身容器的大小而非視窗大小來調整樣式:

/* 定義容器 */
.card-wrapper {
  container-type: inline-size;
  container-name: card;
}

/* 根據容器寬度調整 */
@container card (min-width: 400px) {
  .card {
    display: flex;
    flex-direction: row;
  }

  .card-image {
    width: 40%;
    flex-shrink: 0;
  }
}

@container card (min-width: 600px) {
  .card {
    gap: 2rem;
  }
}

容器查詢的好處是元件真正做到自包含,不管放在哪個版面,都能根據自身可用空間做出最佳調整。

實際排版策略

導覽列

.navbar {
  display: flex;
  align-items: center;
  justify-content: space-between;
  padding: 1rem;
}

.nav-menu {
  display: none; /* 手機預設隱藏 */
}

.hamburger {
  display: block;
}

@media (min-width: 768px) {
  .nav-menu {
    display: flex;
    gap: 2rem;
  }

  .hamburger {
    display: none;
  }
}

兩欄版型

.content-layout {
  display: grid;
  gap: 2rem;
}

@media (min-width: 900px) {
  .content-layout {
    grid-template-columns: 1fr 320px;
  }
}

測試斷點的工具

  1. 瀏覽器開發者工具:Chrome/Firefox 的響應式模式可以自訂尺寸
  2. Responsively App:同時預覽多個尺寸
  3. Polypane:專業的響應式測試瀏覽器

常見錯誤

  1. 斷點太多:3-5 個主要斷點通常就夠了,不需要為每種裝置設一個
  2. 只測試預設尺寸:記得測試斷點之間的過渡區間
  3. 忽略橫向模式:手機橫向(landscape)是常被忽略的情境
  4. px 寫死:考慮使用 emrem 作為斷點單位,讓使用者的字體大小偏好也能影響版型
/* 使用 em 斷點(1em = 使用者的根字體大小,通常 16px) */
@media (min-width: 48em) {   /* 768px / 16 */
  /* 平板版型 */
}

@media (min-width: 64em) {   /* 1024px / 16 */
  /* 桌機版型 */
}

總結

好的斷點策略不是追著裝置跑,而是讓內容在任何寬度都能舒適呈現。採用 Mobile First 思維、以內容決定斷點、善用現代 CSS 特性如 Grid、Flexbox 和容器查詢,你的介面就能真正地「響應式」,而不只是在幾個特定寬度上看起來還行。

分享這篇文章