轉(zhuǎn):移動(dòng)前端開(kāi)發(fā)之viewport的深入理解

(轉(zhuǎn)自:http://blog.csdn.net/tengdazhang770960436/article/details/50236245
在移動(dòng)設(shè)備上進(jìn)行網(wǎng)頁(yè)的重構(gòu)或開(kāi)發(fā),首先得搞明白的就是移動(dòng)設(shè)備上的viewport了乏德,只有明白了viewport的概念以及弄清楚了跟viewport有關(guān)的meta標(biāo)簽的使用菩收,才能更好地讓我們的網(wǎng)頁(yè)適配或響應(yīng)各種不同分辨率的移動(dòng)設(shè)備颈墅。
一岭佳、viewport的概念
通俗的講拜马,移動(dòng)設(shè)備上的viewport就是設(shè)備的屏幕上能用來(lái)顯示我們的網(wǎng)頁(yè)的那一塊區(qū)域喂走,在具體一點(diǎn)呼胚,就是瀏覽器上(也可能是一個(gè)app中的webview)用來(lái)顯示網(wǎng)頁(yè)的那部分區(qū)域躬存,但viewport又不局限于瀏覽器可視區(qū)域的大小张惹,它可能比瀏覽器的可視區(qū)域要大,也可能比瀏覽器的可視區(qū)域要小岭洲。在默認(rèn)情況下宛逗,一般來(lái)講,移動(dòng)設(shè)備上的viewport都是要大于瀏覽器可視區(qū)域的盾剩,這是因?yàn)榭紤]到移動(dòng)設(shè)備的分辨率相對(duì)于桌面電腦來(lái)說(shuō)都比較小雷激,所以為了能在移動(dòng)設(shè)備上正常顯示那些傳統(tǒng)的為桌面瀏覽器設(shè)計(jì)的網(wǎng)站,移動(dòng)設(shè)備上的瀏覽器都會(huì)把自己默認(rèn)的viewport設(shè)為980px或1024px(也可能是其它值告私,這個(gè)是由設(shè)備自己決定的)屎暇,但帶來(lái)的后果就是瀏覽器會(huì)出現(xiàn)橫向滾動(dòng)條,因?yàn)闉g覽器可視區(qū)域的寬度是比這個(gè)默認(rèn)的viewport的寬度要小的驻粟。下圖列出了一些設(shè)備上瀏覽器的默認(rèn)viewport的寬度根悼。

image

二、css中的1px并不等于設(shè)備的1px
在css中我們一般使用px作為單位蜀撑,在桌面瀏覽器中css的1個(gè)像素往往都是對(duì)應(yīng)著電腦屏幕的1個(gè)物理像素挤巡,這可能會(huì)造成我們的一個(gè)錯(cuò)覺(jué),那就是css中的像素就是設(shè)備的物理像素酷麦。但實(shí)際情況卻并非如此玄柏,css中的像素只是一個(gè)抽象的單位,在不同的設(shè)備或不同的環(huán)境中贴铜,css中的1px所代表的設(shè)備物理像素是不同的粪摘。在為桌面瀏覽器設(shè)計(jì)的網(wǎng)頁(yè)中瀑晒,我們無(wú)需對(duì)這個(gè)津津計(jì)較,但在移動(dòng)設(shè)備上徘意,必須弄明白這點(diǎn)苔悦。在早先的移動(dòng)設(shè)備中,屏幕像素密度都比較低椎咧,如iphone3玖详,它的分辨率為320x480,在iphone3上勤讽,一個(gè)css像素確實(shí)是等于一個(gè)屏幕物理像素的蟋座。后來(lái)隨著技術(shù)的發(fā)展,移動(dòng)設(shè)備的屏幕像素密度越來(lái)越高脚牍,從iphone4開(kāi)始向臀,蘋(píng)果公司便推出了所謂的Retina屏,分辨率提高了一倍诸狭,變成640x960券膀,但屏幕尺寸卻沒(méi)變化驯遇,這就意味著同樣大小的屏幕上芹彬,像素卻多了一倍,這時(shí)叉庐,一個(gè)css像素是等于兩個(gè)物理像素的舒帮。其他品牌的移動(dòng)設(shè)備也是這個(gè)道理。例如安卓設(shè)備根據(jù)屏幕像素密度可分為ldpi陡叠、mdpi会前、hdpi、xhdpi等不同的等級(jí)匾竿,分辨率也是五花八門(mén)瓦宜,安卓設(shè)備上的一個(gè)css像素相當(dāng)于多少個(gè)屏幕物理像素,也因設(shè)備的不同而不同岭妖,沒(méi)有一個(gè)定論临庇。
還有一個(gè)因素也會(huì)引起css中px的變化,那就是用戶縮放昵慌。例如假夺,當(dāng)用戶把頁(yè)面放大一倍,那么css中1px所代表的物理像素也會(huì)增加一倍斋攀;反之把頁(yè)面縮小一倍已卷,css中1px所代表的物理像素也會(huì)減少一倍。關(guān)于這點(diǎn)淳蔼,在文章后面的部分還會(huì)講到侧蘸。
在移動(dòng)端瀏覽器中以及某些桌面瀏覽器中裁眯,window對(duì)象有一個(gè)devicePixelRatio屬性,它的官方的定義為:設(shè)備物理像素和設(shè)備獨(dú)立像素的比例讳癌,也就是 devicePixelRatio = 物理像素 / 獨(dú)立像素穿稳。css中的px就可以看做是設(shè)備的獨(dú)立像素,所以通過(guò)devicePixelRatio晌坤,我們可以知道該設(shè)備上一個(gè)css像素代表多少個(gè)物理像素逢艘。例如,在Retina屏的iphone上骤菠,devicePixelRatio的值為2它改,也就是說(shuō)1個(gè)css像素相當(dāng)于2個(gè)物理像素。但是要注意的是商乎,devicePixelRatio在不同的瀏覽器中還存在些許的兼容性問(wèn)題央拖,所以我們現(xiàn)在還并不能完全信賴這個(gè)東西,具體的情況可以看下這篇文章截亦。
devicePixelRatio的測(cè)試結(jié)果:

image

三爬泥、PPK的關(guān)于三個(gè)viewport的理論
ppk大神對(duì)于移動(dòng)設(shè)備上的viewport有著非常多的研究(第一篇柬讨,第二篇崩瓤,第三篇),有興趣的同學(xué)可以去看一下踩官,本文中有很多數(shù)據(jù)和觀點(diǎn)也是出自那里却桶。ppk認(rèn)為,移動(dòng)設(shè)備上有三個(gè)viewport蔗牡。
首先颖系,移動(dòng)設(shè)備上的瀏覽器認(rèn)為自己必須能讓所有的網(wǎng)站都正常顯示,即使是那些不是為移動(dòng)設(shè)備設(shè)計(jì)的網(wǎng)站辩越。但如果以瀏覽器的可視區(qū)域作為viewport的話嘁扼,因?yàn)橐苿?dòng)設(shè)備的屏幕都不是很寬,所以那些為桌面瀏覽器設(shè)計(jì)的網(wǎng)站放到移動(dòng)設(shè)備上顯示時(shí)黔攒,必然會(huì)因?yàn)橐苿?dòng)設(shè)備的viewport太窄趁啸,而擠作一團(tuán),甚至布局什么的都會(huì)亂掉督惰。也許有人會(huì)問(wèn)不傅,現(xiàn)在不是有很多手機(jī)分辨率都非常大嗎,比如768x1024赏胚,或者1080x1920這樣访娶,那這樣的手機(jī)用來(lái)顯示為桌面瀏覽器設(shè)計(jì)的網(wǎng)站是沒(méi)問(wèn)題的吧?前面我們已經(jīng)說(shuō)了觉阅,css中的1px并不是代表屏幕上的1px崖疤,你分辨率越大秘车,css中1px代表的物理像素就會(huì)越多,devicePixelRatio的值也越大戳晌,這很好理解鲫尊,因?yàn)槟惴直媛试龃罅耍聊怀叽绮](méi)有變大多少沦偎,必須讓css中的1px代表更多的物理像素疫向,才能讓1px的東西在屏幕上的大小與那些低分辨率的設(shè)備差不多,不然就會(huì)因?yàn)樘《床磺搴篮俊K栽?080x1920這樣的設(shè)備上搔驼,在默認(rèn)情況下,也許你只要把一個(gè)div的寬度設(shè)為300多px(視devicePixelRatio的值而定)侈询,就是滿屏的寬度了舌涨。回到正題上來(lái)扔字,如果把移動(dòng)設(shè)備上瀏覽器的可視區(qū)域設(shè)為viewport的話囊嘉,某些網(wǎng)站就會(huì)因?yàn)関iewport太窄而顯示錯(cuò)亂,所以這些瀏覽器就決定默認(rèn)情況下把viewport設(shè)為一個(gè)較寬的值革为,比如980px扭粱,這樣的話即使是那些為桌面設(shè)計(jì)的網(wǎng)站也能在移動(dòng)瀏覽器上正常顯示了。ppk把這個(gè)瀏覽器默認(rèn)的viewport叫做 layout viewport震檩。這個(gè)layout viewport的寬度可以通過(guò) document.documentElement.clientWidth 來(lái)獲取琢蛤。
然而,***layout viewport ***的寬度是大于瀏覽器可視區(qū)域的寬度的抛虏,所以我們還需要一個(gè)viewport來(lái)代表 瀏覽器可視區(qū)域的大小博其,ppk把這個(gè)viewport叫做 visual viewport。visual viewport的寬度可以通過(guò)window.innerWidth 來(lái)獲取迂猴,但在Android 2, Oprea mini 和 UC 8中無(wú)法正確獲取慕淡。
******

