html - 在嵌套容器中如何使 flexbox 元素正确收缩?

标签 html css flexbox

如果我像这样设置一个嵌套的 flexbox 容器:

<div class="container1">
  <div class="grow1">
    <div class="container2">
      <div class="grow2"></div>
    </div>
  </div>
</div>

...然后设置 grow2 的宽度,使其比 container1 然后 grow2 溢出 container1。

我认为这应该不会发生,因为 flex 元素在大于 flex 容器时应该收缩。

如果我设置 grow2 的 flex-basis 那么这会按预期工作。

请看下面的演示示例:

https://jsfiddle.net/chris00/ot1gjjtk/20/

为此请使用 Chrome 或 Firefox

此外,我读到 flexbox 规范说 width 和 flex-basis 应该具有相同的效果(当使用水平布局时),但它们显然没有。

现在我可以只使用 flex-basis 而不是 width,但是... Edge 对 flex-basis 和 width 做同样的事情,但它以“错误”的方式进行。 IE11 也做错了(尽管它似乎有多个 flexbox 错误)。 请查看 Edge 演示。

那么这应该如何工作?

所有浏览器都存在错误吗?

flex-basis 实际上应该与宽度不同(在简单的水平布局中)吗?

或者 Edge 是否正确并且 width 和 flex-basis 都应该溢出父容器?

最后,是否有解决方法可以解决 Edge(甚至 IE11)的溢出问题?

.container1 {
  margin-top: 10px;
  display: flex;
  width: 200px;
  height: 50px;
  background-color: red;
}

.grow1 {
  flex-grow: 1;
  height: 40px;
  background-color: green;
}

.container2 {
  display: flex;
  height: 30px;
  background-color: yellow;
}

.grow2a {
  flex-grow: 1;
  flex-basis: 400px;
  height: 20px;
  background-color: turquoise;
}

.grow2b {
  flex-grow: 1;
  width: 400px;
  height: 20px;
  background-color: turquoise;
}
<div class="container1">
  <div class="grow1">
    <div class="container2">
      <div class="grow2a">Working (flex-basis)</div>
    </div>
  </div>
</div>

<div class="container1">
  <div class="grow1">
    <div class="container2">
      <div class="grow2b">Not working (width)</div>
    </div>
  </div>
</div>

最佳答案

问题

就规范而言,这不是关于 flex-basiswidthflex-grow flex 。这是完全不同的东西。

4.5. Implied Minimum Size of Flex Items

To provide a more reasonable default minimum size for flex items, this specification introduces a new auto value as the initial value of the min-width and min-height properties defined in CSS 2.1.

换句话说,默认情况下, flex 元素不能小于其内容的长度(本质上是最长的单词或固定大小的元素)。

该元素不能留在其容器内(甚至呈现滚动条或省略号),因为不允许其内容溢出。内容只是扩展元素。此行为也适用于固定大小(例如代码中的 flex-basis: 400px)。

同样,初始设置是:

  • min-width: auto,行方向
  • min-height: auto,列方向

有关更完整的解释,请参阅此帖子:


Chrome、Safari、Firefox 和 Edge 的解决方案

这个问题的标准解决方案很简单:覆盖默认值。

在您的代码中,将 min-width: 0 添加到 .grow1

这解决了 Chrome、Safari、FF 和 Edge 中的问题。

.container1 {
  margin-top: 10px;
  display: flex;
  width: 200px;
  height: 50px;
  background-color: red;
}

.grow1 {
  flex-grow: 1;
  height: 40px;
  background-color: green;
  min-width: 0; /* NEW */
}

.container2 {
  display: flex;
  height: 30px;
  background-color: yellow;
}

.grow2a {
  flex-grow: 1;
  flex-basis: 400px;
  height: 20px;
  background-color: turquoise;
}

.grow2b {
  flex-grow: 1;
  width: 400px;
  height: 20px;
  background-color: turquoise;
}
<div class="container1">
  <div class="grow1">
    <div class="container2">
      <div class="grow2a">Working (flex-basis)</div>
    </div>
  </div>
</div>

<div class="container1">
  <div class="grow1">
    <div class="container2">
      <div class="grow2b">Not working (width)</div>
    </div>
  </div>
</div>

revised fiddle 1


IE11解决方案

在 IE11 中,与规范指南相反,flex min-width/min-height 默认值已经是 0,但是 flex元素仍然爆发。

默认值是0,因为当flexbox规范首次发布时,min-*属性没有偏离CSS 2.1 initial values。 ,它们是 0

后来,在浏览器完成其实现后,flex min-* 值被更新为 auto。 Chrome、Safari、FF 和 Edge 进行了更新。 IE11 没有。

flex 元素在 IE11 中爆发的原因与另一个问题有关:浏览器需要容器上的显式宽度

在您的代码中,将 flex-basis: 100% 添加到 .grow1

更多细节在这里:

.container1 {
  margin-top: 10px;
  display: flex;
  width: 200px;
  height: 50px;
  background-color: red;
}

.grow1 {
  flex-grow: 1;
  height: 40px;
  background-color: green;
  flex-basis: 100%; /* NEW */
}

.container2 {
  display: flex;
  height: 30px;
  background-color: yellow;
}

.grow2a {
  flex-grow: 1;
  flex-basis: 400px;
  height: 20px;
  background-color: turquoise;
}

.grow2b {
  flex-grow: 1;
  width: 400px;
  height: 20px;
  background-color: turquoise;
}
<div class="container1">
  <div class="grow1">
    <div class="container2">
      <div class="grow2a">Working (flex-basis)</div>
    </div>
  </div>
</div>

<div class="container1">
  <div class="grow1">
    <div class="container2">
      <div class="grow2b">Not working (width)</div>
    </div>
  </div>
</div>

revised fiddle 2 (IE11)


更多浏览器差异

证据似乎存在(在这个问题和我见过的其他例子中),基于 Webkit 的浏览器不再遵守规范中定义的 auto 默认值。

此外,对 auto 标准的遵守可能会因用于调整大小的属性而异:flex-basiswidth/高度

正如在下面的帖子中所讨论的,这些属性应该以相同的方式呈现。

关于html - 在嵌套容器中如何使 flexbox 元素正确收缩?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/43934648/

相关文章:

javascript - 如何使用 justify-content 对容器中的插入和删除进行动画处理?

php - 如何在 Codeigniter 中更改运行时的语言?

css - 将一个元素与其旁边的另一个元素居中

CSS - 将样式表转移到 Wordpress 主题

html - 垂直居中的文本一直在图标下方

javascript - `background-size: cover;` 的 CSS 打印修复

javascript - 如何使底层元素不可点击/停用?

html - 省略号(三个点)不会显示较长的文本

javascript - 在javascript中添加两个 float

html - 鼠标悬停 CSS 问题(CSS 之后应用不透明度)