相邻元素margin-top对绝对定位元素的影响及相关疑问
场景复现
我有两个元素,都设置了margin-top:20px,第一个元素为绝对定位。实际表现为第二个元素位于顶部,距离屏幕边缘20px。
CSS代码
div { width: 200px; height: 200px; } .posa { margin-top: 20px; position: absolute; background-color: #1239; } .normal { margin-top: 20px; margin-left: 20px; background-color: #aaa9; }
HTML代码
<div class="posa">position</div> <div class="normal">normal</div>
此前有相关讨论仅涉及父元素相关情况,未覆盖当前场景,以下针对三个疑问逐一解答:
疑问解答
为何绝对定位元素会受到下方第二个元素的margin影响?
本质不是绝对定位元素被下方元素影响,而是正常文档流中的.normal元素的margin-top发生了“穿透”:由于.posa脱离了正常文档流,页面正常流的第一个元素是.normal,它的margin-top会作用在父容器(如body)上,导致整个文档流向下偏移20px。而绝对定位的.posa是相对于视口(初始包含块)定位的,它自身的margin-top:20px让它距离视口顶部20px,视觉上就和下移后的.normal处于同一垂直位置,看起来像是被影响了。为何两者的margin未发生折叠,使得.normal元素距顶部20px、定位元素距顶部40px?
margin折叠仅发生在正常文档流内的块级元素之间,绝对定位元素脱离了文档流,不属于正常流的布局上下文,因此它的margin和正常流元素的margin不会产生折叠。另外,.normal的margin-top实际是和父容器(或初始包含块)的边界发生了作用,导致文档流整体下移,而非和.posa的margin叠加。为何仅margin-top产生此影响,margin-left却无此表现?
垂直方向的margin存在“穿透”(或与父容器的折叠)特性,但水平方向没有这个规则。.normal的margin-left:20px只会让自身相对于文档流起始位置向右偏移,不会带动父容器或整个文档流移动;而绝对定位元素的margin-left是相对于视口左边缘偏移,因此两者的水平位置不会出现类似垂直方向的视觉重叠效果。
内容的提问来源于stack exchange,提问作者Kolenbass