image

************

******


現(xiàn)在我們已經(jīng)有兩個(gè)viewport了:layout viewportvisual viewport。但瀏覽器覺(jué)得還不夠沸毁,因?yàn)楝F(xiàn)在越來(lái)越多的網(wǎng)站都會(huì)為移動(dòng)設(shè)備進(jìn)行單獨(dú)的設(shè)計(jì)峰髓,所以必須還要有一個(gè)能完美適配移動(dòng)設(shè)備的viewport。所謂的完美適配指的是以清,首先不需要用戶縮放和橫向滾動(dòng)條就能正常的查看網(wǎng)站的所有內(nèi)容儿普;第二,顯示的文字的大小是合適掷倔,比如一段14px大小的文字眉孩,不會(huì)因?yàn)樵谝粋€(gè)高密度像素的屏幕里顯示得太小而無(wú)法看清,理想的情況是這段14px的文字無(wú)論是在何種密度屏幕,何種分辨率下浪汪,顯示出來(lái)的大小都是差不多的巴柿。當(dāng)然,不只是文字死遭,其他元素像圖片什么的也是這個(gè)道理广恢。ppk把這個(gè)viewport叫做 ideal viewport,也就是第三個(gè)viewport——移動(dòng)設(shè)備的理想viewport呀潭。
ideal viewport并沒(méi)有一個(gè)固定的尺寸钉迷,不同的設(shè)備擁有有不同的ideal viewport。所有的iphone的ideal viewport寬度都是320px钠署,無(wú)論它的屏幕寬度是320還是640糠聪,也就是說(shuō),在iphone中谐鼎,css中的320px就代表iphone屏幕的寬度舰蟆。
image
image

但是安卓設(shè)備就比較復(fù)雜了,有320px的狸棍,有360px的身害,有384px的等等,關(guān)于不同的設(shè)備ideal viewport的寬度都為多少草戈,可以到http://viewportsizes.com去查看一下塌鸯,里面收集了眾多設(shè)備的理想寬度。
再總結(jié)一下:ppk把移動(dòng)設(shè)備上的viewport分為layout viewport 猾瘸、 visual viewport ideal viewport 三類(lèi)界赔,其中的ideal viewport是最適合移動(dòng)設(shè)備的viewport丢习,ideal viewport的寬度等于移動(dòng)設(shè)備的屏幕寬度牵触,只要在css中把某一元素的寬度設(shè)為ideal viewport的寬度(單位用px),那么這個(gè)元素的寬度就是設(shè)備屏幕的寬度了咐低,也就是寬度為100%的效果揽思。ideal viewport 的意義在于,無(wú)論在何種分辨率的屏幕下见擦,那些針對(duì)ideal viewport 而設(shè)計(jì)的網(wǎng)站钉汗,不需要用戶手動(dòng)縮放,也不需要出現(xiàn)橫向滾動(dòng)條鲤屡,都可以完美的呈現(xiàn)給用戶损痰。

四、利用meta標(biāo)簽對(duì)viewport進(jìn)行控制
移動(dòng)設(shè)備默認(rèn)的viewport是layout viewport酒来,也就是那個(gè)比屏幕要寬的viewport卢未,但在進(jìn)行移動(dòng)設(shè)備網(wǎng)站的開(kāi)發(fā)時(shí),我們需要的是ideal viewport。那么怎么才能得到ideal viewport呢辽社?這就該輪到meta標(biāo)簽出場(chǎng)了伟墙。
我們?cè)陂_(kāi)發(fā)移動(dòng)設(shè)備的網(wǎng)站時(shí),最常見(jiàn)的的一個(gè)動(dòng)作就是把下面這個(gè)東西復(fù)制到我們的head標(biāo)簽中:
<meta name="viewport" content="width=device-width, initial-scale=1.0, maximum-scale=1.0, user-scalable=0">

