偏好減少動態:有時候,動作越少

「優先減少動作」媒體查詢可偵測使用者是否要求作業系統盡量減少使用的動畫或動作量。

並非所有人都喜歡裝飾動畫或轉場效果,也有些使用者遇到視差捲動、縮放效果等問題時,可能會有動感不安的情況。使用者偏好媒體查詢 prefers-reduced-motion 可讓您針對提出這項偏好設定的使用者,設計網站的動態縮減變化版本。

瀏覽器支援

  • 74
  • 79
  • 63
  • 10.1

資料來源

現實生活中和網路上的動態內容過多

我前幾天要和孩子溜冰,是很可愛的一天,太陽因此發出閃耀,溜冰場也被人死了 ⛸。唯一的問題是:我不太能接受人群的擁擠。由於移動的目標很多,所以我根本無法專注於任何事情,最終會失去畫面並感覺到完全沈浸式的視覺效果,幾乎就像在安靜的山丘上追星 🐜?。

一群英尺的溜冰人。
現實生活中的影像超載。

網路上偶爾也有同樣的情況,例如閃爍廣告、有趣的視差效果、驚喜動畫、自動播放影片等,網頁有時可能會讓人不知從何著手...CSS 媒體查詢 prefers-reduced-motion 可讓開發人員為偏好動作較少的使用者建立網頁的變化版本。例如不要自動播放影片、停用某些純粹的裝飾效果,或是針對特定使用者全面重新設計頁面。

在深入介紹這項功能前,讓我們先回顧一下網站使用的動畫。如有需要,您也可以略過背景資訊,並直接查看下方的技術詳細資料

網頁動畫

動畫通常是用來向使用者提供意見回饋,例如,讓使用者知道已收到動作並且正在處理動作。舉例來說,在購物網站上,產品可能是以動畫形式「飛到」虛擬購物車,在網站右上角以圖示呈現。

另一個應用實例包括結合使用骨架畫面、關聯中繼資料和低畫質圖片預覽,利用動態效果來入侵使用者感知,佔據使用者大量時間,並更快速提供完整體驗。這個概念的用意是讓使用者瞭解接下來將哪些內容,並盡快載入內容。

最後,還有「裝飾」效果,例如動畫漸層、視差捲動、背景影片等。雖然許多使用者喜歡這類動畫,但有些使用者因感到分心或放慢而感到不滿。最糟的情況是,使用者甚至可能感到暈眩不適,就像實際體驗真實的體驗一樣,因此對這類使用者而言,減少動畫效果是必備的

動作觸發的樣子光譜失調

部分使用者可能會因為動畫內容受到影響或感到噁心。舉例來說,當與捲動相關的主要元素多處移動時,捲動動畫可能會引發觸動性失調。舉例來說,視差捲動動畫可能會造成肉眼失調,因為背景元素移動的速率與前景元素不同。身體 (內耳) 失調反應包括暈眩、噁心和偏頭頭痛,有時則需要休息才能恢復。

移除作業系統上的動態效果

許多作業系統都有無障礙設定,可用於指定長期的縮減動作偏好設定。下方螢幕截圖顯示 macOS Mojave 的「Reduce actions」偏好設定,以及 Android Pie 的「Remove animation」(移除動畫) 偏好設定。勾選時,這些偏好設定會導致作業系統不使用裝飾效果,例如應用程式啟動動畫。應用程式本身可以且應一併遵循這項設定,並移除所有不必要的動畫。

macOS 設定畫面的螢幕截圖,其中勾選「減少動態」核取方塊。
Android 設定畫面的螢幕截圖,其中勾選「移除動畫」核取方塊。

移除網路上的動態內容

媒體查詢層級 5 也會降低使用者對網路的偏好。無論轉譯文件為何,作者都能測試及查詢使用者代理程式或顯示裝置的值或功能。媒體查詢 prefers-reduced-motion 可用來偵測使用者是否設定了作業系統偏好設定,以盡可能減少使用的動畫或動作量。這可以是兩個可能的值:

  • no-preference:表示使用者在基礎作業系統中並未偏好設定。在布林環境中,這個關鍵字值評估為 false
  • reduce:表示使用者已設定作業系統偏好設定,表示介面應盡可能減少移動或動畫,最好是移除所有非必要移動的時間點。

使用 CSS 和 JavaScript 結構定義的媒體查詢

與所有媒體查詢一樣,prefers-reduced-motion 可透過 CSS 內容和 JavaScript 內容檢查。

舉例來說,假設我有一個重要的註冊按鈕 我想讓使用者點選我可以定義一個引人注目的「震動」動畫,但作為網路公民,我只有能明確接受動畫的使用者播放動畫,而非任何其他使用者,例如選擇停用動畫的使用者,或者使用不瞭解媒體查詢的瀏覽器使用者。

/*
  If the user has expressed their preference for
  reduced motion, then don't use animations on buttons.
*/
@media (prefers-reduced-motion: reduce) {
  button {
    animation: none;
  }
}

/*
  If the browser understands the media query and the user
  explicitly hasn't set a preference, then use animations on buttons.
*/
@media (prefers-reduced-motion: no-preference) {
  button {
    /* `vibrate` keyframes are defined elsewhere */
    animation: vibrate 0.3s linear infinite both;
  }
}

