为什么Chrome不能正确处理使用jQuery添加的flexbox项目



我在编写一些基本的flexbox代码时,注意到Chrome在添加flex项时显示出奇怪的行为,并且容器的方向设置为columncolumn-reverse。以下是一个简单的flexbox示例,说明如何在方向设置为列并包装的情况下正常工作:

#flexbox_container {
    border: 8px solid #ccc;
    padding: 10px;
    height: 200px;
    display: flex;
    flex-direction:column;
    flex-wrap: wrap;
}
.flex_item {
    background: #eee;
    margin: 4px;
    padding: 10px;
}
<div id="flexbox_container">
    <div class="flex_item">Item</div>
    <div class="flex_item">Item</div>
    <div class="flex_item">Item</div>
    <div class="flex_item">Item</div>
    <div class="flex_item">Item</div>
    <div class="flex_item">Item</div>
    <div class="flex_item">Item</div>
</div>

正如预期的那样,当列的数量增长得太大而无法容纳容器时,会创建第二列,每个列的宽度相等。

下面是一个问题的例子。如果我们从一列的子flex项目开始,并使用jQuery不断添加更多的项目,而不是如上所述将它们平均划分,那么第一列占据整个宽度,新项目突出到侧面:

$('button').click(function() {
  $('#flexbox_container').append('<div class="flex_item">Item</div>');
})
#flexbox_container {
  border: 8px solid #ccc;
  padding: 10px;
  height: 200px;
  display: flex;
  flex-direction: column;
  flex-wrap: wrap;
}
.flex_item {
  background: #eee;
  margin: 4px;
  padding: 10px;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>
<div id="flexbox_container">
  <div class="flex_item">Item</div>
</div>
<button>button</button>

然后让我困惑的是,如果我篡改了几乎任何CSS属性,我可以让Chrome按照我的期望来显示灵活项(几乎就像这会重新绘制或重新计算布局一样)。例如,在这里,我在插入新项目后快速更改弹性项目的位置:

$('button').click(function() {
  $('#flexbox_container').append('<div class="flex_item">Item</div>');
  $('.flex_item').css('position', 'absolute')
  setTimeout(function() {
    $('.flex_item').css('position', 'relative')
  }, 0)
})
#flexbox_container {
  border: 8px solid #ccc;
  padding: 10px;
  height: 200px;
  display: flex;
  flex-direction: column;
  flex-wrap: wrap;
}
.flex_item {
  background: #eee;
  margin: 4px;
  padding: 10px;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>
<div id="flexbox_container">
  <div class="flex_item">Item</div>
</div>
<button>button</button>

现在,这显然是一种很难解决的方法,每次添加新项目时都会引起难看的闪烁。

那么,为什么Chrome在插入jQuery时不能正确显示flex项,而不必对CSS属性进行快速修改呢?

请注意,Firefox和Edge都没有这个问题,并且工作正常,添加-webkit-前缀不会改变结果。此外,这似乎仅在flex-direction被设置为columncolumn-reverse时发生。当它设置为rowrow-reverse时,工作正常。

有趣。您可以通过添加以下样式来解决问题:

#flexbox_container {
  overflow: auto;
}
#flexbox_container::-webkit-scrollbar {
  height: 0;
}

花了一段时间才弄清楚滚动条的高度需要为0。

单独使用overflow,Chrome似乎可以做到以下几点:

  1. 添加一个元素
  2. 如果需要,添加滚动条
  3. 意识到这是一个灵活的盒子,它不需要滚动条
  4. 错误地将列中的最后一个元素定位到下一列的顶部

删除滚动条CSS,看看我在说什么。

$('button').click(function() {
  $('#flexbox_container').append('<div class="flex_item">Item</div>');
})
#flexbox_container {
  border: 8px solid #ccc;
  padding: 10px;
  height: 200px;
  display: flex;
  flex-direction: column;
  flex-wrap: wrap;
  overflow: auto;
}
#flexbox_container::-webkit-scrollbar {
  height: 0;
}
.flex_item {
  background: #eee;
  margin: 4px;
  padding: 10px;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>
<div id="flexbox_container">
  <div class="flex_item">Item</div>
</div>
<button>button</button>

最新更新