該meta標(biāo)簽的作用是讓當(dāng)前viewport的寬度等于設(shè)備的寬度滴铅,同時(shí)不允許用戶手動(dòng)縮放戳葵。也許允不允許用戶縮放不同的網(wǎng)站有不同的要求,但讓viewport的寬度等于設(shè)備的寬度汉匙,這個(gè)應(yīng)該是大家都想要的效果拱烁,如果你不這樣的設(shè)定的話,那就會(huì)使用那個(gè)比屏幕寬的默認(rèn)viewport噩翠,也就是說(shuō)會(huì)出現(xiàn)橫向滾動(dòng)條邻梆。
這個(gè)name為viewport的meta標(biāo)簽到底有哪些東西呢,又都有什么作用呢绎秒?
meta viewport 標(biāo)簽首先是由蘋(píng)果公司在其safari瀏覽器中引入的浦妄,目的就是解決移動(dòng)設(shè)備的viewport問(wèn)題。后來(lái)安卓以及各大瀏覽器廠商也都紛紛效仿见芹,引入對(duì)meta viewport的支持剂娄,事實(shí)也證明這個(gè)東西還是非常有用的。
在蘋(píng)果的規(guī)范中玄呛,meta viewport 有6個(gè)屬性(暫且把content中的那些東西稱(chēng)為一個(gè)個(gè)屬性和值)阅懦,如下:
width
設(shè)置layout viewport 的寬度,為一個(gè)正整數(shù)徘铝,或字符串"width-device"

initial-scale
設(shè)置頁(yè)面的初始縮放值耳胎,為一個(gè)數(shù)字,可以帶小數(shù)

minimum-scale
允許用戶的最小縮放值惕它,為一個(gè)數(shù)字怕午,可以帶小數(shù)

maximum-scale
允許用戶的最大縮放值,為一個(gè)數(shù)字淹魄,可以帶小數(shù)

height
設(shè)置layout viewport 的高度郁惜,這個(gè)屬性對(duì)我們并不重要,很少使用

user-scalable
是否允許用戶進(jìn)行縮放甲锡,值為"no"或"yes", no 代表不允許兆蕉,yes代表允許

這些屬性可以同時(shí)使用,也可以單獨(dú)使用或混合使用缤沦,多個(gè)屬性同時(shí)使用時(shí)用逗號(hào)隔開(kāi)就行了虎韵。
此外,在安卓中還支持 target-densitydpi 這個(gè)私有屬性缸废,它表示目標(biāo)設(shè)備的密度等級(jí)包蓝,作用是決定css中的1px代表多少物理像素
target-densitydpi
值可以為一個(gè)數(shù)值或 high-dpi 缩多、 medium-dpi、 low-dpi养晋、 device-dpi 這幾個(gè)字符串中的一個(gè)

特別說(shuō)明的是衬吆,當(dāng) target-densitydpi=device-dpi 時(shí), css中的1px會(huì)等于物理像素中的1px绳泉。
因?yàn)檫@個(gè)屬性只有安卓支持逊抡,并且安卓已經(jīng)決定要廢棄target-densitydpi 這個(gè)屬性了,所以這個(gè)屬性我們要避免進(jìn)行使用 零酪。


五冒嫡、把當(dāng)前的viewport寬度設(shè)置為 ideal viewport 的寬度
要得到ideal viewport就必須把默認(rèn)的layout viewport的寬度設(shè)為移動(dòng)設(shè)備的屏幕寬度。因?yàn)閙eta viewport中的width能控制layout viewport的寬度四苇,所以我們只需要把width設(shè)為width-device這個(gè)特殊的值就行了孝凌。
<meta name="viewport" content="width=device-width">

下圖是這句代碼在各大移動(dòng)端瀏覽器上的測(cè)試結(jié)果:

image

可以看到通過(guò)width=device-width,所有瀏覽器都能把當(dāng)前的viewport寬度變成ideal viewport的寬度月腋,但要注意的是蟀架,在iphone和ipad上,無(wú)論是豎屏還是橫屏榆骚,寬度都是豎屏?xí)rideal viewport的寬度片拍。
這樣的寫(xiě)法看起來(lái)誰(shuí)都會(huì)做,沒(méi)吃過(guò)豬肉妓肢,誰(shuí)還沒(méi)見(jiàn)過(guò)豬跑啊~捌省,確實(shí),我們?cè)陂_(kāi)發(fā)移動(dòng)設(shè)備上的網(wǎng)頁(yè)時(shí)碉钠,不管你明不明白什么是viewport纲缓,可能你只需要這么一句代碼就夠了。
可是你肯定不知道
<meta name="viewport" content="initial-scale=1">

