CSS 如何使用“flex-flow:列换行”?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/18669216/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-30 00:17:23  来源:igfitidea点击:

How do I use "flex-flow: column wrap"?

cssflexbox

提问by uber5001

Short version

精简版

When using flex-flow: column wrapand display: inline-flex, it doesn't shrinkwrap like inline-block:

使用flex-flow: column wrapand 时display: inline-flex,它不会像inline-block以下那样收缩包装:

enter image description here

在此处输入图片说明

(function() {
  var ascending = true;
  setInterval(function() {
    var parent = document.getElementById('flex');
    if (ascending) {
      var child = document.createElement('p');
      child.innerHTML = "foo";
      parent.appendChild(child);
    } else {
      parent.removeChild(parent.children[0]);
    }
    if (parent.children.length <= 1) ascending = true;
    if (parent.children.length >= 40) ascending = false;
  }, 20);
})();
(function() {
  var ascending = true;
  setInterval(function() {
    var parent = document.getElementById('failex');
    if (ascending) {
      var child = document.createElement('p');
      child.innerHTML = "foo";
      parent.appendChild(child);
    } else {
      parent.removeChild(parent.children[0]);
    }
    if (parent.children.length <= 1) ascending = true;
    if (parent.children.length >= 40) ascending = false;
  }, 20);
})();
#flexdesc {position: absolute; top: 25px;}
#flex {
  top: 50px;
  position: absolute;
  display: inline-flex;
  flex-flow: row wrap;
  outline: 1px solid black;
  padding: 3px;
  max-height: 100%;
  max-width: 180px;
  align-content: flex-start;
  transform: matrix(0, 1, 1, 0, 0, 0);
  transform-origin: top left;
}

#flex > p {
  margin: 0;
  outline: 1px solid black;
  height: 30px;
  width: 30px;
  align-self: flex-start;
  transform: matrix(0, 1, 1, 0, 0, 0);
}
#failexdesc {position: absolute; top: 275px;}
#failex {
  top: 300px;
  position: absolute;
  display: flex;
  flex-flow: column wrap;
  outline: 1px solid black;
  padding: 3px;
  max-height: 200px;
  align-content: flex-start;
  transform-origin: top left;
}

#failex > p {
  margin: 0;
  outline: 1px solid black;
  height: 30px;
  width: 30px;
  align-self: flex-start;
}
<!DOCTYPE html>
<html>
<head>
<meta charset=utf-8 />
<title>JS Bin</title>
</head>
<body>
  <div id="flexdesc">What I expect it to do</div>
  <div id="flex">
    <p>foo</p>
    
    <!-- add extra "<p>foo</p>" here. -->
  </div>
  <div id="failexdesc">What it does</div>
  <div id="failex">
    <p>foo</p>
  </div>
</body>
</html>

