说正事儿。准备在近期的几篇里集中翻译学习一下"响应式Web设计"的相关话题,包括概念、实践方式、案例及观点讨论等方面。相比于从前作的文档译文,这些文章篇幅要长的多(甚至要加分页了!),今天放上的这篇几乎花掉了两天的"闲暇时间";对耐力是个考验,努力提升喽。废话结束,here we go.javascript
眼下,几乎每一个新客户都但愿他们的网站能够有专门的移动设备版本。最完美的状况呐,就是为iPhone、iPad、黑莓、Kindle……各自打造一款——页面分辨率还必须兼容任何设备。谁知道将来5年内咱们还须要为多少新发明的设备设计开发不一样版本的页面?这种疯狂何时算个头?css
在Web设计和开发领域,很快的,咱们将会没法跟上设备与分辨率革新的步伐。对于多数网站来讲,为每种新设备及分辨率建立其独立的版本根本就是不切实际的;结果就是,咱们将会赢得使用某些设备的用户群,而失去那些使用其余设备的用户。不过,或许会有另一种方式,能够帮助咱们避免这种状况的发生。html
响应式Web设计(Responsive Web design)的理念是,页面的设计与开发应当根据用户行为以及设备环境(系统平台、屏幕尺寸、屏幕定向等)进行相应的响应和调整。具体的实践方式由多方面组成,包括弹性网格和布局、图片、CSS media query的使用等。不管用户正在使用笔记本仍是iPad,咱们的页面都应该可以自动切换分辨率、图片尺寸及相关脚本功能等,以适应不一样设备;换句话说,页面应该有能力去自动响应用户的设备环境。这样,咱们就能够没必要为不断到来的新设备作专门的版本设计和开发了。java
响应式Web设计的概念node
Ethan Marcotte曾经在A List Apart发表过一篇文章"Responsive Web Design",文中援引了响应式建筑设计的概念:jquery
最近出现了一门新兴的学科——"响应式建筑(responsive architecture)"——提出,物理空间应该能够根据存在于其中的人的状况进行响应。结合嵌入式机器人技术以及可拉伸材料的应用,建筑师们正在尝试建造一种能够根据周围人群的状况进行弯曲、伸缩和扩展的墙体结构;还可使用运动传感器配合气候控制系统,调整室内的温度及环境光。已经有公司在生产"智能玻璃":当室内人数达到必定的阀值时,这种玻璃能够自动变为不透明,确保隐私。css3
将这个思路延伸到Web设计的领域,咱们就获得了一个全新的概念。为何必定要为每一个用户群各自打造一套设计和开发方案?和响应式建筑类似,Web设计一样应该作到根据不一样设备环境自动响应及调整。git
显然,咱们没法也无需使用运动传感器或是机器人技术,响应式Web设计更多须要的是抽象思惟。好在,一些相关的概念已经获得了实践,好比液态布局、帮助页面从新格式化的media queries和脚本等。可是响应式Web设计不只仅是关于屏幕分辨率自适应以及自动缩放的图片等等,它更像是一种对于设计的全新思惟模式。github
调整分辨率web
不一样的设备都有各自的屏幕分辨率、清晰度以及屏幕定向方式,不断被研发着的各类新设备也将带来新的屏幕尺寸规格。有些设备基于横屏(portrait),有些是竖屏(landscape),甚至还有正方形;对于日益流行的iPhone、iPad及其余一些智能手机、平板电脑,用户还能够经过转动设备来任意切换屏幕的定向方式。怎样才能作到让一种设计方案知足全部状况?
要想作到同时兼容横、竖屏(用户还有可能在页面加载的过程当中切换方向),咱们就必须考虑N种屏幕尺寸规格。诚然,咱们能够将这些规格划分为几个大类,而后为每一类作一种方案,确保该方案至少在本组中尽可能具备弹性。但即便这样,结果也将是无比焦虑的,谁知道某类设备在5年以后的占有率是多少?并且不少用户甚至不去将浏览器的窗口最大化;相似这样的变数,咱们还要考虑多少呢?
Morten Hjerde和他的同事们对2005至2008年市场中的400余种移动设备进行了统计(查看报告),下图展现了大体的统计结果:
在08年以后,更多更有表明性的新设备问世并普及了。显然,咱们不能够沿着"多方案"的思路继续走下去;那么咱们应该怎样作呢?
部分解决方案:一切弹性化
几年前,弹性布局(flexible layout)几乎是一种奢侈品,所谓弹性,也只是体如今竖排布局以及字号等方面;图片始终能够轻易的破坏页面结构,并且即便是哪些弹性的元素结构,在很极端的状况下,仍会破坏布局。因此,所谓的弹性布局其实并不是那样弹性,它有时甚至不能适应台式机与笔记本的屏幕分辨率差别,更不用说手机等移动设备了。
如今,咱们能够经过响应式的设计和开发思路让页面更加"弹性"了。图片的尺寸能够被自动调整,页面布局再不会被破坏。虽然永远没有最完美的解决方案,但它给了咱们更多选择。不管用户切换设备的屏幕定向方式,仍是从台式机屏幕转到iPad上浏览,页面都会真正的富有弹性。
在前文提到的Ethan Marcotte的文章中,他经过一个实例展现了响应式Web设计在页面弹性方面的特性:
该实例的实现方式完美的结合了液态网格和液态图片技术,而且聪明的在正确的地方使用了正确的HTML标记。"液态网格"是一种很常见的实践方式;对于"液态图片"技术,下面的文章作了不错的介绍:
Hiding and Revealing Portions of Images
Creating Sliding Composite Images
Foreground Images That Scale With the Layout
说到建立液态页面,最好看看Zoe Mickley Gillenwater的那本《Flexible Web Design: Creating Liquid and Elastic Layouts with CSS》,或是下载个样章先:"怎样建立弹性图片"。另外,Zoe的这篇"Essential Resources for Creating Liquid and Elastic Layouts."提供了很多关于建立弹性网格和布局的教程、资源、创意指导和最佳实践方式。
从技术角度讲,虽然听上去这些都简单可行,但它比"将这些功能结合在一块儿"要复杂些。举个例子,仔细观察Ethan Marcotte提供的实例中的logo图片:
若是咱们将浏览器窗口不断调小,会发现logo图片的文字部分始终会保持同比缩小,保证其完整可读,而不会和周围的插图同样被两边裁掉。因此整个logo其实包括两部分:插图做为页面标题的背景图片,会保持尺寸,但会随着布局调整而被裁切;文字部分则是一张单独的图片。
<h1 id="logo"> <a href="#"><img src="site/logo.png" alt="The Baker Street Inquirer" /></a> </h1>
其中,<h1>元素使用插图做为背景,文字部分的图片始终保持与背景的对齐。
这个实例小小的展现一下响应式Web设计的思路。不过这点小努力还不足以免整个布局在小尺寸窗口中变的过窄或太短,而且logo文字最终会变的小到难以识别,背景图片也会被过多的裁切。
弹性图片
响应式Web设计的思路中,一个重要的因素是怎样处理图片方面的问题。有不少同比缩放图片的技术,其中有很多是简单易行的。其中,由Richard Rutter最早尝试的一种作法比较流行,即便用CSS的max-width属性。这个方法在Ethan Marcotte的液态图片一文中也有提到。
img { max-width: 100%;}
只要没有其余涉及到图片宽度的样式代码覆盖掉这一行规则,页面上全部的图片就会以其原始宽度进行加载,除非其容器可视部分的宽度小于图片的原始宽度。上面的代码确保图片最大的宽度不会超过浏览器窗口或是其容器可视部分的宽度,因此当窗口或容器的可视部分开始变窄时,图片的最大宽度值也会相应的减少,图片自己永远不会容器边缘隐藏和覆盖。实际上,就像Jason Grigsby在他的CSS Media Query for Mobile is Fool's Gold一文中提到的,"液态图片背后的思路,就是不管什么时候,都确保在其原始宽度范围内,以最大的宽度同比完整的显示图片。咱们没必要在样式表中为图片设置宽度和高度,只须要让样式表在窗口尺寸发生变化时辅助浏览器对图片进行缩放。" 一种简而美的方法。
图片自己的分辨率及加载时间是另一个须要考虑的问题。虽然经过上面的方法,能够很轻松的缩放图片,确保在移动设备的窗口中能够被完整浏览,但若是原始图片自己过大,便会显著下降图片文件的下载速度,对存储空间也会形成没有必要的消耗。
响应式图片
由Filament Group提出的"响应式图片"技术思想,有助于解决上面提到的问题:不只要同比的缩放图片,还要在小设备上下降图片自身的分辨率。能够看下demo页面先。
这个技术的实现须要使用几个相关文件,咱们能够在Github上获取。包括一个JavaScript文件(rwd-images.js),一个.htaccess文件,以及一些范例资源文件。具体使用方法能够参考Responsive Images的说明文档。大体的原理是,rwd-images.js会检测当前设备的屏幕分辨率,若是是大屏幕设备,则向页面head部分中添加BASE标记,并将后续的图片、脚本和样式表加载请求定向到一个虚拟路径"/rwd-router"。当这些请求到达服务器端,.htacces文件会决定这些请求所须要的是原始图片仍是小尺寸的"响应式图片",并进行相应的反馈输出。对于小屏幕的移动设备,原始尺寸的大图片永远不会被用到。
这项技术支持多数的现代浏览器,包括IE8+、Safari、Chrome和Opera,以及这些浏览器的移动设备版本;在FireFox及一些旧浏览器中,则会优雅降级:咱们仍可获得小图片的输出,但同时,原始大图也会被下载。
禁用iPhone中的图片自动缩放
在iPhone及iPod Touch中,页面会被自动的同比例缩小至最适合屏幕大小的尺寸,x轴不会产生滚动条,用户能够上下拖拽浏览所有页面,或在须要的时候放大页面的局部。这里会产生一个问题,即便咱们运用响应式Web设计的思想,专门为iPhone的小屏输出小图片,它一样会随着整个页面一块儿被同比例缩小,以下图左侧所示。
咱们可使用苹果专有的一些meta标记来解决相似的问题。在页面的<head>部分添加如下代码(详情能够参考Think Vitamin的相关文章):
<meta name="viewport" content="width=device-width; initial-scale=1.0">
将initial-scale的值设定为"1",便可覆写默认的缩放方式,保持原始的尺寸及比例。更多关于viewport meta标记的用法,能够参考苹果官方的文档。
打造布局结构
当页面所须要适应的不一样设备的屏幕尺寸差别过大时,除了图片方面,咱们也应该考虑到整个布局结构的响应式调整;咱们可使用独立的样式表,或者更有效的,使用CSS media query。这不会引发多大的麻烦,多数样式设定不会被影响和改变,只有一些特定的元素会经过浮动、宽度和高度等的设置来改变位置。
咱们可使用一个默认主样式表来定义页面的主要结构元素,好比#wrapper、#content、#sidebar、#nav等的默认布局方式,以及一些全局性的配色和字体方案。
咱们能够监测页面布局随着不一样的浏览环境而产生的变化,若是它们变的过窄太短或是过宽过长,则经过一个子级样式表来继承主样式表的设定,并专门针对某些布局结构进行样式覆写。咱们来看下代码示例:
下面的代码能够放在默认主样式表style.css中:
/* Default styles that will carry to the child style sheet */ html,body{ background... font... color... } h1,h2,h3{} p, blockquote, pre, code, ol, ul{} /* Structural elements */ #wrapper{ width: 80%; margin: 0 auto; background: #fff; padding: 20px; } #content{ width: 54%; float: left; margin-right: 3%; } #sidebar-left{ width: 20%; float: left; margin-right: 3%; } #sidebar-right{ width: 20%; float: left; }
下面的代码能够放在子级样式表mobile.css中,专门针对移动设备进行样式覆写:
#wrapper{ width: 90%; } #content{ width: 100%; } #sidebar-left{ width: 100%; clear: both; /* Additional styling for our new layout */ border-top: 1px solid #ccc; margin-top: 20px; } #sidebar-right{ width: 100%; clear: both; /* Additional styling for our new layout */ border-top: 1px solid #ccc; margin-top: 20px; }
大体的视觉效果以下图所示:
Media Queries
CSS3支持CSS2.1所支持的全部媒体类型,例如screen、print、handheld等,同时添加了不少涉及媒体类型的功能属性,包括max-width(最大宽度)、device-width(设备宽度)、orientation(屏幕定向,横屏或竖屏)和color。在CSS3发布以后出现的新玩具,如iPad或Android相关设备,均可以完美的支持这些属性。因此咱们能够经过media query为新设备设置独特的样式,而忽略那些不支持CSS3的台式机中的旧浏览器。
在Ethan的文章中,咱们能看到一段media query使用实例:
<link rel="stylesheet" type="text/css" media="screen and (max-device-width: 480px)" href="shetland.css" />
代码自己能够很好的说明工做机制:若是页面经过屏幕呈现(非打印一类),而且屏幕宽度不超过480px,则加载shetland.css样式表。要了解更多关于CSS3媒体新属性的信息,能够参考"The Orientation Media Query"一文。
咱们能够建立多个样式表,以适应不一样设备类型的宽度范围。Ethan的文章中的"Meet the media query"部分有更多的范例及解释。更有效率的作法是,将多个media queries整合在一个样式表文件中:
/* Smartphones (portrait and landscape) ----------- */ @media only screen and (min-device-width : 320px) and (max-device-width : 480px) { /* Styles */ } /* Smartphones (landscape) ----------- */ @media only screen and (min-width : 321px) { /* Styles */ } /* Smartphones (portrait) ----------- */ @media only screen and (max-width : 320px) { /* Styles */ }
上面的代码来自于Andy Clark建立的能够兼容各类主流设备的免费模板。这样整合多个media queries于一个样式表文件的方式,与经过media queries调用不一样样式表的方式之间的区别与联系,能够参考"Hardboiled CSS3 Media Queries"一文。
CSS3 Media Queries
上面演示的一些代码范例是CSS2.1与CSS3通吃的。如今让咱们来看看怎样使用CSS3专有的media queries功能来建立响应式Web设计。其中某些方法在当前就有切实的使用价值,不久的未来则必定会所有派上用场。
min-width和max-width这两个属性很靠谱。经过min-width的设置,咱们能够在浏览器窗口或设备屏幕宽度高于这个值的状况下,为页面指定一个特定的样式表;max-width则反之。
下面的几个示例中,咱们使用的是将多个media queries整合在单同样式表中进行编码的句法。如前文所述,这样作更加高效,减小请求数量。
@media screen and (min-width: 600px) { .hereIsMyClass { width: 30%; float: right; } }
上面代码中定义的类(hereIsMyClass)只有在浏览器或屏幕宽度超过600px时才会有效。
@media screen and (max-width: 600px) { .aClassforSmallScreens { clear: both; font-size: 1.3em; } }
而这段代码的做用则相反:aClassforSmallScreens类只有在浏览器或屏幕宽度小于600px时才会有效。
能够看出min-width和max-width能够同时判断设备屏幕尺寸与浏览器实际宽度。有些时候,咱们但愿经过media queries做用于某种特定的设备,而忽略其上运行的浏览器是否因为没有最大化而在尺寸上与设备屏幕尺寸产生不一致的状况。这时,咱们须要使用min-device-width与max-device-width,用来判断设备自己的屏幕尺寸。
@media screen and (max-device-width: 480px) { .classForiPhoneDisplay { font-size: 1.2em; } }
@media screen and (min-device-width: 768px) { .minimumiPadWidth { clear: both; margin-bottom: 2px solid #ccc; } }
还有一些其余方法,能够帮咱们有效的使用media queries锁定某些指定的设备。能够参考下面两篇出自Thomas Maier的文章:
CSS for iPhone 4 (Retina display)
对于iPad来讲,orientation属性尤为有用。它的值能够是landscape(横屏)或portrait(竖屏)。
@media screen and (orientation: landscape) { .iPadLandscape { width: 30%; float: right; } }
@media screen and (orientation: portrait) { .iPadPortrait { clear: both; } }
不幸的是,这个属性目前确实只在iPad上有效。对于其余能够转屏的设备,譬如iPhone,可使用min-device-width和max-device-width来变通实现;详情能够参考"Determine iPhone orientation using CSS"一文。
咱们还能够将上述属性组合使用,来锁定某个屏幕尺寸范围:
@media screen and (min-width: 800px) and (max-width: 1200px) { .classForaMediumScreen { background: #cc0000; width: 30%; float: right; } }
上面的代码能够做用于浏览器窗口或屏幕宽度在800px至1200px之间的全部设备。
其实,不少设计师和开发者仍会选择使用多个样式表的方式来实现media queries。若是从资源的组织和维护的角度出发,其益处确实高于效率的损耗的话,那么这样作也彻底不坏:
<link rel="stylesheet" media="screen and (max-width: 600px)" href="small.css" /> <link rel="stylesheet" media="screen and (min-width: 600px)" href="large.css" /> <link rel="stylesheet" media="print" href="print.css" />
因此呐,凡事没有绝对,最好根据实际状况决定使用media queries的方式。好比,对于iPad,咱们能够将多个media queries直接写在一个样式表中。由于iPad用户随时有可能切换屏幕定向,这种状况下,要保证页面在极短的时间内响应屏幕尺寸的调整,咱们必须选择效率最高的方式。
JavaScript
JavaScript也是咱们的武器之一,特别是当某些旧设备没法完美支持CSS3的media query时,它能够做为后备支援。幸运的是,已经有专门的JS库来帮助旧浏览器(IE 5+,Firefox 1+,Safari 2等)支持CSS3的media queries。使用方法很简单,下载css3-mediaqueries.js并在你的页面中调用它。
而下面的代码则演示了怎样使用简单的几行jQuery代码来检测浏览器宽度,并为不一样的状况调用不一样的样式表:
<script type="text/javascript" src="http://ajax.googleapis.com/ajax/libs/jquery/1.4.4/jquery.min.js"></script> <script type="text/javascript"> $(document).ready(function(){ $(window).bind("resize", resizeWindow); function resizeWindow(e){ var newWindowWidth = $(window).width(); // If width width is below 600px, switch to the mobile stylesheet if(newWindowWidth < 600){ $("link[rel=stylesheet]").attr({href : "mobile.css"}); } // Else if width is above 600px, switch to the large stylesheet else if(newWindowWidth > 600){ $("link[rel=stylesheet]").attr({href : "style.css"}); } } }); </script>
相似这样的解决方案还有不少。因此咱们要清楚,media queries不是一个绝对惟一的答案,它只是一个以纯CSS方式实现响应式Web设计思路的手段。借助JavaScript,咱们则能够实现更多的变化。这篇"Combining Media Queries and JavaScript"向咱们展现了JavaScript配合media queries的更多细节信息。
显示或隐藏内容
经过前文的学习,咱们已经了解到,对于响应式Web设计,同比例缩减元素尺寸以及调整页面结构布局,是两个重要的方式方法。可是对于页面中的文字内容信息来讲,则不能简单的只从"同比缩小"和"调整布局结构"这两方面去处理。对于手机等移动设备来讲,在文字内容方面,已经有了不少最佳实践方式和指导原则:简化的导航、更易聚焦的内容、以信息列表代替传统的多行文案内容等。

响应式Web设计的思想,一方面要保证页面元素及布局具备足够的弹性,来兼容各种设备平台和屏幕尺寸;另外一方面,则是加强可读性和易用性,帮助用户在任何设备环境中都能更容易的获取最重要的内容信息。
有一条样式代码,咱们已经使用了多年:
display: none;
咱们能够在一个针对某类小屏幕设备的样式表中使用它来隐藏掉页面中的某些块级元素,也可使用前文的方法,经过JS判断当前硬件屏幕规格,在小屏幕设备的状况下直接为须要隐藏的元素添加工具类class。好比,对于手机类设备,咱们能够隐藏掉大块的文字内容区,而只显示一个简单的导航结构,其中的导航元素能够指向详细内容页面。
注意,不要使用visibility: hidden的方式,由于这只能使元素在视觉上不作呈现;display属性则可帮助咱们设置整块内容是否须要被输出。对于移动设备来讲,避免这些没必要要的资源浪费仍是很重要的。咱们来看一个简单的示例:

图中上半部分是大屏幕设备所显示的完整页面,下面的则是该页面在小屏幕设备的呈现方式。页面HTML代码以下:
<p class="sidebar-nav"><a href="#">Left Sidebar Content</a> | <a href="#">Right Sidebar Content</a></p>
<div id="content">
<h2>Main Content</h2>
</div>
<div id="sidebar-left">
<h2>A Left Sidebar</h2>
</div>
<div id="sidebar-right">
<h2>A Right Sidebar</h2>
</div>
下面是默认的主样式表,其中,咱们要隐藏掉连接导航部分(sidebar-nav),由于默认样式适用的设备屏幕会足够大,足够显示包括两个侧边栏在内的全部内容。
#content{
width: 54%;
float: left;
margin-right: 3%;
}
#sidebar-left{
width: 20%;
float: left;
margin-right: 3%;
}
#sidebar-right{
width: 20%;
float: left;
}
.sidebar-nav{display: none;}
下面是用于小屏幕移动设备的样式表代码。如今,咱们要隐藏掉两个侧边栏,并使sidebar-nav显示出来。借助JavaScript,当用户点击sidebar-nav中的连接时,对应的侧边栏能够恢复显示。固然,触发恢复显示的方式有不少种,便可以经过JS改变侧边栏的display属性值,也能够为其添加额外的布局样式。
#content{
width: 100%;
}
#sidebar-left{
display: none;
}
#sidebar-right{
display: none;
}
.sidebar-nav{display: inline;}
如今,咱们的页面已经能够随着设备和屏幕规格的变动,响应式的作到元素的同比缩放、布局结构的改变、内容的优化调整。特别是对于手机设备,咱们还要在实践过程当中注意一些该类设备共有的设计指导原则。好比,针对手机设备,使用一个特定的样式,将页面原有的文字导航元素变为更易操做的图标形式。下面的一些文章资源可做参考阅读:
Mobile Web Design Trends For 2009
7 Usability Guidelines for Websites on Mobile Devices
触屏与鼠标
触屏设备已经成为主流。虽然目前多数触屏设备仍是小屏幕类型的产品,好比手机,可是市场上愈来愈多的大屏幕设备也开始使用触屏技术;且不说iPad一类的平板电脑,就连一些笔记本和台式机也加入了这一行列。好比HP Touchsmart tm2t,即便用传统的键鼠设备,同时也加入了触屏技术。

相比于传统的基于鼠标指针的互动,触屏技术显然带来了大相径庭的交互方式与相应的设计规范;二者又有各自所适用的领域。所幸,要使咱们的设计方案同时知足这两类设备的规范,并不是一件难事,只是有些地方须要注意。好比,触屏设备没法反映CSS定义的hover行为及相应的样式,由于它没有鼠标指针的概念,手指点击就是click行为。因此不要让任何功能依赖于对hover状态的触发。
有兴趣的话,能够读读这篇"Designing for Touchscreen",这里提到的不少建议即有利于改进针对触屏设备的设计方式,同时也不会削弱传统键鼠设备上的用户体验。好比,放在页面右侧的导航列表能够对触屏设备的用户更加友好。由于多数人习惯用右手点击操做,而左手负责握住设备;这样,放在右侧的导航列表即方便右手的点击,又能够避免被握着设备的左手不当心触碰到。而这一点与键鼠设备用户的习惯彻底不矛盾。
做者:C7210
文章来源:beforweb.com