這句代碼也能達(dá)到和前一句代碼一樣的效果喊废,也可以把當(dāng)前的的viewport變?yōu)?ideal viewport祝高。
呵呵,傻眼了吧操禀,因?yàn)閺睦碚撋蟻?lái)講褂策,這句代碼的作用只是不對(duì)當(dāng)前的頁(yè)面進(jìn)行縮放横腿,也就是頁(yè)面本該是多大就是多大颓屑。那為什么會(huì)有 width=device-width 的效果呢?
要想清楚這件事情耿焊,首先你得弄明白這個(gè)縮放是相對(duì)于什么來(lái)縮放的揪惦,因?yàn)檫@里的縮放值是1,也就是沒(méi)縮放罗侯,但卻達(dá)到了 ideal viewport 的效果器腋,所以,那答案就只有一個(gè)了,縮放是相對(duì)于 ideal viewport來(lái)進(jìn)行縮放的纫塌,當(dāng)對(duì)ideal viewport進(jìn)行100%的縮放诊县,也就是縮放值為1的時(shí)候,不就得到了 ideal viewport嗎措左?事實(shí)證明依痊,的確是這樣的。下圖是各大移動(dòng)端的瀏覽器當(dāng)設(shè)置了<meta name="viewport" content="initial-scale=1"> 后是否能把當(dāng)前的viewport寬度變成 ideal viewport 的寬度的測(cè)試結(jié)果怎披。

image

測(cè)試結(jié)果表明 initial-scale=1 也能把當(dāng)前的viewport寬度變成 ideal viewport 的寬度胸嘁,但這次輪到了windows phone 上的IE 無(wú)論是豎屏還是橫屏都把寬度設(shè)為豎屏?xí)rideal viewport的寬度。但這點(diǎn)小瑕疵已經(jīng)無(wú)關(guān)緊要了凉逛。
但如果width 和 initial-scale=1同時(shí)出現(xiàn)性宏,并且還出現(xiàn)了沖突呢?比如:
<meta name="viewport" content="width=400, initial-scale=1">

width=400表示把當(dāng)前viewport的寬度設(shè)為400px状飞,initial-scale=1則表示把當(dāng)前viewport的寬度設(shè)為ideal viewport的寬度毫胜,那么瀏覽器到底該服從哪個(gè)命令呢?是書(shū)寫(xiě)順序在后面的那個(gè)嗎诬辈?不是指蚁。當(dāng)遇到這種情況時(shí),瀏覽器會(huì)取它們兩個(gè)中較大的那個(gè)值自晰。例如凝化,當(dāng)width=400,ideal viewport的寬度為320時(shí)酬荞,取的是400搓劫;當(dāng)width=400, ideal viewport的寬度為480時(shí)混巧,取的是ideal viewport的寬度枪向。(ps:在uc9瀏覽器中,當(dāng)initial-scale=1時(shí)咧党,無(wú)論width屬性的值為多少秘蛔,此時(shí)viewport的寬度永遠(yuǎn)都是ideal viewport的寬度)
最后,總結(jié)一下傍衡,要把當(dāng)前的viewport寬度設(shè)為ideal viewport的寬度深员,既可以設(shè)置 width=device-width,也可以設(shè)置 initial-scale=1蛙埂,但這兩者各有一個(gè)小缺陷倦畅,就是iphone、ipad以及IE 會(huì)橫豎屏不分绣的,通通以豎屏的ideal viewport寬度為準(zhǔn)叠赐。所以欲账,最完美的寫(xiě)法應(yīng)該是,兩者都寫(xiě)上去芭概,這樣就 initial-scale=1 解決了 iphone赛不、ipad的毛病,width=device-width則解決了IE的毛舶罩蕖:
<meta name="viewport" content="width=device-width, initial-scale=1">