為了說明如何搭配 JavaScript 使用 prefers-reduced-motion,讓我們想像一下,我使用 Web Animation API 定義了複雜的動畫。雖然使用者偏好設定變更時,瀏覽器會動態觸發 CSS 規則,但如果是 JavaScript 動畫,我就必須自行監聽變更,然後手動停止可能發生的傳輸中動畫 (如果使用者允許,則重新啟動):

const mediaQuery = window.matchMedia('(prefers-reduced-motion: reduce)');
mediaQuery.addEventListener('change', () => {
  console.log(mediaQuery.media, mediaQuery.matches);
  // Stop JavaScript-based animations.
});

請注意,實際媒體查詢的括號是必備條件:

錯誤做法
window.matchMedia('prefers-reduced-motion: reduce');
正確做法
window.matchMedia('(prefers-reduced-motion: reduce)');

處理來自 <picture> 結構定義的媒體查詢

有趣的用途是製作依附於 media 屬性的 AVIF、WebP 或 GIF 動畫。如果 (prefers-reduced-motion: no-preference) 評估為 true,建議顯示動畫版本,否則顯示靜態版本:

<picture>
  <!-- Animated versions. -->
  <source
    srcset="nyancat.avifs"
    type="image/avif"
    media="(prefers-reduced-motion: no-preference)"
  />
  <source
    srcset="nyancat.gif"
    type="image/gif"
    media="(prefers-reduced-motion: no-preference)"
  />
  <!-- Static versions. -->
  <img src="nyancat.png" alt="Nyan cat" width="250" height="250" />
</picture>

請參考以下範例。請嘗試切換裝置的動作偏好設定,看看有何差異。

彩虹貓

在要求時探索使用者的偏好設定

Sec-CH-Prefers-Reduced-Motion 用戶端提示標頭可讓網站選擇在要求時選擇性取得使用者的動作偏好設定,讓伺服器可以基於效能考量而內嵌正確的 CSS。

示範

我根據 Rogério Vicente 的驚奇 🐈? HTTP 狀態貓咪製作了一則示範影片。首先,花點時間聽講笑話 感覺特別有趣,我馬上就會等現在您已回來,我來介紹示範。當您向下捲動時,每個 HTTP 狀態貓會隨右側或左側顯示。這是一場流暢的 60 FPS 動畫,但如上所述,部分使用者可能會不喜歡,甚至感到動作不適,因此示範內容是以 prefers-reduced-motion 為基準。這甚至可以動態運作,因此使用者可以即時變更偏好設定,不需要重新載入。如果使用者偏好減少動作,不必要的顯示動畫會消失,只留下一般捲動動作。下方螢幕側錄展示實際運作情形:

prefers-reduced-motion 示範應用程式的影片

結論

現代網站關鍵在於尊重使用者偏好,瀏覽器為了協助網頁程式開發人員實現上述目標,瀏覽器提供了更多和更多功能。另一個已啟動的例子為 prefers-color-scheme,可以透過其偵測使用者偏好為淺色或深色的色彩配置。您可以在我的「Hello Darkness, My Old Friend」文章中閱讀有關 prefers-color-scheme 的所有資訊 🌒?。

CSS Working Group 目前正在將更多使用者偏好媒體查詢標準化,例如 prefers-reduced-transparency (偵測使用者偏好降低透明度)、prefers-contrast (偵測使用者是否要求系統增加或減少相鄰顏色的對比度) 和 inverted-colors (偵測使用者偏好反轉顏色)。

(獎勵) 強制要求所有網站減少運動

並非所有網站都會使用 prefers-reduced-motion,或可能不太符合你的口味。 如果您基於任何原因想要停止在所有網站上執行動作,當然可以。其中一個方法是在您造訪的每個網頁中,插入具有以下 CSS 的樣式表。市面上有許多瀏覽器擴充功能 (需自行承擔使用風險!),才能達到這個效果。

@media (prefers-reduced-motion: reduce) {
  *,
  ::before,
  ::after {
    animation-delay: -1ms !important;
    animation-duration: 1ms !important;
    animation-iteration-count: 1 !important;
    background-attachment: initial !important;
    scroll-behavior: auto !important;
    transition-duration: 1ms !important;
    transition-delay: 1ms !important;
  }
}

這個做法的運作原理是,上述的 CSS 會覆寫所有動畫的時間長度,並轉到這段短時間內,這些動畫效果就不再那麼明顯。部分網站需要執行動畫才能正常運作 (原因可能是某些步驟取決於觸發 animationend 事件),因此較極端的 animation: none !important; 方法無法正常運作。即使是上述的入侵行動,也不保證在所有網站上都能成功 (例如,無法停止透過 Web Animations API 啟動的動作),因此當您發現這類攻擊毀損時,請務必停用。

特別銘謝

大力向 Stephen McGruer 致意,他們在 Chrome 中實作 prefers-reduced-motion,以及和 Rob Dodson 一起評論。主頁橫幅由 Hannah Cauhepe 在 Unsplash 上提供。