描述性語法

在本單元中,您將瞭解如何讓瀏覽器選擇圖片,藉此決定要顯示的圖片。srcset 並不是在特定中斷點替換圖片來源的方法,也不是替換圖片來源。這些語法允許 能解決一個非常困難的問題,我們完全不必依賴 Google 瀏覽器,可以流暢地請求並顯示符合使用者瀏覽內容的圖片來源。 包括可視區域大小、顯示密度、使用者偏好設定、頻寬,以及各種其他因素。

這個問題往往不只是因為我們標記網路圖片而已,並非我們所想而已。 資訊

使用 x 描述密度

無論使用者的密度為何,採用固定寬度的 <img> 在任何瀏覽環境中都會有相同的可視區域數量 螢幕 - 其螢幕的實際像素數量。舉例來說,假設圖片的寬度為 400px,圖片幾乎佔據整個空間 整個瀏覽器可視區域 (包括第一代 Google Pixel 和更新款的 Pixel 6 Pro) 兩者都採用正規化的412px 「邏輯像素」寬可視區域

Pixel 6 Pro 的螢幕更清晰高,但 6 Pro 的實體解析度是 1440 × 3120 像素,而 Pixel 為 1080 × 1920 像素,也就是組成螢幕本身的硬體像素數量。

裝置的邏輯像素和實體像素之間的比率,就是該螢幕的裝置像素比例 (DPR)。DPR 為 計算方式是將裝置的實際螢幕解析度除以可視區域的 CSS 像素。

控制台視窗中顯示的 DPR 為 2。

因此,原版 Pixel 的 DPR 為 2.6,Pixel 6 Pro 的 DPR 為 3.5。

iPhone 4 是第一部 DPR 大於 1 的裝置,回報的裝置像素比例為 2—螢幕的實體解析度是 邏輯解析度加倍iPhone 4 之前的任何裝置的 DPR 為 1:一個實體像素的邏輯像素。

如果你在 DPR 為 2 的螢幕上查看 400px 寬幅圖片,每個邏輯像素都會以四維顯示 螢幕的實際像素:兩條水平和兩個垂直像素。高密度螢幕無法呈現圖片,因為 與 DPR 為 1 的螢幕一樣相同。當然,任何「繪製」項目瀏覽器轉譯引擎,包括文字、CSS 形狀或 SVG 例如繪製在高密度螢幕中。不過,如同您從圖片格式和壓縮學到的,光柵圖片已修正 像素格狀檢視畫面雖然您未必會顯而易見,但為了配合高密度螢幕而調大的光柵圖片,畫面看起來會很明顯 但解析度卻很低

為避免這種縮放情形,顯示的圖片必須具有至少 800 像素的內建寬度。縮小時 在版面配置為 400 邏輯像素寬的版面配置中,這個 800 像素的圖片來源的像素密度是兩倍,在 DPR 為 2 的螢幕上, 圖片會很清晰

花瓣粉顯示密度差異的特寫照。

由於 DPR 為 1 的螢幕無法使用放大的圖片密度,因此系統會將圖片縮小以符合 顯示,「縮小」的圖片看起來沒有問題,適用於低密度螢幕,其中圖片適用於高密度螢幕 看起來就像任何其他低密度的圖片。

如同「圖片與效能」一文所述,低密度螢幕使用者查看圖片來源時,將圖片縮小為 400px 只需要需要相同寬度為 400px 的來源。雖然一張較大的圖片能讓所有使用者都能輕鬆瀏覽 在小型、低密度螢幕上顯示的高解析度圖片來源,將外觀和其他小型、低密度的圖片一樣,但速度較慢。

猜猜看, DPR 為 1 的行動裝置裝置很少。 但還是在電腦上的瀏覽情境:根據資料 由 Matt Hobbs 分享,截至 2022 年 11 月,在 GOV.UK 瀏覽工作階段中,約有 18% 的 DPR 為 1。雖然高密度圖片的「樣式」符合使用者的預期,但需要較高的頻寬和處理費用, 尤其是舊型和效能較差的裝置,仍可能出現低密度螢幕。

使用 srcset 可確保只有高解析度螢幕裝置接收的圖片來源夠大,可以清晰顯示,同時又不會傳遞相同的影像 減少頻寬成本。

srcset 屬性代表一或多個以半形逗號分隔的「候選項目」,用於算繪圖片。每位候選人 兩件事:一個網址,就跟在 src 中使用的一樣,以及用於「說明」圖片來源的語法。每位srcset候選人 以其固有的「寬度」(「w 語法」) 或預期「密度」(「x 語法」) 描述。