六俄删、關(guān)于meta viewport的更多知識(shí)
1、關(guān)于縮放以及initial-scale的默認(rèn)值
首先我們先來(lái)討論一下縮放的問(wèn)題奏路,前面已經(jīng)提到過(guò)畴椰,縮放是相對(duì)于ideal viewport來(lái)縮放的,縮放值越大鸽粉,當(dāng)前viewport的寬度就會(huì)越小斜脂,反之亦然。例如在iphone中触机,ideal viewport的寬度是320px帚戳,如果我們?cè)O(shè)置 initial-scale=2 ,此時(shí)viewport的寬度會(huì)變?yōu)橹挥?60px了儡首,這也好理解片任,放大了一倍嘛,就是原來(lái)1px的東西變成2px了蔬胯,但是1px變?yōu)?px并不是把原來(lái)的320px變?yōu)?40px了对供,而是在實(shí)際寬度不變的情況下,1px變得跟原來(lái)的2px的長(zhǎng)度一樣了氛濒,所以放大2倍后原來(lái)需要320px才能填滿的寬度現(xiàn)在只需要160px就做到了产场。因此,我們可以得出一個(gè)公式:
visual viewport寬度 = ideal viewport寬度 / 當(dāng)前縮放值當(dāng)前縮放值 = ideal viewport寬度 / visual viewport寬度

ps: visual viewport的寬度指的是瀏覽器可視區(qū)域的寬度舞竿。
大多數(shù)瀏覽器都符合這個(gè)理論京景,但是安卓上的原生瀏覽器以及IE有些問(wèn)題。安卓自帶的webkit瀏覽器只有在 initial-scale = 1 以及沒(méi)有設(shè)置width屬性時(shí)才是表現(xiàn)正常的骗奖,也就相當(dāng)于這理論在它身上基本沒(méi)用确徙;而IE則根本不甩initial-scale這個(gè)屬性,無(wú)論你給他設(shè)置什么执桌,initial-scale表現(xiàn)出來(lái)的效果永遠(yuǎn)是1鄙皇。
好了,現(xiàn)在再來(lái)說(shuō)下initial-scale的默認(rèn)值問(wèn)題鼻吮,就是不寫(xiě)這個(gè)屬性的時(shí)候育苟,它的默認(rèn)值會(huì)是多少呢?很顯然不會(huì)是1椎木,因?yàn)楫?dāng) initial-scale = 1 時(shí)违柏,當(dāng)前的layout viewport寬度會(huì)被設(shè)為 ideal viewport的寬度,但前面說(shuō)了香椎,各瀏覽器默認(rèn)的 layout viewport寬度一般都是980啊漱竖,1024啊,800啊等等這些個(gè)值畜伐,沒(méi)有一開(kāi)始就是 ideal viewport的寬度的馍惹,所以 initial-scale的默認(rèn)值肯定不是1。安卓設(shè)備上的initial-scale默認(rèn)值好像沒(méi)有方法能夠得到玛界,或者就是干脆它就沒(méi)有默認(rèn)值万矾,一定要你顯示的寫(xiě)出來(lái)這個(gè)東西才會(huì)起作用,我們不管它了慎框,這里我們重點(diǎn)說(shuō)一下iphone和ipad上的initial-scale默認(rèn)值良狈。

根據(jù)測(cè)試,我們可以在iphone和ipad上得到一個(gè)結(jié)論笨枯,就是無(wú)論你給layout viewpor設(shè)置的寬度是多少薪丁,而又沒(méi)有指定初始的縮放值的話,那么iphone和ipad會(huì)自動(dòng)計(jì)算initial-scale這個(gè)值馅精,以保證當(dāng)前l(fā)ayout viewport的寬度在縮放后就是瀏覽器可視區(qū)域的寬度严嗜,也就是說(shuō)不會(huì)出現(xiàn)橫向滾動(dòng)條。比如說(shuō)洲敢,在iphone上漫玄,我們不設(shè)置任何的viewport meta標(biāo)簽,此時(shí)layout viewport的寬度為980px压彭,但我們可以看到瀏覽器并沒(méi)有出現(xiàn)橫向滾動(dòng)條称近,瀏覽器默認(rèn)的把頁(yè)面縮小了。根據(jù)上面的公式哮塞,當(dāng)前縮放值 = ideal viewport寬度 / visual viewport寬度刨秆,我們可以得出:
當(dāng)前縮放值 = 320 / 980
也就是當(dāng)前的initial-scale默認(rèn)值應(yīng)該是 0.33這樣子。當(dāng)你指定了initial-scale的值后忆畅,這個(gè)默認(rèn)值就不起作用了衡未。
總之記住這個(gè)結(jié)論就行了:在iphone和ipad上,無(wú)論你給viewport設(shè)的寬的是多少家凯,如果沒(méi)有指定默認(rèn)的縮放值缓醋,則iphone和ipad會(huì)自動(dòng)計(jì)算這個(gè)縮放值,以達(dá)到當(dāng)前頁(yè)面不會(huì)出現(xiàn)橫向滾動(dòng)條(或者說(shuō)viewport的寬度就是屏幕的寬度)的目的绊诲。

