我尝试在另一个div内的一个div上添加边缘值。所有工作都很好,除了顶部值,它似乎被忽略了。但是为什么呢?

我的期望是:

我得到的是:

代码:

#{外 宽度:500 px; 身高:200 px; 背景:# FFCCCC; Margin: 50px auto 0 auto; 显示:块; } #{内部 背景:# FFCC33; Margin: 50px 50px 50px 50px; 填充:10 px; 显示:块; } < div id = "外" > < div id = "内部" > 你好世界! < / div > < / div >

W3Schools没有解释为什么margin会这样。


尝试使用display: inline-block;在内部div上,就像这样:

#outer {
    width:500px; 
    height:200px; 
    background:#FFCCCC;
    margin:50px auto 0 auto;
    display:block;
}
#inner {
    background:#FFCC33;
    margin:50px 50px 50px 50px;
    padding:10px;
    display:inline-block;
}

不太清楚为什么,但改变内部CSS为

display: inline-block;

似乎有用。


实际上,您可以看到#inner元素的上边缘塌陷到#outer元素的上边缘,只留下#outer边缘完好无损(尽管在图像中没有显示)。两个盒子的上边缘彼此平齐,因为它们的边距相等。

以下是来自W3C规范的相关要点:

8.3.1边际萎缩 在CSS中,两个或多个框(可能是也可能不是兄弟)的相邻边距可以组合成一个边距。以这种方式结合的保证金被称为崩溃保证金,由此产生的合并保证金被称为崩溃保证金。 相邻的垂直边缘塌陷[…]

当且仅当: 两者都属于参与同一块格式化上下文的流内块级框 没有行框,没有间隙,没有填充,没有边界将它们分开 两者都属于垂直相邻的框边,即形成以下对之一: 一个盒子的上边距和它的第一个流入子框的上边距

你可以做以下任何一件事来防止边缘崩溃:

浮动任意一个div元素 使任何一个div元素成为内联块 将#outer的overflow设置为auto(或除visible以外的任何值)

上述选项防止保证金崩溃的原因是:

浮动框和任何其他框之间的边距不会折叠(即使浮动和它的流中子框之间也不会折叠)。 建立新的块格式上下文的元素的边距(例如float和带有“overflow”而不是“visible”的元素)不会随其流内子元素一起折叠。 内联块框的页边距不会折叠(即使它们的流子框也不会折叠)。

左右边距的表现如你所料,因为:

水平边距永不塌陷。


不知道为什么你没有工作,但你可以添加overflow: auto;到外部div。


如果你给#outer添加任何填充,它就可以工作。演示:

#{外 宽度:500 px; 身高:200 px; 背景:# FFCCCC; Margin:50px auto 0 auto; 显示:块; padding-top: 1 px; } #{内部 背景:# FFCC33; Margin:50px 50px 50px 50px; 填充:10 px; 显示:块; } < div id = "外" > < div id = "内部" > 你好世界! < / div > < / div >


没有回答“为什么”(必须是w/边距折叠的东西),但似乎最简单/最合乎逻辑的方法来做你正在尝试做的事情,将只是添加padding-top到外部div:

#{外 宽度:500 px; 身高:200 px; 背景:# FFCCCC; Margin:50px auto 0 auto; padding-top: 50 px; } #{内部 背景:# FFCC33; Margin:0px 50px 50px 50px; 填充:10 px; } < div id = "外" > < div id = "内部" > 你好世界! < / div > < / div >

注意:没有必要将div设置为display:block;除非你的代码中有其他东西告诉它不是block。


试试这个:

#{外 宽度:500 px; 身高:200 px; 背景:# FFCCCC; Margin:50px auto 0 auto; 显示:表; } #{内部 背景:# FFCC33; Margin:50px 50px 50px 50px; 填充:10 px; 显示:块; } < div id = "外" > < div id = "内部" > 你好世界! < / div > < / div >

好运!


我想将#inner div的位置属性设置为相对也可以帮助实现这个效果。但无论如何,我尝试了粘贴在IE9和最新的谷歌Chrome浏览器上的问题的原始代码,他们已经给出了理想的效果,没有任何修改。