x 語法是「此來源適合具有此密度的螢幕」的簡寫,也就是後面的 2x 是 則適合 DPR 為 2 的螢幕。

<img src="low-density.jpg" srcset="double-density.jpg 2x" alt="...">

支援 srcset 的瀏覽器會顯示兩個候選項目:double-density.jpg,其中 2x 說明的性質適合適當。 表示 DPR 為 2 且 src 屬性中的 low-density.jpg 的螢幕;如果沒有其他適合的選項,就會選擇候選 在「srcset」中找到。如果是不支援 srcset 的瀏覽器,系統會忽略該屬性及其內容,也就是 src 的內容 按照慣例收到要求

很容易出錯 srcset 屬性中指定的值,以獲取操作說明。2x 會通知瀏覽器 關聯的來源檔案適用於 DPR 為 2 的顯示器 (來源本身相關資訊)。完全無從得知 瀏覽器應該使用這個來源,只告知瀏覽器如何使用來源。這是兩個細微卻重要的區別: 是雙密度「image」,而非用於雙密度「螢幕」的圖片。

說明「這個來源適合用於 2x 顯示」的語法以及顯示「在 2x 上使用這個來源」 顯示密度只是紙本內容,但顯示密度只是瀏覽器用來決定候選廣告的眾多相互關聯因素之一。 ,但其中只有其中幾個可以轉譯舉例來說,您可以個別判斷使用者是否啟用了 透過 prefers-reduced-data 媒體查詢讓瀏覽器偏好節省頻寬,並能隨時選擇是否向使用者顯示低密度圖片。 與每個開發人員的網站顯示頻率不盡相同。 除非開發人員針對每個網站採用一致的方式導入,才能為使用者帶來什麼好處。 因此,他們可能在某個網站上看到比較尊重自己的偏好,然後在下次瀏覽圖片時看到放大頻寬。

如果 srcset/sizes 使用的資源選取演算法不明確,會留下空間供瀏覽器決定選取較低密度 為盡可能減少資料用量,或基於偏好減少資料用量, 選擇門檻瀏覽器性能更完善地處理責任與工作也毫無意義。

使用 w 說明寬度

srcset 接受適合圖片來源的第二種描述元。它的功能比以前更強大 但就本而言, 非常容易瞭解與其針對特定顯示密度的候選文字標記為適當尺寸, w 語法說明每個候選來源的固有寬度。再次提醒,每個候選項目都是相同的維度儲存,也就是相同的 相同的裁剪和顯示比例但在這種情況下,您希望使用者的瀏覽器從兩種候選清單中選擇: small.jpg 這個來源的寬度為 600px,而大於 1200px 的來源。

srcset="small.jpg 600w, large.jpg 1200w"

這並無法告訴瀏覽器該如何處理這些資訊,只是提供圖片的候選清單。 您必須先提供以下資訊,讓瀏覽器決定要轉譯哪個來源: 說明圖片在網頁上的顯示方式。方法是使用 sizes 屬性。

說明 sizes 的使用狀況

瀏覽器在傳送圖片方面效能非常出色。我們會長時間發出圖片素材資源請求 才能載入樣式表或 JavaScript 要求,而這通常是在系統完整剖析標記之前。瀏覽器 發出這些要求,但除了標記以外,沒有網頁本身的資訊,甚至可能沒有已發出要求 導入外部樣式表,請再自行套用。瀏覽器剖析標記並開始外部 其中只有瀏覽器層級的資訊,包括使用者可視區域的大小、螢幕的像素密度、 使用者偏好設定等等

這並非圖片呈現在網頁版面配置中的顯示方式,甚至無法使用可視區域。 做為 img 大小上限的 Proxy,因為它可能會佔用水平捲動容器。因此我們必須 將這些資訊提供給瀏覽器,並使用標記完成。這就是我們可用於這些要求的所有資訊。

srcset 一樣,sizes 是用來在剖析標記後,立即提供圖片相關資訊。和 srcset 一樣 屬性是「這裡是來源檔案及其固有大小」sizes 屬性是「此處」的簡寫 就是版面配置中算繪的圖片大小。描述圖片的方式與可視區域相關,同樣是可視區域 大小是發出圖片要求時,瀏覽器唯一可用的版面配置資訊。

這可能會聽起來有點複雜,但在實務上較為簡單:

<img
 sizes="80vw"
 srcset="small.jpg 600w, medium.jpg 1200w, large.jpg 2000w"
 src="fallback.jpg"
 alt="...">

