取代float基于display:inline-block的列表布局
根据一些前辈的说法,IE6/7不支持display:inline-block属性,只是可以让标签有类似于inline-block的属性,起初我也是接受这种说法的,不过后来又表示了怀疑,最近使用text-align:justify;做测试的时候的一些样式表现证实了:确实IE6/7是不支持display:inline-block属性,只是让其表现的跟inline-block一样,尤其对于inline水平的元素,其表现度可以用perfect一词来形容了。
对于IE8+以及现代浏览器,直接使用:
您可以狠狠地点击这里:换行符与inline-block元素间间隙demo
要让这些空格不出现,最简单的最容易理解的就是让列表的结束标签与下一个列表的开始标签连在一起,就像是:
现在来看看几个主流浏览器下的反应,首先是Firefox浏览器:
然后是IE7浏览器:
哦呵呵,来看看大神Chrome浏览器:
希望越大失望越大,Chrome下的空格对于font-size:0貌似很不屑一顾。唉,这个问题在Chrome还是婴儿阶段的时候就有了,到现在还没有改过来。
经过我稀里哗啦一轮番的浏览器测试,发现就只有Chrome浏览器对font-size:0置若罔闻,连同样内核的Safari都不会这样。
您可以狠狠地点击这里:font-size:0清除换行符间隙demo
虽然Chrome目前国内份额有限,但是毕竟有不少高端用户在用啊。所以,一旦Chrome不支持font-size:0,那么,此方法显然不能应用到实际项目中,在加上IE和Safari下还是有1像素的间隙,所以此方法就此刷掉。现在得去考虑其他更好的方法。
我们一起开动脑筋,还有什么CSS属性可以影响文字的水平间距的。啊,只见脑袋上灯泡一亮,有了,不是有个letter-spacing属性嘛。可以控制文字间的水平距离的,支持负值,可以让文字水平方向上重叠(line-height是让文字垂直方向上重叠)。哟呵呵,心动不如行动,还拿那两张美女图片做示例,看看letter-spacing属性可否抹掉换行符产生的间距。参见如下测试代码:
先来看看一向表现优异的Firefox3.6浏览器,如下图:
很不错吧,再来看看前面让我们失望的Chrome浏览器:
嘿嘿,也是不错,希望就在眼前,看看IE新生主力军IE8下的表现:
再来看看对inline-block属性不支持的IE7浏览器:
您可以狠狠地点击这里:letter-spacing去除间隙空格
结果让人心里咯噔了一下,晕那,好像没有作用诶!不会啊,我很清楚的记得即使IE6/7浏览器也是支持letter-spacing去空格的。后来我仔细对比,发现这里的letter-spacing:-4px是有所用的,只是默认的空格间隙比较大,所以,即使舍去4像素间距,还是有一段空白内容。但是,我清楚的记得在Arial字体下,空格间距应该是兼容的,为何这里就IE6/IE7浏览器下不一样呢?后来,我反复测试,终于发现了一个第一次看到的bug,“冒号影响了空格间隙的水平大小”。现将“效果:”这个小标题后面的中文冒号还成英文的,结果,空格间距一下子兼容了,真是很神奇,我不得不佩服IE6/7浏览器的怪异指数。
您可以狠狠地点击这里:IE6/7下冒号英文化后间隙demo
IE6/7浏览器本身就是个怪胎,喜欢不走寻常路。在这两个浏览器下,block水平的元素inline-block化之后,会直接忽略换行符的间隙。所以,这里还有一点点疑虑没有解决。既然IE6/7浏览器div,li 这些标签inline-block化后没有空格间隙,那么使用letter-spacing负值会不会让列表元素水平重叠呢?啊,这个问题就不要担心了,如果元素间本身没有空格,使用letter-spacing属性是不会发生水平重叠的问题的。例如下面的测试代码:
结果如下图:
也就是说,如果元素间本身就没有间隔,无论letter-spacing的值多小,元素都不会重叠。但是,如果有空格间隙存在,letter-spacing会发生重叠的。所以,我们无需为IE6/7元素会不会重叠这个问题担心了。
您可以狠狠地点击这里:letter-spacing与无间隙重叠demo
按照我自己浅薄的经验开看,换行符产生的空格与按一下space键的作用是一样的。此空格所撑开的水平距离受空格字符所在环境的字体以及字体影响。由于不同的网站使用的字体不一样,所以,在借助letter-spacing属性实现列表布局时的letter-spacing的取值可能就不一样,所以,我专门研究了下空格水平间距与字体/字体大小之间的关系,以及兼容性等,整理在下面的表格中了,希望能对您有所帮助,要是发现不准确之处欢迎指正:
结果不支持font-size:0去间隙的Chrome浏览器:
letter-spacing无法实现完全去间隙的Opera浏览器:
您可以狠狠地点击这里:font-size:0,letter-spacing负值杂交demo
如果您使用的是IE6/7浏览器,可能会看到图片重叠了2像素,这是1像素文字间隙-3像素letter-spacing值的结果。但是,实际情况下,列表元素都是从block元素inline-block化的,元素间本身就没有间隙的,所以,就不会有重叠的问题了。
所以,应用display:inline-block属性实现列表布局的几个关键字就是:block水平的标签,font-size:0和letter-spacing负值。
下面就将通过实例展现基于display:inline-block的列表布局。
本部分主要是实例展示,我比较喜欢顺手找素材做实例,而新浪微博又是我常常挂着的,所以,没有恶意的,又拿新浪微博做示例了。
目前新浪微博右侧的人气用户推荐列表是采用浮动布局的,现在,采用inline-block布局实现同样的,但是高度可不宜的布局:
您可以狠狠地点击这里:inline-block布局和浮动布局对比实例页面
下为效果截图:
页面的上面列表采用的是目前新浪微博的原CSS代码,而下面的列表就是使用的inline-block列表布局。相比前面的浮动布局,不必担心每个列表高度不一的问题,所以用户的姓名可以完整显示,这可比直接裁掉要好些。
demo页面中默认加载会有两条参考线,是由于应用了我自己写的jQuery标尺参考线插件,您有兴趣可以狠狠地点击这里:网页制作辅助工具-jQuery标尺参考线插件
此插件会产生透明遮罩层,所以,你用firebug看代码的时候不能准确找到目标元素,此时只要按下”ESC”快捷键就可以隐藏标尺与参考线了。如果要想显示标尺,按下快捷键”R”即可,具体使用还是参见上面给出的文章链接。
显示两条参考线是用来说明,使用inline-block列表布局是没有兼容性问题的,可以达到与float布局一样的像素级无差异布局。
此例子中,文字大小为12像素,字体环境为Arial字体,对照上面的letter-spacing间隙数据表可知,这里的letter-spacing值应该是-3像素,于是……
其实人人网上就已经应用了基于display:inline-block的列表布局,您可以去看人人网的分享页面,其热门分享视频列表就是采用的基于display:inline-block的列表布局,但是其布局仅仅采用了letter-spacing负值,这也就意味着在Opera浏览器下,此列表是有兼容性问题的,如下面在Opera 10上的截图:
其他浏览器列表间距是12像素,而Opera下却是15像素,这是Opera浏览器letter-spacing负值反弹结果。但是,考虑到国情:Opera用户寥寥无几,所以,此不兼容性问题的影响也甚小。所以,您如果也不把Opera浏览器放在考虑范围内,使用inline-block列表布局时只要一个辅助CSS letter-spacing就可以了,如果顾虑到Opera,则不要忘了font-size:0;
如果你以为基于display:inline-block的列表布局的优点仅仅在于可以让列表元素不等高,那你就大错特错了。
在IE6/7下,inline水平标签inline-block化后与纯正的inline-block元素的作用就像是一个模子里出来的,这种“兼容性”可以很好地发挥inline-block列表布局的潜力。例如,使用white-space:nowrap;属性可以让列表不换行,你是否想到了列表元素的水平滚动切换?
使用text-align:justify可以实现自动等宽水平排列的列表布局,而且是两端对齐的,不需要计算宽度,一切都是浏览器自动的,很方便很强大。尤其在自适应布局中,大显身手,大放光彩。就以此举个简单的例子吧,如下CSS代码:
效果参见下面的视频(录制的是改变浏览器宽度时的效果):
从视频中可以看出,当浏览器宽度改变时,只要列表元素满行,inline-block化的列表都是等宽且两端对齐排列的,您可以狠狠地点击这里:列表自动两端对齐排列demo
IE6/7下inline水平的元素模仿inline-block属性就算再像还是模仿,MJ还是MJ,小月月依旧是小月月,所以IE6/7下,像是text-justify两端对齐还是比较脆弱的,像是一不留神的标签,或是换行符都会导致失效,远不如纯正的inline-block属性来得威武与坚挺。