Notice how the size of each flex container changes (or doesn't change!)

注意每个 flex 容器的大小是如何变化的(或不变!)

I want this behavior because I want to place these element side by side for a horizontally scrolling website.

我想要这种行为,因为我想为水平滚动的网站并排放置这些元素。

Why doesn't it shrinkwrap? How do I make it shrinkwrap?

为什么不收缩包装?我如何使它收缩包装?











Original question

原始问题

flex-flow: row wrapis simple enough to understand. If nothing is "flexing", it acts similar to inline elements; It flows to the right until it can't do so anymore, at which point it makes a new row.

flex-flow: row wrap很容易理解。如果没有什么是“弯曲的”,它的作用类似于内联元素;它向右流动,直到它不能再这样做,此时它会创建一个新行。

flex-flow: column wrapwith display: flexis similar. It flows down, until it can't flow down anymore (max-width?), and then starts a new column. Of course, since the parent is display: flex, it's a block-level element, so that column will be halfway over due to the fact that align-contentdefaults to stretch. I could easily change that to flex-startto make the new column adjacent to the previous.

flex-flow: column wrapdisplay: flex是相似的。它向下流动,直到它不能再向下流动(max-width?),然后开始一个新的列。当然,由于父是 display: flex,它是一个块级元素,因此该列将由于align-content默认为stretch. 我可以轻松地将其更改flex-start为使新列与前一列相邻。

...but the container is still too wide. It's still a block, and fills the width of it's parent.

...但容器仍然太宽。它仍然是一个块,并填充其父级的宽度。

I need the flexbox to shrink-to-fit its columns.Why? I'm trying to use flexbox in a horizontally scrolling website. Granted, I could just let the children overflow, but that overflowing tends to... break things. So I figured I needed flex-flow: column wrapwith display: inline-flex. I was hoping for a "top to bottom, left to right" effect, where the parent has no empty space.

我需要 flexbox 来缩小以适应它的列。为什么?我正在尝试在水平滚动的网站中使用 flexbox。当然,我可以让孩子们溢出,但溢出往往会……破坏东西。所以我想我需要flex-flow: column wrap使用display: inline-flex. 我希望有一个“从上到下,从左到右”的效果,其中父级没有空白空间。

...and then thishappened. In chrome, the parent width is equal to the sum of the widths of the children, but otherwise, wrapping is normal. In firefox, the parent is full width, and just grows taller to accomodate the elements (I don't think firefox supports wrapping). In IE11, the width is correct, but the children just overflow down (even out of the body).

......然后发生了。在 chrome 中,父级宽度等于子级宽度的总和,否则,换行是正常的。在 firefox 中,父级是全宽的,只是为了容纳元素而变高(我认为 firefox 不支持环绕)。在 IE11 中,宽度是正确的,但孩子只是向下溢出(甚至超出了身体)。

I'm so confused.

我很困惑。

What am I doing wrong here? I understand that flexbox is a more recent feature, but I can't tell how much of this is my fault vs the browser.

我在这里做错了什么?我知道 flexbox 是一个更新的功能,但我不知道这与浏览器相比有多少是我的错。

By they way, I'm testing this in chrome. A chrome-only solution is fine by me. (But an elegant catch-all solution is always nice!)

顺便说一下,我正在用 chrome 测试这个。仅 chrome 的解决方案对我来说很好。(但是一个优雅的包罗万象的解决方案总是好的!)



Here's the code for the demo I linked to, in case jsbin is down:

这是我链接到的演示代码,以防 jsbin 关闭:

var ascending = true;
   setInterval(function() {
     var parent = document.getElementById('flex');
     if (ascending) {
       var child = document.createElement('p');
       child.innerHTML = "f";
       parent.appendChild(child);
     } else {
       parent.removeChild(parent.children[0]);
     }
     if (parent.children.length <= 1) ascending = true;
     if (parent.children.length >= 30) ascending = false;
   }, 200);
#flex {
  display: inline-flex;
  flex-flow: column wrap;
  outline: 1px solid black;
  padding: 3px;
  max-height: 100%;
  align-content: flex-start;
}
p {
  margin: 0;
  outline: 1px solid black;
  width: 10px;
}
body {
  height: 150px;
  width: 300px;
  outline: 1px dashed black
}
<!DOCTYPE html>
<html>
<head>
  <meta charset=utf-8 />
  <title>JS Bin</title>
</head>
<body>
  <div id="flex">
    <p>f</p>
    <!-- add extra "<p>foo</p>" here. -->
  </div>
</body>
</html>

回答by Asim K T

This was a bug indeed. Here the links to tracker:

这确实是一个错误。这里是跟踪器的链接:

https://bugs.chromium.org/p/chromium/issues/detail?id=247963https://bugs.chromium.org/p/chromium/issues/detail?id=507397

https://bugs.chromium.org/p/chromium/issues/detail?id=247963 https://bugs.chromium.org/p/chromium/issues/detail?id=507397

As OP wanted:

正如 OP 所希望的那样:

I need the flexbox to shrink-to-fit its columns. Why? I'm trying to use flexbox in a horizontally scrolling website. Granted, I could just let the children overflow, but that overflowing tends to... break things. So I figured I needed flex-flow: column wrap with display: inline-flex. I was hoping for a "top to bottom, left to right" effect, where the parent has no empty space.

我需要 flexbox 来缩小以适应它的列。为什么?我正在尝试在水平滚动的网站中使用 flexbox。当然,我可以让孩子们溢出,但溢出往往会……破坏东西。所以我想我需要 flex-flow: column wrap with display: inline-flex。我希望有一个“从上到下,从左到右”的效果,其中父级没有空白空间。

We can simply achieve it with flex-flow: column wrap;, align-content: flex-start;and a fixed height wrapper together.

我们可以简单地使用flex-flow: column wrap;,align-content: flex-start;和一个固定高度的包装器来实现它。

http://output.jsbin.com/qixuxiduxe/1

http://output.jsbin.com/qixuxiduxe/1

#flex {
  display: flex;
  flex-flow: column wrap;
  max-height: 100%;
  width: 150px;
  overflow: auto;
  align-content: flex-start;
}

p {
  margin: 0;
  align-self: flex-start
}

body {
  height: 150px;
}

Updated fiddle: http://jsbin.com/qixuxiduxe/1/edit?html,css,js,console

更新小提琴:http: //jsbin.com/qixuxiduxe/1/edit?html,css,js, console

回答by Marcus

If you don't know the height of each item or how many items you will have, a more flexible solution is this:

如果您不知道每个项目的高度或您将拥有多少项目,一个更灵活的解决方案是:

.parent {
  column-count: 4
}
.child {
  display: inline-block;
  width: 100%;
}

https://developer.mozilla.org/en-US/docs/Web/CSS/column-count

https://developer.mozilla.org/en-US/docs/Web/CSS/column-count

You may also need to adjust margin-topof .child:first-childif they don't align to the top.

您可能还需要调整margin-top.child:first-child,如果他们不顶端对齐。

回答by Adrián.

It might be late but I think 'column-wrap' is not fully supported by Firefox. As you said, you'll need this in Chrome, in that case you can see what Chris Coyier did: add webkit prefix --> http://css-tricks.com/snippets/css/a-guide-to-flexbox/

可能已经晚了,但我认为 Firefox 并不完全支持“列换行”。正如你所说,你需要在 Chrome 中使用它,在这种情况下你可以看到 Chris Coyier 做了什么:添加 webkit 前缀 --> http://css-tricks.com/snippets/css/a-guide-to-flexbox /

Hope is not late :/

希望不迟:/