[译文]此像素非彼像素,非彼像素

这是 一篇 2010 年的文章,很老了。翻译完这篇文章后,我感觉对于移动网页的开发。我多想了两个问题:图片变模糊?字体使用 em 而不是像素?这根本就不是一开始就应该担心的事情。作为网页开发人员,我只要知道能从手机屏幕上得到多大的使用空间就行了,其他问题都会顺其自然的发现并解决的。还有一点:当设置 <meta name="viewport" width="device-width"> 后,1 CSS 像素等于 1 设备像素了,也就是说 CSS 像素基本就等同于设备像素了。

新的 iPhone 即将面世,它采用 960x640,而不是 480x320。昨天 John Gruber 解释了苹果为什么要这么做。他也想知道这会给网页开发者带来什么后果。

碰巧我最近也在跨浏览器地研究手机的宽度和高度。并且可以合理的确定,这些变化对网页开发者的影响仅有 1%。

这剩下的 1% 是个很棘手的问题,但苹果可以通过插入一个中间像素层(intermediate layer of pixels)来解决这个问题(John 提到在 Android 中已经存在这个层了)。

网页开发者需要的是什么?

我知道网页开发者的关注点在哪里----CSS 像素----也就是在 CSS 声明里的"像素",比如:width: 300pxfont-size: 14px

其实,CSS 像素跟实际的设备像素密度(actual pixel density of the device)没有关系,甚至与中间像素层都没有关系。它们本质上是专门为网页开发者创建的抽象单元(abstract construct)。

我们拿缩放(zooming)来通俗地解释上面这句话。当用户做放大操作时,width: 300px 的元素会占据越来越多的屏幕空间,于是使用设备(物理)像素测量时就变得越来越宽。但以 CSS 像素的角度考虑,元素的宽度始终保持在 300px。这里的缩放效果根据需要扩张了 CSS 像素。

当缩放因子(zooming factor)是 100% 的时候,1 CSS 像素等于 1 设备像素(虽然即将到来的中间像素层会取代设备像素的位置)。下面的图片就描述了缩放 100% 的情况,看不到效果的原因,1 CSS 像素和 1 设备像素完全重叠了。

1 CSS 像素和 1 设备像素完全重叠图

(需要提醒你的是,"缩放 100%"在 Web 开发中没有什么意义。缩放级别对我们来说不重要,我们需要知道的是现在有多少 CSS 像素容纳在屏幕上。)

下面两张图片显示了当用户做缩小、放大操作时发生的情况。第一张图片显示的是当用户缩小时的设备像素(深蓝色背景)和 CSS 像素(浅蓝色前景)----CSS 像素变小了,1 设备像素交叠了几个 CSS 像素;第二张图片显示的是用户放大时的设备像素和 CSS 像素----1 CSS 像素交叠了几个设备像素。

用户做缩小操作图

用户做放大操作图

因此,width: 300px 的元素总是 300 CSS 像素宽,而它等同于多少设备像素则取决于缩放因子。

(在手机上,使用 screen.width 除以 window.innerWidth 就可以得到缩放因子。但这存在浏览器兼容问题,希望在不远的将来有关于这方面的完整报告出现。作为一名网页开发者如果对缩放因子不关注的话,但要知道设备屏幕里到底可以容纳多少(设备或 CSS)像素。)

这个系统不会改变。如果改变了,所有针对 iPhone 优化的网站都会立即废掉。这是苹果不惜一切代价要避免的。

因此,一个完全缩小的网站仍然显示为 980 CSS 像素,它等于多少设备像素对我们来说不重要。

棘手的问题

有两个棘手的问题:device-width 媒体查询(media query)和 <meta name="viewport" width="device-width"> 标签。这两者都是与设备像素协作的,而不是 CSS 像素。因为它表达的是页面上下文,而不是内部的 CSS。

媒体查询

device-width 媒体查询测量设备宽度,以设备像素统计。width 媒体查询测量的是整个页面的宽度,以 CSS 像素统计,原因我以后解释,在 iPhone 上 width 至少是 980px。

device-width 和 width 的介绍

device-width 媒体查询的工作方式如下:

div.sidebar {
	width: 300px;
}

