理解viewport與device-width

原文  http://www.xiaocaoge.com/understanding-viewport-and-device-width.html

在響應式設計或移動Web開發當中經常見到的一句代碼:

<meta name=”viewport” content=”width=device-width” >

content屬性還包括initial-scale,user-scalable等,不過這裏不談,它們的意思都很容易理解。這裏要談得是:viewport代表什麼?device-width又是啥?

先來理解兩個概念:device pixels與CSS pixels。

device pixels指設備的物理像素,在PC端就是你在操作系統裏設置的屏幕分辨率y,其值可以通過 screen.width/screen.height 獲取。在移動端下面再說。

CSS pixels指在CSS文件中設置的字體大小、元素寬度等,如 font-size: 14px;width: 100px; 。在PC端,瀏覽器縮放比例爲100%,也即默認情況下,1 CSS pixel = 1 device pixel。

當你放大頁面到200%時,字體大小與元素寬度的像素值不會改變,是因爲這些像素值是用CSS pixels表示的,實際上放大的是CSS pixels,此時 1 CSS pixel = 4 device pixels,高和寬都是200%。此時你獲取 screen.width/screen.height 的值,並沒有變化,而 window.innerWidth 和 window.innerHeight 的值變成了原來一半,是因爲window.innerWidth/window.innerHeight 的值也是用CSS pixels來表示的。

當你進行流式佈局時,會用百分比設置元素的寬度,比如一個塊級元素寬度爲10%,那麼你也知道10%實際上是父級元素寬度的10%。但是你並沒有設置父級元素的寬度啊,好吧,你也知道父級元素的寬度與其父級元素寬度一樣(通過繼承得來,假設這些元素都是塊級元素)。然後向上到body元素的寬度,最終爲html元素的寬度,其值可以通過 document.documentElement.clientWidth 獲取。那這個寬度怎麼來得呢?

Viewport

viewport,翻譯爲視口,也即可視區域的大小,PC端通過 window.innerWidth 和window.innerHeight 獲取。

html元素也即文檔的寬度,來自於viewport的寬度,在PC端要加上滾動條的寬度纔會與viewport的寬度一樣。因此,文檔的寬度最終來自於viewport的寬度,PC端通過window.innerWidth 獲取。

而在移動端,情況將變得複雜。

首先,上面提到文檔的寬度來自於viewport的寬度,我們把這個viewport稱爲layout viewport,因爲它和佈局有關。在手機上面,因爲手機的屏幕很小,當初iphone發佈時,爲了顯示完整的桌面網頁,就把給layout viewport設置了一個980px的值。手機上,可以通過 document.documentElement.clientWidth 來獲取,我在安卓手機上測試也是980px。

但是這樣顯示網頁,那網頁的字體、元素都很小,小到打開這樣一個網頁,首先要做的就是放大頁面。爲了提高可讀性,Apple允許通meta標籤來設置layout viewport的寬度,也即文章開頭的那行代碼。

但是,device-width又是什麼呢?

第一代iphone的分辨率爲320*480,屏幕尺寸爲3.5寸。當時把layout viewport設置成與瀏覽器寬度一樣(而手機上瀏覽器寬度與手機屏幕寬度一樣)時,不用每次打開網頁放大了,而且顯示的字體與桌面上差不多,可讀性很好。因此就定義了一個device-width,即是手機的屏幕分辨率,此時device翻譯爲“設備”還合適。

但是第二代iphone發佈時,屏幕的分辨率變成了480*960,而屏幕尺寸仍然爲3.5寸,如果device-width仍然爲手機的屏幕分辨率寬度,那麼字體將會比第一代小很多。所以,維持device-width的值不變將會是個很好得選擇,能與前面兼容。也因此,iphone上的device-width的值一直爲320,只不過device再表示“設備”已經不合適了,實際上代表的是一箇中間層。而Android也採用了這一概念,其device-width的值爲360的多,360=540/1.5,360=720/2。

如何獲取device-width的值呢?

瀏覽器並沒有提供一個獲取device-width的屬性或方法,但是通過window.innerWidth 可以獲取,需要注意的是,必須添加文章開頭那行代碼纔可以跨瀏覽器獲取。如果不添加那行代碼,我自己在HTC G18/ Andoird OS 4.0.3中測試,自帶瀏覽器/UC9.6/QQ5.0可以獲取,而在Chrome33和Opera20中通過screen.width可以獲取。iPhone與iPad我沒測試。這是測試網頁地址:

http://www.xiaocaoge.com/demo/viewport-screen-device-width-mobile.html

Chrome與Opera比較深入實現了中間層的概念,屏幕的實際分辨率與Web開發關係並不大,Chrome與Opera就將 screen.width 返回中間層的寬度。這裏我也不明白哪種設計更好些。

這裏 有個鏈接 可以查看各種手機型號的device-width/device-height大小,雖然鏈接稱爲viewport size。

參考資源:

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章