image

image

2送粱、動(dòng)態(tài)改變meta viewport標(biāo)簽
第一種方法
可以使用document.write來(lái)動(dòng)態(tài)輸出meta viewport標(biāo)簽掂之,例如:
document.write('<meta name="viewport" content="width=device-width,initial-scale=1">')

第二種方法
通過(guò)setAttribute來(lái)改變
<meta id="testViewport" name="viewport" content="width = 380"><script>var mvp = document.getElementById('testViewport');mvp.setAttribute('content','width=480');</script>

**

安卓2.3自帶瀏覽器上的一個(gè)bug

image

<meta name="viewport" content="width=device-width"><script type="text/javascript">alert(document.documentElement.clientWidth); //彈出600,正常情況應(yīng)該彈出320</script><meta name="viewport" content="width=600"><script type="text/javascript">alert(document.documentElement.clientWidth); //彈出320,正常情況應(yīng)該彈出600</script>

image

測(cè)試的手機(jī)ideal viewport 寬度為320px钾虐,第一次彈出的值是600,但這個(gè)值應(yīng)該是第行meta標(biāo)簽的結(jié)果啊,然后第二次彈出的值是320丐枉,這才是第一行meta標(biāo)簽所達(dá)到的效果啊弯院,所以在安卓2.3(或許是所有2.x版本中)的自帶瀏覽器中异赫,對(duì)meta viewport標(biāo)簽進(jìn)行覆蓋或更改,會(huì)出現(xiàn)讓人非常迷糊的結(jié)果。

七、結(jié)語(yǔ)
說(shuō)了那么多廢話个曙,最后還是有必要總結(jié)一點(diǎn)有用的出來(lái)。
首先如果不設(shè)置meta viewport標(biāo)簽米绕,那么移動(dòng)設(shè)備上瀏覽器默認(rèn)的寬度值為800px碱鳞,980px崩泡,1024px等這些靴寂,總之是大于屏幕寬度的磷蜀。這里的寬度所用的單位px都是指css中的px,它跟代表實(shí)際屏幕物理像素的px不是一回事百炬。
第二褐隆、每個(gè)移動(dòng)設(shè)備瀏覽器中都有一個(gè)理想的寬度,這個(gè)理想的寬度是指css中的寬度剖踊,跟設(shè)備的物理寬度沒(méi)有關(guān)系庶弃,在css中衫贬,這個(gè)寬度就相當(dāng)于100%的所代表的那個(gè)寬度。我們可以用meta標(biāo)簽把viewport的寬度設(shè)為那個(gè)理想的寬度歇攻,如果不知道這個(gè)設(shè)備的理想寬度是多少固惯,那么用device-width這個(gè)特殊值就行了,同時(shí)initial-scale=1也有把viewport的寬度設(shè)為理想寬度的作用缴守。所以葬毫,我們可以使用
<meta name="viewport" content="width=device-width, initial-scale=1">

來(lái)得到一個(gè)理想的viewport(也就是前面說(shuō)的ideal viewport)。為什么需要有理想的viewport呢屡穗?比如一個(gè)分辨率為320x480的手機(jī)理想viewport的寬度是320px贴捡,而另一個(gè)屏幕尺寸相同但分辨率為640x960的手機(jī)的理想viewport寬度也是為320px,那為什么分辨率大的這個(gè)手機(jī)的理想寬度要跟分辨率小的那個(gè)手機(jī)的理想寬度一樣呢村砂?這是因?yàn)槔谜挥羞@樣才能保證同樣的網(wǎng)站在不同分辨率的設(shè)備上看起來(lái)都是一樣或差不多的。實(shí)際上础废,現(xiàn)在市面上雖然有那么多不同種類(lèi)不同品牌不同分辨率的手機(jī)汛骂,但它們的理想viewport寬度歸納起來(lái)無(wú)非也就 320、360评腺、384帘瞭、400等幾種,都是非常接近的歇僧,理想寬度的相近也就意味著我們針對(duì)某個(gè)設(shè)備的理想viewport而做出的網(wǎng)站图张,在其他設(shè)備上的表現(xiàn)也不會(huì)相差非常多甚至是表現(xiàn)一樣的。

