首先了解下什么是CSS pixels/ 'pɪks(ə)l; -sel /,什么是device pixels;css
1. CSS pixels能够理解为css像素,是浏览器使用的抽象单位,主要用来在网页上绘制内容。也能够说css px是专门为web开发者提出的一个抽象概念,也只跟咱们平时写的css样式有关,与分辨率(好比720px*1280px)里的px不要紧。html
2. device pixels能够理解为是设备像素,官方的解释是:显示屏幕的最小物理单位,每一个dp包含本身的颜色、高宽等。web
对于咱们作web开发的人来讲,咱们用到的最多的地方是“css像素”,即相似width:300px;font-size:14px;这类的css语句里用到的。它跟设备自身的px是不要紧的。也就是说1个CSS 像素占多少个物理像素是不肯定的,这个问题经过页面的放缩比较容易理解。好比一个普通的html页面上,有一个300px的元素;若是咱们放大页面,元素会占据更多的设备像素(即device pixels),但它的CSS pixels不变,依然是300px;缩小页面也是一样的道理,占据了更少的device pixels,但它的CSS pixels不变。也就是说,元素占据了多少device pixels,是由当前页面的放缩比例而定的。浏览器
不过,页面的缩放对咱们web开发来讲是好像没有任何意义的。但有一个问题,咱们开发出来的页面是想要在各个屏幕个以最佳的样式展现出来的,咱们不能让页面里存在不能控制的元素。因此就出现了它:<meta name="viewport" content="width=device-width, initial-scale=1.0, minimum-scale=1.0, maximum-scale=1.0" /> 也就是咱们在进行web开发的时候常常用到的viewport。那么viewport究竟是个什么玩意儿呢,并且content里面width为何要等于device-width呢,device-width又是个什么概念呢?下面咱们来看看它们哥俩儿是什么。app
在解释这两个概念以前,先说一个你们都知道,但不明白为何的状况:把一个普通的在PC上开发的HTML页面直接放手机上,你会发现无论多大的页面均可以在小小的手机屏幕上显示,可是图文都会显示的特别小;若是你用JAVASCRIPT获取下页面宽度,你会发现,大多数的页面宽度都是980px的,这个就跟viewport有关。webapp
Viewport起源于苹果,但如今已经被大多数浏览器支持。关于viewport有两个概念visual viewport跟layout viewport。这里visual viewport也就是视觉上的窗口,能够理解为设备本身的宽度。这时,若是你有一个长960的页面,有一个元素是20%(实际解析出来就是192px)。但若是我用宽为320px的屏幕打开呢,这个元素就成了64px,可是这个时候我设置的字体大小是12px,在320px的屏幕上就只能显示64/12个字了~iphone
鉴于这个问题,苹果找到一种解决方法,在移动版的safari中定义了viewport meta标签,它的做用就是建立一个虚拟的窗口(viewport),这个虚拟的窗口就是layout viewport分辨率接近桌面显示器,apple将其定位为980px。在手机上,能够经过document.documentElement.clientWidth来获取。布局
其余浏览器厂商也有不一样的解决办法,例如UCweb是使用的中间技术。post
另外听说,不一样浏览器厂商对于layout viewport的大小都有本身的定义。可是,我用手上很少的几个手机(小米2s、SONY、金立、ipad)测试的结果,都是980px。其中在小米2s上测试了小米自带浏览器、QQ浏览器、UC浏览器、谷歌浏览器,还有opera浏览器,结果都同样;其余的手机上面无论装了什么浏览器,都测试了,结果都是980px。可是这个值对于咱们web开发来讲,好像也没有什么用处。测试
由于大多数状况下,<meta name="viewport" content="width=device-width" /> 这个标签对咱们来讲是最给力的,可让咱们的页面里的图文显示的是正常的,很大程度上提升了页面的可读性。而这一meta标签的功能就是设置layout viewport为device-width的宽度。可是device-width具体是什么呢?
第一代iphone的时候,分辨率为320*480,屏幕尺寸为3.5寸(注意,这个3.5寸说的是屏幕的对角线宽),这时候device-width就是320px,也是手机的分辨率宽,此时device-width就是设备宽。但第二代的iphone分辨率提升为了480*960,屏幕尺寸为依然为3.5寸,若是device-width仍是设备宽,那么一样是320px的页面放480*960的手机屏上,图文就会变得比较小,又会影响其可读性。所以iphone的device-width一直维持在320px,ipad一直维持在1024px。这个时候,device-width就不是设备宽了(也就不是分辨率的宽了),是一个中间层。Android采用的也是这一律念,其device-width值以360居多,但也不乏有像540px和600px这样的奇葩。在设置了<meta />标签之后,device-width值能够用window.innerWidth来获取device-width值。
dpi(Dots Per Inch),有时也叫作ppi(Point Per Inch),翻译过来也叫像素密度,表示设备每英寸所占有的像素数;数值越高,即表明显示屏可以以越高的密度显示图像。(注:这里的像素,指的是device pixels。)DPI的计算公式:
有意思的是,这个值比苹果官网上公布的326还有高一点点。
其中,PPI在120-160之间的手机被归为低密度手机,160-240被归为中密度,240-320被归为高密度,320以上被归为超高密度(Apple给了它一个上流的名字——retina)。
这些密度对应着一个特定的缩放比例值,拿咱们最熟悉的iphone4或4s来讲,它们的PPI是326,属于超高密度的手机。当咱们书写一个宽度为320px的页面放到iphone中显示,你会发现,它居然是满宽的。这是由于,页面被默认放大了两倍,也就是640px,而iphone4或4s的宽,正是640px。
DevicePixelRadio,定义:window.devicePixelRatio是设备上物理像素(也就是device-width)和设备独立像素(device-independent pixels,即dips)的比例。公式表示就是:window.devicePixelRatio = 物理像素/dips
Android 和 iPhone 中,都有一个占整个屏幕大小的换算单位,Android 中叫 dip 或 dp,iPhone 中叫 point。Dip,就是device independent pixels,设备独立像素。而设备的物理像素和 dip 的比例就是 devicePixelRatio,此值能够经过 window.devicePixelRatio 属性获取。
据我查找到的一些资料显示,这里的独立像素的值其实就是device-width值。这个值也就是咱们平时在手机上布局用的宽度,固然是在设置了<meta />标签的前提下。
这里为何提到devicePixelRatio这个概念呢?
由于当devicePixelRatio=1.5的时候,也就是说当屏幕分辨率宽与device-width的比值为1.5时,某些手机自带的浏览器(特别是三星手机出如今最多)会出现1px的线解析成2px的bug,可是经测试同一部手机上安装的UC浏览器通常不会有这个bug。关于这个bug,网上有一篇文章作了比较好的解释:
https://www.imququ.com/post/devicepixelratio-and-border-width.html
注:文章不少知识引用了《移动webapp开发必备知识》和《什么是viewport,为啥须要viewport》,连接分别是:
http://www.qianduan.net/mobile-webapp-develop-essential-knowledge.html
http://www.myexception.cn/mobile/428756.html
还有这篇: http://www.quirksmode.org/blog/archives/2010/04/a_pixel_is_not.html
Sanding整理