此處的 sizes 值會通知瀏覽器,img 版面配置中的空間寬度為 80vw - 80% 檢視區域提醒您,這並非操作步驟,而是反映圖片在網頁版面配置中的尺寸說明。這裡並未說 佔可視區域 80% 的面積」但「當網頁轉譯完畢後,這張圖片就會佔據 80% 的可視區域」。

身為開發人員,您的工作完成了,您已正確說明 srcset 中的候選來源清單及圖片寬度 在 sizes 中,而如同 srcset 中的 x 語法,其他部分則是由瀏覽器決定。

不過,為了充分瞭解這些資訊的使用方式,請花點時間瞭解各項資訊的決策 使用者的瀏覽器發現下列標記時:

您已告知瀏覽器此圖片佔用 80% 的可用可視區域,所以如果我們在 img 上顯示該圖片 裝置寬度為 1000 像素的可視區域時,這個圖片將佔用 800 像素。瀏覽器就會取得這個值 這個函式的寬度,是我們在 srcset 中指定的每個圖片來源候選圖片的寬度。最小來源的固有大小為 600 像素 例如:600÷800=.75。我們的中型圖片寬度為 1200 像素:1200÷800=1.5。我們最大的圖片寬度為 2000 像素:2000÷800=2.5。

這些計算結果 (.751.52.5) 是有效且有效的 DPR 選項,根據使用者的 可視區域大小。由於瀏覽器本身也能掌握使用者的顯示密度資訊,因此做出了一系列決定:

在此可視區域大小中,無論使用者的螢幕密度為何,系統都會捨棄 small.jpg 候選,而且計算出的 DPR 較低 與 1 相比,這個來源需要為所有使用者擴充資源,因此這個來源並不適當。在 DPR 為 1 的裝置上,medium.jpg 會提供 最接近 - 該來源適合以 1.5 的 DPR 顯示,因此比必要稍大。但請注意,縮減資源大小是 可以透過流暢的工作流程在 DPR 為 2 的裝置上,large.jpg 是最相符的結果,因此系統會選取該值。

如果同一張圖片在 600 像素寬的可視區域中顯示,則所有數學的結果都會完全不同:80vw 現已變成 480 像素。 當我們劃分來源針對此寬度,我們可以取得 1.252.54.1666666667。套用這個可視區域大小時,系統會選擇 small.jpgmedium.jpg 會在 2 部裝置上配對。

這張圖片在所有瀏覽環境中看起來都一樣:我們所有的來源檔案都與尺寸完全相同。 每個元素都會因使用者的螢幕密度正常顯示。但是,而不是向每位使用者顯示 large.jpg 為了容納最大可視區域和密度最高的顯示方式,系統一律會向使用者提供最小的適當內容。 使用描述性語法而非詳細語法,您就不必手動設定中斷點,同時考量未來的可視區域, DPR:您只要提供資訊給瀏覽器,並讓瀏覽器判斷答案即可。

由於 sizes 值與可視區域有關,且與網頁版面配置完全無關,因此會加上小工具層。 圖片很少佔據一定百分比的可視區域,而且沒有任何固定寬度的邊界、邊框間距或影響 從頁面上其他元素中消失您需要使用單位組合來表示圖片的寬度;%、empx

好消息是,您可以在這裡使用 calc()。任何內建支援回應式圖片的瀏覽器,也都支援 calc(),讓我們可以: 混搭的 CSS 單位,例如:佔據使用者可視區域完整寬度的圖片,減去兩側的 1em 邊界:

<img
    sizes="calc(100vw-2em)"
    srcset="small.jpg 400w, medium.jpg 800w, large.jpg 1600w, x-large.jpg 2400w"
    src="fallback.jpg"
    alt="...">

說明中斷點

如果您已經花太多時間使用回應式版面配置,很可能會發現這些例子中缺少某些元素: 版面配置中圖片佔用的空間很可能會在版面配置的中斷點時變動。在此情況下, 以便向瀏覽器傳送更多詳細資料:sizes 接受一組以半形逗號分隔的候選項目,做為轉譯大小的 圖片,就像 srcset 可接受以半形逗號分隔的圖片來源候選項目。這些條件使用熟悉的媒體查詢語法。 系統會先比對這個語法:只要符合媒體條件,瀏覽器就會停止剖析 sizes 屬性,並停止剖析該值 會發生什麼事