作者:一個(gè)廢人
鏈接:http://www.reibang.com/p/9c80c238cb25
來(lái)源:簡(jiǎn)書(shū)
著作權(quán)歸作者所有诈悍。商業(yè)轉(zhuǎn)載請(qǐng)聯(lián)系作者獲得授權(quán)祸轮,非商業(yè)轉(zhuǎn)載請(qǐng)注明出處。

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末侥钳,一起剝皮案震驚了整個(gè)濱河市适袜,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌舷夺,老刑警劉巖苦酱,帶你破解...
    沈念sama閱讀 219,366評(píng)論 6 508
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場(chǎng)離奇詭異给猾,居然都是意外死亡疫萤,警方通過(guò)查閱死者的電腦和手機(jī),發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 93,521評(píng)論 3 395
  • 文/潘曉璐 我一進(jìn)店門(mén)敢伸,熙熙樓的掌柜王于貴愁眉苦臉地迎上來(lái)扯饶,“玉大人,你說(shuō)我怎么就攤上這事∥残颍” “怎么了钓丰?”我有些...
    開(kāi)封第一講書(shū)人閱讀 165,689評(píng)論 0 356
  • 文/不壞的土叔 我叫張陵,是天一觀的道長(zhǎng)每币。 經(jīng)常有香客問(wèn)我携丁,道長(zhǎng),這世上最難降的妖魔是什么兰怠? 我笑而不...
    開(kāi)封第一講書(shū)人閱讀 58,925評(píng)論 1 295
  • 正文 為了忘掉前任梦鉴,我火速辦了婚禮,結(jié)果婚禮上痕慢,老公的妹妹穿的比我還像新娘尚揣。我一直安慰自己涌矢,他們只是感情好掖举,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,942評(píng)論 6 392
  • 文/花漫 我一把揭開(kāi)白布。 她就那樣靜靜地躺著娜庇,像睡著了一般塔次。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上名秀,一...
    開(kāi)封第一講書(shū)人閱讀 51,727評(píng)論 1 305
  • 那天励负,我揣著相機(jī)與錄音,去河邊找鬼匕得。 笑死继榆,一個(gè)胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的汁掠。 我是一名探鬼主播略吨,決...
    沈念sama閱讀 40,447評(píng)論 3 420
  • 文/蒼蘭香墨 我猛地睜開(kāi)眼,長(zhǎng)吁一口氣:“原來(lái)是場(chǎng)噩夢(mèng)啊……” “哼考阱!你這毒婦竟也來(lái)了翠忠?” 一聲冷哼從身側(cè)響起,我...
    開(kāi)封第一講書(shū)人閱讀 39,349評(píng)論 0 276
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤乞榨,失蹤者是張志新(化名)和其女友劉穎秽之,沒(méi)想到半個(gè)月后,有當(dāng)?shù)厝嗽跇?shù)林里發(fā)現(xiàn)了一具尸體吃既,經(jīng)...
    沈念sama閱讀 45,820評(píng)論 1 317
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡考榨,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,990評(píng)論 3 337
  • 正文 我和宋清朗相戀三年,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了鹦倚。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片河质。...
    茶點(diǎn)故事閱讀 40,127評(píng)論 1 351
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出愤诱,到底是詐尸還是另有隱情云头,我是刑警寧澤,帶...
    沈念sama閱讀 35,812評(píng)論 5 346
  • 正文 年R本政府宣布淫半,位于F島的核電站溃槐,受9級(jí)特大地震影響,放射性物質(zhì)發(fā)生泄漏科吭。R本人自食惡果不足惜昏滴,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,471評(píng)論 3 331
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望对人。 院中可真熱鬧谣殊,春花似錦、人聲如沸牺弄。這莊子的主人今日做“春日...
    開(kāi)封第一講書(shū)人閱讀 32,017評(píng)論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)势告。三九已至蛇捌,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間咱台,已是汗流浹背络拌。 一陣腳步聲響...
    開(kāi)封第一講書(shū)人閱讀 33,142評(píng)論 1 272
  • 我被黑心中介騙來(lái)泰國(guó)打工, 沒(méi)想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留回溺,地道東北人春贸。 一個(gè)月前我還...
    沈念sama閱讀 48,388評(píng)論 3 373
  • 正文 我出身青樓,卻偏偏與公主長(zhǎng)得像遗遵,于是被迫代替她去往敵國(guó)和親萍恕。 傳聞我的和親對(duì)象是個(gè)殘疾皇子,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 45,066評(píng)論 2 355

推薦閱讀更多精彩內(nèi)容