资讯专栏INFORMATION COLUMN

CSS魔法堂:"那不是bug,是你不懂我!" by inline-block

cucumber / 809人阅读

摘要:那不是,是我不懂而已。的用途之一西文是以空格来分隔单词的,而汉字间则无需空格分隔,但为了统一西文东亚和的排版,于是抽象出一个名为的概念用于分隔词义单元,则作为的值域,而定义域就是语言信息。

前言

每当来个需要既要水平排版又要设置固定高宽时,我就会想起display:inline-block,还有为了支持IE5.5/6/7的hack*display:inline;*zoom:1;。然后发现盒子间无端端多了个不可选的空白符,于是想尽办法修复这个bug。

直到一天拜读了@一丝姐、@HAX等高人的秘笈后才顿悟,原来我错了。那不是bug,是我不懂而已。

先行者——IE5.5中的inline-block

当我们为支持IE5.5/6/7而添加这段hack时*display:inline;*zoom:1,总以为从IE8开始才支持display:inline-block属性值。其实从IE5.5开始已经支持了,只是IE5.5/6/7支持的是IE的自定义标准,而从IE8开始则是支持CSS2.1标准而已。

https://msdn.microsoft.com/library/ms530751%28v=vs.85%29.aspx

The inline-block value is supported starting with Internet Explorer 5.5. You can use this value to give an object a layout without specifying the object’s height or width.


经过CSS2.1洗礼的我们对上述内容不禁会发出两个疑问:

为啥block-level element设置了display:inline-block后还是垂直方向排列呢?

为啥inline-level element设置了display:inline-block后之间没有诡异的间隙呢?

还记得杨过是如何变成神雕大侠的吗?不就是被断右臂后发现左手才是真爱吗:)

好了,其实我的意思是抛弃过去对display:inline-block的认知,重新来理解IE5.5/6/7下的它才是硬道理啦。

对于问题1,首先上面的引用很直白地告诉我们——display:inline-block能触发hasLayout,然后就没了。所以block-level element依然是block-level element,不会一夜成了inline-level element的。结论:display:inline-block仅会触发hasLayout,而元素本该怎么排版还是怎么排版。关于hasLayout的内容可参考《CSS魔法堂:hasLayout原来是这样!》

对于问题2,我们先看看是否真的没有间隙吧!






bk1

见鬼了,在前一个盒子内添加些文本就出现间隙了?其实这真的和display:inline-block无关的,大家就放过他吧!来上呈堂证供!


before
before
after
after
after
one two
one two

chrome43

对于起始标签与第一个non-white-space字符间的white-space字符串,以carriage return( )作为white-space合并单元的起始符,最后保留各合并单元的合并结果。

结束标签与最后一个non-white-space字符间的white-space字符串,以carriage return( )作为white-space合并单元的结束符,最后保留各合并单元的合并结果。

词义单元间的white-space字符串,以carriage return( )作为white-space合并单元的分界符,最后保留各合并单元的合并结果。

标签内仅包含white-space字符串,那么这些white-space字符串将被忽略。

FF5.0

对于起始标签与第一个non-white-space字符间和结束标签与最后一个non-white-space字符间的white-space字符串将被忽略。

词义单元间的white-space字符串,以carriage return( )作为white-space合并单元的分界符,最后保留各合并单元的合并结果。

标签内仅包含white-space字符串,那么这些white-space字符串将被忽略。

IE8+

对于起始标签与第一个non-white-space字符间和结束标签与最后一个non-white-space字符间的white-space字符串将被忽略。

词义单元间的white-space字符串,合并为1个(ASCII space)字符。

标签内仅包含white-space字符串,那么这些white-space字符串将被忽略。

IE5.5/6/7

对于起始标签与第一个non-white-space字符间的white-space字符串将被忽略。

结束标签与最后一个non-white-space字符间的white-space字符串,合并为1个(ASCII space)字符。

