JavaScript-像素

745 阅读6分钟

像素

设备像素(device pixel)

设备像素是物理概念,指的是设备中使用的物理像素(Physic pixel),单位用px表示。

在同样一个设备上,每1个设备像素所代表的物理长度(如英寸)是固定不变的
在不同的设备之间,每1个设备像素所代表的物理长度(如英寸)是可以变化的

设备分辨率

设备分辨率的单位就是设备像素(px)。

屏幕是由很多像素点组成的,各像素点通过发出不同颜色的光来呈现屏幕的色彩。比如 iPhone4 的屏幕分辨率为 640×960,就表示屏幕的横向有 640 个像素点,纵向有 960 个像素点。

在同一个手机或电脑设备上,它的设备像素是固定的,这是厂商在出厂时就设置好了的————即一个设备的分辨率是固定不变的

所以调整电脑屏幕的分辨率,那只是你的眼睛在欺骗你。

系统给你推荐的是1366px768px的分辨率,你知道意味着什么吗?没错,微软在这块屏幕上横向设置了768个像素,竖向设置了1366个像素。再怎么拉扯,这个数字是不会变了。那么,为啥我还能调整分辨率呢?我要是调整到800px600px,按照定义,横向就是600个像素,竖向就是800个像素了啊。其实呢,你把分辨率调成800600,系统就会分配给你800600个有效像素个数,也就是真实的色彩块。其他的个数呢,就由系统自作主张,通过一系列运算给你一个模拟色彩块,填充成正好1366*768个色彩块。这些拿来充数的像素块,和真实的像素块放到一起。就好比一个正规军,里面掺了很多杂牌军一样,只能是队伍不好带了。

CSS像素(css pixel)

CSS 像素 是 Web 编程的概念,本质上是为我们 Web 开发者创建的一个抽象结构,单位用px表示。

在同样一个设备上,每1个CSS像素所代表的设备像素是可以变化的
在不同的设备之间,每1个CSS像素所代表的设备像素是可以变化的

所以,CSS像素是一个相对单位,相对的是物理像素(device pixel)

设备独立像素(Device independent Pixel)

随着高设备分辨率的屏幕出现,理论上将同一个图片,在高设备分辨率的屏幕上会显得更小。但是实际上不同分辨率的屏幕上,我们看到的图片相对屏幕的比例是类似的。这是基于乔布斯在iPhone4上提出了Retina Display(视网膜屏幕)的概念,会把2x2个设备像素用来展示1像素,使画面更紧致,但是元素的大小没什么变化。

基于Retina Display,我们需要一个单位告诉屏幕,在屏幕上展示的元素大小是多少,这就是设备独立像素,也称为逻辑像素,简称dip。

缩放

缩放会引起CSS像素的变化——即引起每1个CSS像素所代表的物理像素变化。例如,当用户把页面放大一倍,那么css中1px所代表的物理像素也会增加一倍;反之把页面缩小一倍,css中1px所代表的物理像素也会减少一倍。

综上,页面缩放比例 = 物理像素/CSS像素

准确的说,这里应该是 页面缩放比例 = 设备独立像素/CSS像素

DPI&PPI

DPI(dots per inch)为打印机每英寸可以喷的墨汁点数,用于印刷行业中度量空间点的密度
PPI(pixels per inch)为屏幕每英寸的像素数量(即在一个对角线长度为1英寸的正方形内所拥有的像素数),用于度量计算机显示屏上像素的密度

目前PPI(主要是iOS)和DPI(比如在Android中)都会用在计算机显示设备的参数描述中,并且二者的意思是一样的,都是代表像屏幕素密度。显然 PPI(或DPI) 越高,屏幕显示效果越细腻。

屏幕像素密度,屏幕分辨率,屏幕尺寸三者的关系如下:

image

DPR

全称设备像素比(Device Pixel Ratio)。

在移动端浏览器中以及某些桌面浏览器中,window对象有一个devicePixelRatio属性,是设备上物理像素和设备独立像素的比例的比例。

公式表示就是:

window.devicePixelRatio = 物理像素 / 设备独立像素

DPR与PPI的关系

一般情况下是DPR = PPI/160

根据上述设备像素与CSS像素之间的关系、及DPR的官方定义,我们可以推断出:
一般情况下(页面缩放比例为100%时)CSS像素 =设备独立像素 = 逻辑像素

应用

devicePixelRatio为1.5

在 devicePixelRatio = 1.5 的设备上,如果边框被设置为奇数(用 x 表示),结果为下(具体可以点击此处):

  • 对于左右边框,如果距离屏幕左边的页面像素是偶数,则宽度显示为 1.5x+0.5;否则显示为 1.5x-0.5;
  • 对于上下边框,如果距离屏幕上边的页面像素是偶数,则宽度显示为 1.5x+0.5;否则显示为 1.5x-0.5;
  • 要让容器左右或上下边框显示为一致的宽度,容器 width 或 height 必须是奇数;

1px问题

有时会觉得1px在手机上会显得更粗些,从我的理解上说,感觉上更多是和设计师之间关于设计稿的理解。以iPhone6为例,设备分辨率是750x1334,设备独立像素为375x667,故DPR为2。

image.png 可以看到在web端设计稿中,元素(基于设备像素)的宽度为1px,而在iPhone6中,1设备像素等于0.5逻辑像素,故CSS需要写为0.5px。若CSS直接使用web设计稿中的1px,则会出现更粗些的问题。

当然解法方案很多,transform或者基于Viewport进行缩放,网上很多,这里就不过多描述。

CSS 和 图片

对于一张实际大小为100px * 100px(这里px指物理像素)图片,若设置width 和 height 都设了 100px(注意这里的px是css像素),实际占用了屏幕的像素数就是(假设设备像素比是 3)300x300px(注意这里的px指物理像素),那么图片变模糊了

所以在这种情况下,图片应做3倍尺寸的(即 300px * 300px)的。

此外,可以使用响应式图片srcset来根据不同的设备像素比来加载不同的图片。

媒体查询

媒体查询的px针对的为css像素。

@media all and (max-device-width: 320px) {}

Viewport

后续补充...

参考

  1. 前端:移动开发-像素、viewport
  2. 关于移动端适配,你必须要知道的
  3. 吃透移动端 1px|从基本原理到开源解决方案