假設您的圖片是用於佔據 80% 的可視區域,而且在可視區域超過 1200 像素的可視區域上,該圖片兩側加上一個 em 的邊框間距 較小的可視區域會佔滿可視區域的全寬度

  <img
     sizes="(min-width: 1200px) calc(80vw - 2em), 100vw"
     srcset="small.jpg 600w, medium.jpg 1200w, large.jpg 2000w"
     src="fallback.jpg"
     alt="...">

如果使用者的可視區域大於 1200 像素,calc(80vw - 2em) 會說明版面配置中的圖片寬度。如果 (min-width: 1200px) 條件「不」相符,瀏覽器就會移至下一個值。由於 與這個值相關的媒體條件時,系統會使用 100vw 做為預設值。如果您要使用 sizes 寫入這個 屬性 max-width 媒體查詢:

  <img
     sizes="(max-width: 1200px) 100vw, calc(80vw - 2em)"
     srcset="small.jpg 600w, medium.jpg 1200w, large.jpg 2000w"
     src="fallback.jpg"
     alt="...">

淺顯易懂的文字:「(max-width: 1200px)」達成比對嗎?如果問題仍未解決,請繼續進行其他步驟。下一個值 (calc(80vw - 2em)) 沒有合格條件, 也就是已選取的

現在,您已向瀏覽器提供 img 元素的所有相關資訊,包括可能來源、固有寬度、 以及您想要如何呈現圖片 — 瀏覽器採用了一套模糊規則來決定如何處理 這些資訊如果聽起來不清楚,就是為了設計問題。來源選取演算法採用 HTML 規格明確無法判斷應如何選擇來源。來源、描述元及其描述元 圖片算繪完成後,瀏覽器就可以自由做任何想做的事,也就是說,您「無法」判斷哪些圖片 瀏覽器選擇的來源

「在高解析度螢幕上顯示這個來源」的語法這雖然是可預測的,但無法解決核心問題 圖片採用回應式版面配置:節省使用者頻寬。螢幕的像素密度只會與網際網路相關 連線速度。如果您使用的是高階筆電,但透過計量付費連線瀏覽網路,可以共用網路共用 或者使用飛航模式的 Wi-Fi 連線不穩,因此建議您停用高解析度圖片來源。 螢幕品質

與瀏覽器做出最終訊息相較,效能大幅提升,我們透過嚴格規定 語法。舉例來說:在大多數瀏覽器中,使用 srcsetsizes 語法的 img 絕對不會要求尺寸較小的來源 大於使用者瀏覽器快取中的現有尺寸向來源提出新要求時的時間點 看起來會完全相同,是否能順暢縮減已取得的圖片來源?但如果使用者將應用程式 直到可視區域為止,為了避免放大圖片而必須建立新圖片,「該」要求仍會發出,因此系統會傳送所有內容 讓您目不轉睛

若缺乏明確控制權限,可能會讓您感覺有點不安,但因為使用的是完全相同的來源檔案 這就不太可能以「毀損」的方式向使用者呈現可以提升使用者對單一來源的src體驗,無論 做出決策

正在使用 sizessrcset

無論是您、讀者還是瀏覽器,這裡都能提供豐富的資訊。srcsetsizes 都是稠密語法, 簡單介紹一些駭人聽聞的資訊也就是較好或更糟的,設計方式是: 這些語法不僅較不容易,使用者更容易剖析,也使得瀏覽器更難以剖析。 字串加入的複雜性越高,表示剖析器錯誤或行為發生意外差異的可能性就越大 在不同瀏覽器之間來回切換這裡還有一個不行,但機器更容易理解的語法比較容易寫出 。

srcset」是明確的自動化做法。您很少可以為 正式環境,而是要透過 Gulp 等工作執行器自動處理相關程序;Gulp 是第三方廠商 Webpack 等工具組 如同 Cloudinary,或是所選 CMS 內建的功能掌握足夠的資訊來產生來源 第一,系統可能會獲得足夠的資訊,以便將這些資訊寫入可用的 srcset 屬性中。

sizes 的自動化難度較高。如您所知,系統在計算 轉譯版面配置是為了「轉譯」版面配置。幸好,我們提供了多種開發人員工具, 手動輸入 sizes 屬性的程序,以及手動比對效率。 舉例來說,respImageLint 是檢查 sizes 屬性的程式碼片段 。Lazysizes 專案入侵 將圖片要求延遲到版面配置建立完成,讓 JavaScript 可以 並為您產生 sizes 值如果使用 React 或 Vue 等完整的用戶端轉譯架構, 編寫和/或產生 srcsetsizes 屬性的解決方案數量,我們會在 CMS 和架構中進一步討論。