词义单元间的white-space字符串,合并为1个(ASCII space)字符。

标签内仅包含white-space字符串,那么这些white-space字符串将被忽略。

合并单元:合并单元包含0到N个white-space字符串,最终合并为0到1个white-space字符

SGML描述B.3.1 Line breaks

specifies that a line break immediately following a start tag must be ignored, as must a line break immediately before an end tag. This applies to all HTML elements without exception.

My favorite Website

My favorite Website

望文生义翻译法:标签与正文间的line breaks要被忽略掉!也就是上下两种HTML格式的渲染效果应该一致。实际上除了IE5.5/6/7外其他浏览器均遵守之一规定的。也许你会说上面的实验不是已经证明chrome43不遵守这个法则吗?其实


My favorite Website

HTML格式等价于#x000A;My favorite Website#x000A;而不是#x000D;#x000A;My favorite Website#x000D;#x000A;。现在大家都清楚了吧:)

绕到这里我想大家都有点晕了,到底这个跟问题2有啥关系呢?先不要着急嘛,我们先记住两点:

IE5.5/6/7中"结束标签与最后一个non-white-space字符间的white-space字符串,合并为1个(ASCII space)字符";

IE5.5/6/7中仅字符(串)可以作为词义单元,而IE8+中inline-level element也作为词义单元。





bk1

IE5.5/6/7下等价于





bk1

对比一下上面的规则,空隙自然就有了。

IE8+下等价于

 
 


   

inline-level element整体作为词义单元,从外部看根本不用管里面具体字符串是什么。

后来者居上——CSS2.1描述中的inline-block

相对IE自定义的inline-block,CSS2.1引入的inline-block就好理解多了,它做了两件事:

将元素变性为inline-level element;

让元素产生新的BFC。

消灭尾行者

现在我们终于明白通过display:inline-block进行元素的水平排版时,为啥会有个讨人厌的跟屁虫了,那剩下的工作当然是去而快之啦。首先这个跟屁虫实质上就是white-space字符串,而我们一般会输入的就是ASCII space( )ASCII tab( )和让HTML Markup更可读的line breakscarriage return( )line feed( )

那么消灭尾行者的方式就只有两个方向:1. 从根本上消除white-space字符串;2. 视觉效果上消除white-space字符串的影响。

牺牲HTML Markup可读性

牺牲前

one
two
three

牺牲后1:一行搞定(一大坨代码,会斗鸡眼的。。。)

onetwothree

牺牲后2:注释衔接(通过JS获取子元素数会有问题)

onetwothree

牺牲后3

onetwothree

然后@一丝姐说为展现效果牺牲结构是耍流氓,@HAX说这是"削足适履"。虽说这方法从根本上清除了white-space字符串,但那种丑不是一般人能接受的。

font-size:0大法

这种方式存在兼容性的问题,而且子元素需要重新设置font-size以保证后续采用em设置属性值正确有效这个就是一个巨蛋疼的事了。

负margin-right法

原理是通过负margin-right将white-space字符收入盒子后方,而margin-right的属性值需要根据font-size来决定,必须恰恰等于字形宽度的负数,否则会出现元素重叠的问题。(IE5.5/6/7不兼容这玩法)

引入HTML预编译

引入如Jade等HTML模板引擎,开发和维护时采用可读性可维护性更高的语言,而浏览器运行时则采用效率更佳但可读性差甚至非人类友好的编码,然后通过如sourcemap来做映射。

但若仅仅为解决本文的问题而引入HTML模板引擎,是不是小题大造了呢?

用float啦!

既然上述方式皆不爽,而你又熟知float的使用和注意事项,那直接换成float就好了。float的内容可参考《CSS魔法堂:说说Float那个被埋没的志向》

总结