外部div使用padding-top:50px,如下所示:

#outer {
    width:500px; 
    height:200px; 
    background:#FFCCCC;
    margin:50px auto 0 auto;
    display:table;}

注意:填充会增加你的div的大小。在这种情况下,如果你的div的大小很重要,我的意思是如果它必须有一个特定的高度。降低高度50px:

#outer {
    width:500px; 
    height:150px; 
    background:#FFCCCC;
    margin:50px auto 0 auto;
    display:table;}

重要的是,它会强迫一切:

margin:50px 50px 50px 50px !important;

@BoltClock提到的是相当扎实的。 这里我想为这个问题添加更多的解。 检查w3c_collapse边距。绿色部分是潜在的思考如何解决这个问题。

解决方案1

浮动框和任何其他框之间的边距不会折叠(即使浮动和它的流中子框之间也不会折叠)。

这意味着我可以添加float:left到#outer或#inner demo1中。

还要注意,float会使auto在保证金中无效。

解决方案2

建立新的块格式上下文的元素的边距(例如float和带有“overflow”而不是“visible”的元素)不会随其流内子元素一起折叠。

除了visible,让我们把overflow: hidden放到#outer中。这种方法看起来很简单也很得体。我喜欢它。

#outer{
    width: 500px;
    height: 200px;
    background: #FFCCCC;
    margin: 50px auto;
    overflow: hidden;
}
#inner {
    background: #FFCC33;
    height: 50px;
    margin: 50px;
}

解决方案3

绝对定位框的页边距不会折叠(即使它们的子流也不会折叠)。

#outer{
    width: 500px;
    height: 200px;
    background: #FFCCCC;
    margin: 50px auto;
    position: absolute; 
}
#inner{
    background: #FFCC33;
    height: 50px;
    margin: 50px;
}

or

#outer{
    width: 500px;
    height: 200px;
    background: #FFCCCC;
    margin: 50px auto;
    position: relative; 
}
#inner {
    background: #FFCC33;
    height: 50px;
    margin: 50px;
    position: absolute;
}

这两种方法将破坏正常的div流程

解决方案4

内联块框的页边距不会折叠(即使它们的流子框也不会折叠)。

和@enderskill一样吗

解决方案5

流内块级元素的下边距总是与它的下一个流内块级兄弟元素的上边距一起折叠,除非该兄弟元素有间隙。

这与问题没有太大关系,因为它是兄弟姐妹之间的崩溃边缘。这通常意味着如果一个top-box有margin-bottom: 30px,而一个sibling-box有margin-top: 10px。它们之间的总边距是30px而不是40px。

解决方案6

如果一个流内块元素没有顶部边框,没有顶部填充,并且子元素没有间隙,则该流内块元素的顶部边距与其第一个流内块级子元素的顶部边距一起折叠。

这很有趣,我可以添加一条顶部边框

#outer{
    width: 500px;
    height: 200px;
    background: #FFCCCC;
    margin: 50px auto;
    border-top: 1px solid red;

}
#inner {
    background: #FFCC33;
    height: 50px;
    margin: 50px;

}

并且<div>默认是块级的,所以你不必刻意声明它。抱歉,由于我的新手声誉,不能发布超过2个链接和图像。下次看到类似的问题时,至少你知道问题从哪里来。


只是为了快速修复,尝试像这样将子元素包装成div元素-

<div id="outer">
   <div class="divadjust" style="padding-top: 1px">
      <div id="inner">
         Hello world!
      </div>
   </div>
</div>

内部div的边距不会因为外部和内部div之间1px的填充而崩溃,所以逻辑上你会有1px的额外空间以及内部div的现有边距。


创建新的块格式化上下文

您可以在父元素上使用display: flow-root来防止在创建新的块格式化上下文时通过包含元素的边距崩溃。

将overflow属性的值更改为auto或使用flexbox将具有相同的效果。

https://codepen.io/rachelandrew/pen/VJXjEp


如果你有一个边际崩溃的问题,那么解决这个问题,你可以添加 显示:flow-root;到父容器。

除此之外,如果margin-top被忽略,尝试margin-top的负值,例如:margin-top: -2px;