我有一个包含另一个div(子)的div(父)。Parent是body中的第一个元素,没有特定的CSS样式。当我设置

.child
{
    margin-top: 10px;
}

最终的结果是我的子的顶部仍然与父对齐。我的父结点向下移动10px,而不是子结点向下移动10px。

我的DOCTYPE被设置为XHTML Transitional。

我错过了什么?

编辑1 我的父母需要有严格定义的尺寸,因为它有一个背景,必须显示在它下面从上到下(像素完美)。所以不能在上面设置垂直边距。

编辑2 这种行为在FF、IE和CR上都是一样的。


当前回答

纯css解决方案

使用下面的代码将一个无内容的第一个子元素添加到无意移动的div前面:

.parent:before
{content: '';position: relative;height: 0px;width: 0px;overflow: hidden;white-space: pre;}

这种方法的优点是不需要更改任何现有元素的CSS,因此对设计的影响最小。在它旁边,添加的元素是伪元素,它不在dom树中。

伪元素的支持非常广泛:Firefox 3+、Safari 3+、Chrome 3+、Opera 10+和IE 8+。这可以在任何现代浏览器中工作(注意使用更新的::before,它在IE8中不受支持)。

上下文

如果元素的第一个子元素有一个margin-top,父元素将调整它的位置,以减少冗余边距。为什么?就像这样。

给定以下问题:

<style type="text/css">
div {position: relative;}
.parent {background-color: #ccc;}
.child {margin-top: 40px;}
</style>

<div class="parent"><!--This div moves 40px too-->
    <div class="child">Hello world!</div>
</div>

您可以通过添加带有内容(例如简单空格)的子元素来修复它。但我们都不喜欢为设计问题添加空格。因此,可以使用空白属性来伪造内容。

<style type="text/css">
div {position: relative;}
.parent {background-color: #ccc;}
.child {margin-top: 40px;}
.fix {position: relative;white-space: pre;height: 0px;width: 0px;overflow: hidden;}
</style>

<div class="parent"><!--This div won't move anymore-->
    <div class="fix"></div>
    <div class="child">Hello world!</div>
</div>

其中位置:相对;确保固定的正确位置。和空格:pre;使您不必添加任何内容-如空白-到修复。和高度:0px;宽度:0px;溢出:隐藏;确保你永远都看不到解决办法。

你可能需要添加line-height: 0px;或者max-height: 0px;以确保高度实际上是零在古老的IE浏览器(我不确定)。还可以添加<!——dummy——>到旧的IE浏览器,如果它不工作。

简而言之,你可以用CSS完成所有这些(这就不需要向HTML dom树中添加实际的子节点):

<style type="text/css">
div {position: relative;}
.parent {background-color: #ccc;}
.child {margin-top: 40px;}

.parent:before {content: '';position: relative;height: 0px;width: 0px;overflow: hidden;white-space: pre;}
</style>

<div class="parent"><!--This div won't move anymore-->
    <div class="child">Hello world!</div>
</div>

其他回答

在DIVs内的子元素中找到了一个边距的替代方法,您还可以添加:

.parent { overflow: auto; }

or:

.parent { overflow: hidden; }

这可以防止边际崩溃。边框和填充也是如此。 因此,你也可以使用以下方法来防止最高利润崩溃:

.parent {
    padding-top: 1px;
    margin-top: -1px;
}

2021年更新:如果你愿意放弃IE11支持,你也可以使用新的CSS结构display: flow-root。有关块格式上下文的全部细节,请参阅MDN Web文档。


按大众要求更新: 缩边距的全部意义在于处理文本内容。例如:

H1, h2, p, ul { margin-top: 1 em; margin-bottom: 1 em; 轮廓:1px蓝色虚线; } Div{大纲:1px固体红色;} <标题>标题!< / h1 > < div class = " text " > < h2 >标题!< / h2 > < p > < / p >款 < / div > < div class = " text " > < h2 >标题!< / h2 > < p > < / p >款 < ul > <李>列表项李< / > < / ul > < / div >

由于浏览器折叠了页边距,因此文本将按照您所期望的方式显示,并且<div>包装器标记不会影响页边距。每个元素确保其周围有间距,但间距不会加倍。<h2>和<p>的裕度不会叠加,而是相互滑入(它们坍缩)。<p>和<ul>元素也是如此。

可悲的是,在现代设计中,当你明确地想要一个容器时,这个想法会让你感到不快。这在CSS中被称为新的块格式化上下文。溢出或边距技巧会给你这个。

父元素不能为空,至少要放&nbsp;在子元素之前。

你可以通过在伪元素display: flex;给父母。

.parent:before {
  content: '';
  display: flex;
}

另一种方法是将父节点的display属性设置为flow-root。

.parent {
  display: flow-root;
}

我发现, 在你的.css >中,如果你设置一个div元素的显示属性为内联块,它就会修复这个问题。保证金会像预期的那样起作用。

在我知道正确答案之前,我找到了另一个解决方案,即向父元素添加透明边框。

你的盒子将使用额外的像素…

.parent {
    border:1px solid transparent;
}