原来display:inline-block受委屈的这么多年,现在总算沉冤得雪了!都怪CSS2没有专门的布局模块,逼得我们东拼西凑地拼页面。所幸的是CSS3专设了Flexbox/Grid/Multi-columns Layout Modules,我们可以寄望更美好的将来了!

尊重原创,转载请注明来自:http://www.cnblogs.com/fsjohnhuang/p/5396037.html^_^肥仔John

感谢

inline-block 前世今生
inline-block 未来
应不应该使用inline-block代替float
inline-block元素间间隙产生及去除详解
有哪些好方法能处理 display: inline-block 元素之间出现的空格?
Fighting the Space Between Inline Block Elements
拜拜了,浮动布局-基于display:inline-block的列表布局
9.1 White space
9.3.2 Controlling line breaks

文章版权归作者所有,未经允许请勿转载,若此文章存在违规行为,您可以联系管理员删除。

转载请注明本文地址:https://www.ucloud.cn/yun/115185.html

相关文章

  • CSS魔法:一起玩透伪元素和Content属性

    摘要:前言继上篇魔法堂稍稍深入伪类选择器记录完伪类后,我自然而然要向伪元素伸出魔掌的啦。和的注意事项默认必须设置属性,否则一切都是无用功默认,就是和的内容无法被用户选中的伪元素和伪类结合使用形如。 前言  继上篇《CSS魔法堂:稍稍深入伪类选择器》记录完伪类后,我自然而然要向伪元素伸出魔掌的啦^_^。本文讲讲述伪元素以及功能强大的Contet属性,让我们可以通过伪元素更好地实现更多的可能! ...

    DevTalking 评论0 收藏0
  • CSS魔法:hasLayout原来是这样的!

    摘要:到底是何方神圣可以简单看作是中的。和产生新的特性一样,无法通过属性直接设置,而是通过某些属性间接开启这一特性。不同的是某些属性是以不可逆方式间接开启为。因此所引发的问题,很大程度可以理解为在不应该的或没有预料到的地方产生新的导致的。 前言 过去一直听说旧版本IE下很多诡异bug均由一个神秘角色引起的,那就是hasLayout。趁着最近突然发神经打算好好学习CSS,顺便解答多年来的疑惑。...

    URLOS 评论0 收藏0
  • CSS魔法:重拾Border之——不仅仅是圆角

    摘要:撸代码实现首页检验单查询成品通用标准审核圆角的何止是啊上图的变成椭圆形了,而且中的文字好像飘到外面。我们可以看到两边相交所形成的矩形的对角线,将作为边的相交点。 前言  当CSS3推出border-radius属性时我们是那么欣喜若狂啊,一想到终于不用再添加额外元素来模拟圆角了,但发现border-radius还分水平半径和垂直半径,然后又发现border-top-left/right...

    _Dreams 评论0 收藏0
  • CSS魔法:深入理解line-height和vertical-align

    摘要:下的属性值详解以下内容均在中测试默认对齐方式这里作为参考系,而它的就是所要对齐的了。没有任何变化。那改变又如何呢为了让的清晰可见,特意添加一个的包裹着。 前言 一直听说line-height是指两行文本的基线间的距离,然后又说行高等于行距,最近还听说有个叫行间距的家伙,@张鑫旭还说line-height和vertical-align基情四射,贵圈真乱啊。。。。。。于是通过本篇来一探究竟...

    avwu 评论0 收藏0
  • CSS魔法:你真的懂text-align吗?

    摘要:深入本届集团公司党委由公司党委由本届集团公司党委由公司党委由组均是,而组则是。下英文泰文等的默认对齐方式,下的默认对齐方式等同于,采用增加减少象形文字间的距离。 前言 也许提及text-align你会想起水平居中,但除了这个你对它还有多少了解呢?本篇打算和大家一起来跟text-align来一次负距离的交往,你准备好了吗? text-align属性详解 The text-align C...

    tinylcy 评论0 收藏0

发表评论

0条评论

最新活动
阅读需要支付1元查看
<