@media all and (max-device-width: 320px) {
	// 设备宽度小于 320px 时使用的样式
	div.sidebar {
		width: 100px;
	}
}

现在侧边栏是 300 CSS 像素宽,当设备宽度小于 320px 时,就变成 100 CSS 像素宽了。

顺便提一下,理论上可以使用厘米或者英寸来查询设备屏幕(@media all and (max-device-width: 9cm))。不幸的是,包括 iPhone 在内的设备对此的支持都不太好。这儿的问题是,像英寸这样的物理单位(physical units)通常转换为 CSS 像素。我测试了迄今为止所有的浏览器,测出 width: 1in 基本等于 width: 96px。所以这些媒体查询是不可靠的。

<meta> 标签

一般来说 <meta name="viewport" content="width=device-width"> 很有用。这个标签最开始是苹果专有的,现在越来越多的浏览器都支持了,它实际的布局视图(layout viewport)正好适合设备。

那什么是布局视图?浏览器使用百分比宽度计算元素尺寸、并且使用 CSS 像素计算的一块区域。例如 div.sidebar {width: 20%}。它通常比设备屏幕大些:在 iPhone 上是 980px,在 Opera 上是 850px,在 Android 上是 800px 等。

layout viewport 图

使用了 <meta name="viewport" content="width=device-width"> 后,布局视图的宽度被限制为设备像素所表现的设备宽度。在 iPhone 中是 320。

没有 meta 标签的情况图

这样设置后,页面就会变得足够窄以适应屏幕大小。下面这张图片是没有使用 CSS width 语句和 <meta> 标签的情况,整个设备屏幕延伸到布局视图的可用宽度。

这或许不是你想要的,你希望堂文字在屏幕上合适的显示,这就是 <meta name="viewport" content="width=device-width"> 要完成的工作----整个视口缩小(在 iPhone 中是 320px),文字得以合适的显示。

使用了 meta 标签的情况图

苹果的变化

现在,苹果的分辨率变化对 device-width 媒体查询和 <meta> 标签会造成什么影响?我还不清楚,但我认为对网页开发人员不会有任何改变。

<meta> 标签

<meta> 标签最容易解释。苹果特意发明了它,是为了让人们能够在 iPhone 屏幕上适用他们的内容,并把它推给了开发者。就是说,现在 <meta> 标签读出来的设备宽度是无法改变的。

事实上,Nexus One 已经为苹果公司开辟了一条新的道路。其官方屏幕宽度(纵向模式)是 480px,但是当你使用 <meta>标签查询时,显示屏幕宽度 320px,也就是官方宽度的 2/3。如果我理解正确的话,这就是 John Gruber 所说的关于 Nexus 显示缺少一个子像素,也就是少了 1/3 的像素。这正好符合 Nexus 对 ` 标签的准确解释。

Google 已经插入了一个被称为 dips 的图层,即设备独立像素(device-independent pixels)。此层位于官方屏幕大小和 CSS 像素(网页开发人员接触的)之间。

我期待新版 iPhone 复制 Nexus 的方式,当使用 <meta> 标签进行媒体查询时,报告出来的屏幕尺寸是 320px(也就是分辨率宽度的一半)。之所以不是三分之二,是因为新版 iPhone 像素密度高于 Nexus。

媒体查询

这使得 device-width 媒体查询成为唯一的问题区域。在 Nexus 上它使用 480px 作为屏幕宽度,但 320px 可能更合适。我们得看看苹果是怎么做的。

更为根本的问题是,dips 是否将用于媒体查询。总的来说,对于网页开发者来说,正式的设备大小不重要,而是想知道我们能从屏幕上得到多少内容,而且 dips 好像是最适合的。

不幸的是,Nexus 现在没那么做。媒体查询的设备宽度仍显示 480px,而不是 320px。但也许苹果可以为网页开发人员解决这个问题。

所以,现在的情况是,对于正常的一个 Web 网站我们清楚,对 <meta> 标签的使用我们也清楚。但遇到媒体查询时,我们就不清楚了。

敬请关注。

posted @ 2017-10-24 15:27  Hi!张宝  阅读(249)  评论(0编辑  收藏  举报