picture
元素和srcset
、sizes
屬性納入HTML 5.1規(guī)范草案 。因為我們無法預(yù)測用戶在何地以及如何訪問我們的網(wǎng)站,所以我們需要瀏覽器自身根據(jù)情況選擇最好的圖像。新規(guī)范將解決以下問題:
- 基于設(shè)備象素比(device-pixel-radio)選擇
- 基于viewport選擇
- 基于Art direction(美術(shù)設(shè)計)選擇
- 基于圖像格式選擇
img
元素增加了兩個新屬性:srcset
和sizes。
srcset
用來聲明一組圖像源,瀏覽器根據(jù)我們使用描述符指定的條件來選擇圖像。描述符x
表示圖像的像素密度,描述符w
表示圖像的寬度;瀏覽器使用這些信息從列表中選擇合適的圖像。sizes
屬性為瀏覽器提供將要顯示圖像的尺寸信息,srcset
使用w
描述符時必須包含此屬性。這種方法尤其適用于可變寬度的圖像,我將在后面詳細討論。 我們現(xiàn)在可以根據(jù)用戶的viewport,提供不同質(zhì)量或美術(shù)設(shè)計(art direction)的圖像,無需借助復雜的服務(wù)器端設(shè)置。響應(yīng)式圖像將成為HTML規(guī)范的重要組成部分,所有瀏覽器終將都會支持此解決方案。 固定寬度圖像:基于設(shè)備像素比選擇 視網(wǎng)膜屏幕的廣泛應(yīng)用,使我們不僅需要考慮屏幕分辨率,而且也需要考慮像素密度。視網(wǎng)膜屏幕,4K顯示器,UltraHD-它們都比相同尺寸的標準分辨率顯示器填充了更多的像素。更多的像素=更清晰的圖像。 有些圖片不管屏幕尺寸,始終以固定寬度顯示-如站點logo或人物簡介圖像,也就是說需要根據(jù)設(shè)備像素比來選擇。瀏覽器將根據(jù)設(shè)備像素比來選擇加載哪張圖像。 srcset
屬性列出了瀏覽器可以選擇加載的源圖像池,是一個由逗號分隔的列表。x
描述符表示圖像的設(shè)備像素比。瀏覽器根據(jù)運行環(huán)境,利用這些信息來選擇適當?shù)膱D像。不理解srcset
的瀏覽器會直接加載src
屬性中聲明的圖像。 網(wǎng)站logo就是固定寬度圖像的一個例子,不管viewport的寬度如何,始終保持相同的寬度。不過,與內(nèi)容相關(guān)的圖片,通常也需要響應(yīng)式,它們的大小往往隨viewport改變。對于這類圖像,還有更好的處理方法。 可變寬度的圖像:基于viewport選擇 對于可變寬度的圖像,我們使用
srcset
搭配w
描述符以及sizes
屬性 。w
描述符告訴瀏覽器列表中的每個圖象的寬度。sizes
屬性是一個包含兩個值的,由逗號分隔的列表。根據(jù)最新規(guī)范,如果srcset
中任何圖像使用了w
描述符,那么必須要設(shè)置sizes
屬性。 sizes
屬性有兩個值:第一個是媒體條件;第二個是源圖尺寸值,在特定媒體條件下,此值決定了圖片的寬度。需要注意是,源圖尺寸值不能使用百分比,vw
是唯一可用的CSS單位。 上例中,我們告訴瀏覽器在viewport寬度小于400像素時,使圖像的寬度與viewport等寬。在viewport寬度小于960像素時,使圖像的寬度為viewport寬度的75%。當viewport大于960像素時,使圖像的寬度為640像素。如果你不熟悉vw
,可以看看Tim Severien的大文viewport單位詳解 。 瀏覽器利用srcset
和sizes
信息來選擇最符合規(guī)定條件的圖像。如果瀏覽器的viewport是600像素,圖像最可能以75vw
的寬度顯示。瀏覽器將嘗試加載第一張大于450像素(600*0.75)的圖像,也就是uswnt-480.jpg
。如果我的是dpr為2的Retina顯示屏,那么瀏覽器就會嘗試加載第一張大于900像素(600*0.75*2)的圖像,也就是uswnt-960.jpg。
我們無法確定究竟顯示哪張圖像,因為每個瀏覽器根據(jù)我們提供的信息挑選適當圖像的算法是有差異的。(譯者注:srcset和size列表是對瀏覽器的一個建議(hint),而非指令。例如,設(shè)備像素比(dpr)為1.5的設(shè)備,亦可用1x也可用2x的圖像,由瀏覽器根據(jù)其能力、網(wǎng)絡(luò)等因素來決定。) 前兩個例子都是以不同質(zhì)量顯示相同的圖像,僅用srcset
屬性就足夠了。不必擔心老舊瀏覽器,老舊瀏覽器會把它看作為一個普通的圖像并從src
中加載。如果你想在不同寬度下顯示稍微不同的圖像,比如在較窄屏幕下僅顯示圖像的關(guān)鍵部分,那么要使用picture
元素。 picture:基于Art direction(美術(shù)設(shè)計)選擇 picture
元素就像是圖像和其源的容器。瀏覽器仍然需要img
元素,用來表明需要加載圖片,如果沒有img
,那么什么都不會渲染。source
為瀏覽器提供了要顯示圖像的供選版本?;诿佬g(shù)設(shè)計選擇的適用場景為:在一個特定的轉(zhuǎn)效點(breakpoint)需要顯示一個特定的圖像。使用picture
元素選擇圖像,不會有歧義。 在本例中,當viewport大于960像素時,會加載圖像的風景模式版本(ticker-tape-large.jpg
)。當viewport寬度大于575像素時,瀏覽器會加載圖像的裁剪過的肖像模式版本(ticker-tape-medium.jpg
)。而當寬度小于575像素時,加載的圖像( ticker-tape-small.jpg
)已經(jīng)被裁剪成焦點僅在一個球員上了。 picture
元素是向后兼容的;不支持picture
元素的瀏覽器將顯示img
。圖像的所有標準屬性(如alt
),應(yīng)該作用在img上
而不是picture
上。 source:基于圖片格式選擇 最近幾年出現(xiàn)了一些新的圖片格式,這些新圖像格式在較小的文件大小情況下保證了較好的圖片質(zhì)量。聽起來還不錯,但殘酷的事實是沒有一個新格式被所有瀏覽器支持。谷歌的WebP表現(xiàn)不錯,但只有Chrome和Opera原聲支持。JPEG-XR,最初被稱為高清照片,是微軟發(fā)布的一個專有圖像格式,僅Internet Explorer支持。如果你想了解更多信息,可以查看Zoltan Hawryluk對這些新格式的深入研究。
source
的type屬性用來指定每個圖像的MIME類型,瀏覽器會選擇第一個含有其支持的MIME類型的源。源的順序是至關(guān)重要的,如果瀏覽器無法識別所有的圖象類型,它會回退至原來的img
元素。 現(xiàn)在可以使用這些東東嗎? 在寫這篇文章的時候, Firefox,Chrome和Opera的最新穩(wěn)定版本均支持picture
。Safari和IE本身均不支持picture
。srcset
的情況稍微好一點,F(xiàn)irefox、Chrome和Opera的最新穩(wěn)定版本完全支持,Safari8和Internet Explorer Edge部分支持,可以使用x
描述符用于根據(jù)分辨率切換,但不支持w
描述符。Safari9已經(jīng)完全支持srcset了(譯者注)。 現(xiàn)有不少polyfills解決支持性問題,最知名的恐怕是Scott Jehl的picturefill。目前我(原作者)在我自己的網(wǎng)站上使用Alexander Farkas的respimage。目前的狀況是,我們已對響應(yīng)式圖像的處理方案達成一致,并且這些解決方案逐漸被所有的主流瀏覽器實現(xiàn)。盡管該規(guī)范仍在不斷完善之中,但原生的響應(yīng)式解決方案離我們越來越近了。