CSS 相对/绝对(relative/absolute)定位系列(二)
//zxx:直接接上回
一、常见absolute布局的替代实现方案
absolute属性配合left/top/right/bottom属性具有极强的定位性。这种功能特性是如此的明显与强烈,可能会让页面重构人员很单纯的被这一特性“捕获”,而产生迷失。
一板一眼的描述可能难以理解,举个通俗点的例子吧:
一个脸蛋不错身材超好的姑娘穿上超PP的衣服后是如此的光艳动人,对于我们这类常年困居于深宅大院的光棍男来讲,这种美艳是如此的迷人,以至于我们的精力多集中在这沉鱼落雁的美貌上,而忽略了其他一些东西,例如知性,善良,贤惠等。很容易的,我们以后一想到此女子,第一反应就是“美貌”,至于其他,在如此美貌下已经不重要了。
此道理反映在web上就是,我们极易先入为主地认为absolute
的价值就是借助left
/top
属性来进行定位的。说句不严谨的话,目前估计超过90%的普通布局中的absolute
属性都是用在定位上了。恩,这个回头再说,这里还是看看一些常见的absolute
布局如何通过使用其他属性完成同样的布局效果。既然absolute
属性是拿来定位,我们只要使用其他属性定位就可以了。此时,自然而然想到了CSS中另外一个更加低调全能的定位属性margin
,下面的前两个例子都是使用margin
代替absolute
及相关属性。
京东商城首页标价定位
首先拿京东商城首页的一个标价样式举例,见下截图:
用小bug一看其code实现,果然是绝对定位+定位属性://zxx:小bug时我对firebug的昵称
@H_126_25@
要是我来实现,就不会使用absolute
属性,会使用margin
实现扩展性容错性更强的布局。
不管怎样,先看对比实现效果,您可以狠狠地点击这里:absolute/margin定位布局对比demo
下图为在IE7浏览器下的上下实现方式对比截图(默认):
可见使用margin
,可以实现与absolute
布局一样的效果,且CSS属性使用量折半,更为关键的是,布局的扩展性与容错性大大增强了。
在demo页面上的底部有两个测试布局扩展性与容错性的按钮,如下图,第一个按钮是改变标签的宽度,第二个按钮是改变父标签的posITion
属性值为static
:
我们点击第一个按钮改变dl
父标签的宽度后,结果absolute
定位的标价已经和图片远离了,而使用margin
定位的橙红色背景标价依旧坚挺地呆在原来的位置上,如下图所示:
点击第二个按钮改变父标签的position
属性为static
后,结果使用absolute
绝对定位的标价没有了束缚,直接跑到浏览器窗口的右下角去了,而margin
定位没有丝毫影响(如下图所示,截自Firefox3.6):
从上面两个简单的测试可以看出两种实现方式见扩展性和容错性方面的差异。
下面简单讲下相关布局的实现,以下是原来absolute
实现的HTML部分代码:
dl> dt class="p-img"> a href="##"> img width="130" height="130" src="http://img10.360buyimg.COM/n3/834/11752677-6197-4ffa-b4c0-e66d02640bad.jpg" /> /a> div class="p-PRice"> ¥999.00/div> /dt> dd class="p-name"> a href="##"> LG GD580 3G手机 300万像素 999返100元券!/a> /dd> /dl>
类名为”p-price”标签核心样式如下:
.p-price { position: absolute; bottom: 10px; right: 50px; ......
京东商城的实现,中规中矩,想这种带有覆盖效果的定位,使用absolute
定位估计是大部分页面重构人员的首选。但是,绝对定位之“绝对”一词本身就意味着其在扩展性方面的表现受限。如果我们要求更高,可以使用CSS代码量更少,扩展性更强的margin
布局。
其实现代码如下:
首先HTML部分需要添加一层block
水平的标签(其实可以不用加,只要让img
外面的a
标签block
水平显示即可),让标价与图片不会在一个line box中显示,同时将标价外面的div
标签改为inline水平元素的标签方便inline-block
化,于是,最后的HTML代码如下:
dl> dt class="p-img"> a href="##"> img width="130" height="130" src="http://img10.360buyimg.com/n3/834/11752677-6197-4ffa-b4c0-e66d02640bad.jpg" /> /a> div class="new-price-x"> span class="new-price"> ¥999.00/span> /div> /dt> dd class="p-name"> a href="##"> LG GD580 3G手机 300万像素 999返100元券!/a> /dd> /dl>
相关的核心的CSS代码如下:
.new-price-x { margin: -28px 0 0 74px; } .new-price { display: inline-block; ...... }
淘宝首页示例
下面再看另外一个例子,就是淘宝首页的滚动播放效果,使用是absolute
定位,通过改变top
属性值实现上下的滚动切换,如下图:
实际上,完全可以使用margin-top
属性代替这里的relative
+absolute
+top
属性组合。
您可以狠狠地点击这里:淘宝首页margin下的滚动播放demo
使用小bug一看demo页面的定位属性,啊,是margin-top
,如下截图所示:
就效果来说,margin-top
与绝对定位的切换是一样的,优点在于省了一点点的CSS代码量。但是,相对absolute
的动画切换,margin-top
值的改变会产生更强的回流(reflow
),就性能上而言,要比absolute
属性低。
究竟使用哪个,看您自己如何取舍了。
新浪微博示例
最后,拿新浪微博页面的主导航示例。
首先来看看为什么新浪微博的主导航要使用绝对定位。我想主要原因可能是半透明的纯色背景吧。
而IE浏览器下药实现opacity
效果需要使用filter
滤镜,然而opacity
属性的半透明效果不仅会影响到当前元素,所有的子元素也会跟着半透明,此时,如果导航内元素放在半透明化的div
内部显然容易死翘翘。所以,半透明背景层,与导航内容层不是父子关系,而是兄弟关系,导航内容覆盖于半透明背景上,就避免了导航内容被半透明化的危险。
而覆盖定位一般都离不开absolute
属性,所以,新浪微博的主导航使用了绝对定位。然而,这里的绝对定位使用我必须称赞一下,因为很难得的,这里的absolute
使用主要是利用了absolute
属性的破坏性(高宽占据空间为0
的特性),而不是利用其定位性(借助left
/top
等属性的定位)。
至于这里如何利用absolute
属性的破坏性实现自适应的布局,不想讲。有微博的自己用小bug看看,没微博的注册个。
就这里绝对定位的使用来讲,除了莫名的top
/right
属性外,还是不错的。然而,问题在于这里非要使用绝对定位吗?兼容性的半透明纯色效果非要用并行的两个标签错开重叠定位吗?父子关系不行吗?有句成语叫做“与时俱进”,要是几年前,可能还真得这么搞。但是现在,什么绝对定位啊,重叠啊,计算啊什么乱七八糟的东西完全不需要。就当没有什么半透明效果写,同样可以实现一样的效果。
同样的,关于这里的替代方法,我做了个demo,您可以狠狠地点击这里:新浪微博主导航无absolute实现demo
使用opacity
属性或是IE filter
半透明滤镜会让子元素跟着半透明。实际上对于半透明的纯色背景,有更佳的实现方法。下面是demo页面的替换实现方法的CSS代码:
.newheader .menu_c { background-color: rgba(0, 0, 0, .25); filter: progid:DXImageTransform.Microsoft.Gradient(startColorStr=#40000000,endColorStr=#40000000); }
现代浏览器使用CSS3 rgba
实现半透明背景色,IE浏览器使用渐变滤镜实现半透明。
HTML方面,原来的绝对定位的半透明div层直接删掉,此时相关的relative
属性等也可以一并去掉。HTML结构变得简单有层次,维护也更加方便了。
关于实现兼容性的半透明背景色,您可以参考我之前的“RGBA颜色与兼容性的半透明背景色”一文。所以具体使用,细节等这里就不多说,下图为前后两种半透明背景实现方式效果对比图:
二、absolute可以一个人战斗
如果在CSS的世界中没有left
/top
/right
/bottom
属性,absolute
的潜力估计会挖得深得多。
我们需要意识到,一个应用的position:absolut
e的元素,其实就只是个非常普通的元素,我感觉与应用了float:left
的差异仅仅在于宽度的缺失。为说明此观点,我做了个很简单的demo.
您可以狠狠地点击这里:absolute元素只是个普通的货demo
此demo默认如下图,可以看到浮动的高度缺失造成的塌陷:
点击示意的按钮后,可以发现图片还是那个图片,还在那个位置,还是那么的安静与优雅。唯一变化的就是文字们有的跑到它的下面了(宽度缺失)。
由此可见,absolute
属性只是个很普通的属性,跟float:left
是个近亲。一个是陨落凡间的恶魔,一个是天空中的恶魔。所以,很多时候,我们在普通布局中使用absolute
时候,只要设置position:absolute
就可以了,至于left
/top
之类的都是浮云,定位什么的就当作普通元素,使用margin
定位一样有着刮目的表现的。
三、absolute与left/top等属性之间的关系
单纯应用了absolute
属性的元素就是个普通元素,跟变身前的美少女战士一样。left
/top
等属性是具有变身性质的东西,是恶魔absolute
元素的翅膀。absolute
元素一旦应用了left
/top
等属性,就具有了飞翔的能力,奔向天空自由驰骋,如果没有relative
属性的限制,其会一直飞到天空的边缘(浏览器窗口),并且具有非常明确的方向性。
四、body标签是absolute元素自由的天空
来首小诗调节一下吧:
生命成可贵,
爱情价更高。
若为自由故,
两者皆可抛。
知道《美少女战士》吧,知道主人公水冰月(月野兔)吧,因为人家牛叉,所以为了保护地球,保护未来而战斗。知道《火影忍者》吧,你说要是把鸣人就限制在火影村,帮助老太太抓抓猫,帮助欧巴桑照看孩子,能有大成吗?人家是注定要肩负起忍者世界和平的职责的。
同样的,要是把绝对定位属性用在很深的DOM tree中,再用relative
限制住。其实就是把鸣人当作看孩子的人使用,虽然用的时候觉得很好用,但是实际上是埋没了绝对定位元素的才能。没有限制,给予足够的自由,广阔的天空才是绝对定位元素大放异彩,拯救人类的舞台。
一般而言,在web页面上,最宽广的天空莫过于body
标签,所以,在我看来,把绝对定位元素直接放在body标签下才是王道,才能最大限度的发挥绝对定位元素的才能。举个例子,淘宝首页顶部小横条上的下拉。
此下拉就是使用的绝对定位,但是却是深深地嵌入到DOM中的,如下图:
这种方法的好处在于简单,对于非IE6浏览器直接使用CSS就可以实现效果了。然而,将默认隐藏的绝对定位元素被relative
限制在很深的DOM节点中,弊处相当多:首先增加了DOM的复杂度,不利于维护;越深的DOM元素,造成了回流越强;因为父标签需要relative
限制,增加了CSS代码的消耗量;隐藏元素头部加载,延迟了页面的呈现速度;每个下拉几乎都要重新定位,其重用性受限。
如果是我,一定会把这些隐藏的绝对定位元素放在在body
标签内部,且最底部加载,以提高页面的呈现速度,甚至根本就不加载。此做法就是mtime时光网下拉导航的做法,是推荐的做法。绝对元素的定位不是通过当前触发元素的relative
限制,而是在body
大环境中,直接通过触发元素的偏移值设定位置,是最直接最高效的做法。
在body
标签下自由驰骋,这才是绝对定位元素真正应该呆的地方。真正有才华的元素应该放在更大的舞台上,限制在蹩脚的角落里注定要埋没的。我之前写过一个名为”powerFloat“的万能浮动插件,就是希望通过降低使用的学习成本,让大家都把绝对定位元素解放到body标签下。
于是乎,我们不用担心什么层级错乱的破问题,不会再看到密密麻麻错乱的HTML代码。做页面重构的,本来就应该是每天喝喝咖啡,跟美女前台打情骂俏的工作,现在却搞那么辛苦,太不应该了。
absolute
元素犹如有翅膀的小鸟,你是把它限制在鸟笼中,还是把它放飞到天空中自由的飞翔?我想,一切不言而喻。
下集看点:
下篇还是关于absolute
属性的(relative
属性以及z-index
还在其后),内容大致有,
absolute
与reflow
回流及应用;
IE6/7下行高与absolute
元素间的误会;
IE6/7下haslayout与absolute
元素间的误会;
等……
(本篇完)
觉得可用,就经常来吧! 欢迎评论哦! html5教程,巧夺天工,精雕玉琢。小宝典献丑了!
声明:本文内容由网友自发贡献,本站不承担相应法律责任。对本内容有异议或投诉,请联系2913721942#qq.com核实处理,我们将尽快回复您,谢谢合作!
若转载请注明出处: CSS 相对/绝对(relative/absolute)定位系列(二)
本文地址: https://pptw.com/jishu/586872.html