不考虑边距和框大小的 Flex 项目:边框框 [英] Flex items not respecting margins and box-sizing: border-box

查看:16
本文介绍了不考虑边距和框大小的 Flex 项目:边框框的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在尝试实现标准 CSS 中的简单功能.

假设我有一个包含 3 列和 box-sizing: border-box 的网格系统.

这意味着我将适合 3 个盒子,并且边距将缩小尺寸以适合最多 3 个盒子.

但是当我尝试用 FLEXBOX 做到这一点时,它很痛苦!!

所以,如果我有 flex: 1 1 33.33%;margin: 10px; 我原以为每行有 3 个盒子……但是如果我使用 flex-wrap: wrap,那将不会缩小以适应 3 个盒子.

这是一个例子..这个想法是第二行有 3 个盒子在一行中,第四个盒子在最后一行.

谢谢

来源:W3C

<块引用>

3.1.改变盒子模型:box-sizing财产

content-box

指定的宽度和高度分别适用于宽度和高度元素的内容框.的填充和边框元素在指定的宽度和高度之外进行布局和绘制.

border-box

此元素上宽度和高度的长度和百分比值确定元素的边框.也就是说,任何填充或在元素上指定的边框被布置并绘制在此内部指定的宽度和高度.内容的宽度和高度是通过减去边框和填充宽度来计算来自指定宽度和高度属性的各个边.

<小时>

此外,flex 容器的初始设置是 flex-shrink: 1.这意味着 flex 项目可以收缩以适应容器.

因此,指定的widthheightflex-basis 将不成立,除非flex-shrink已禁用.

您可以使用 flex-shrink: 0 覆盖默认值.

这里有更完整的解释:flex-basis 和 width 有什么区别?

<小时>

这是一个简单的解决方案:

你有四个盒子.您需要第 1 行三个,第 2 行最后一个.

这就是你所拥有的:

flex: 1 1 33.33%;边距:10px;

这分解为:

  • flex-grow: 1
  • flex-shrink: 1
  • flex-basis: 33.33%

我们知道 box-sizing: border-box 将内边距和边框因素考虑到 flex-basis 中.那不是问题.但是利润率呢?

好吧,既然你在每个项目上都有 flex-grow: 1,那么 flex-basis 不需要是 33.33%.

由于 flex-grow 会消耗该行上的所有可用空间,flex-basis 只需要足够大以强制换行.

由于边距也消耗可用空间,flex-grow 不会侵入边距空间.

所以试试这个:

flex: 1 1 26%;边距:10px;

* {box-sizing: 边框框;}.水平布局{显示:弹性;宽度:400px;}标题 >跨度 {弹性:1 0 26%;/* 调整 */边距:10px;}标题#with-border-padding {flex-wrap: 包裹;}标头#with-border-padding>span {弹性:1 0 26%;/* 调整 */}header#with-border-padding>.button {边框:1px纯黑色;左边距:5px;}标题>.按钮{背景颜色:灰色;}header>.app-name {背景颜色:橙色;}

没有 flex-wrap: wrap,所以它不尊重 flex 33% <br/><header class="horizo​​ntal-layout"><span class="button">A</span><span class="app-name">B</span><span class="button">C</span><span class="button">D</span></标题><br/><br/>WITH flex-wrap: wrap :我希望第一排有 3 个盒子,而向下有 D 个盒子<br/><header id="with-border-padding" class="horizo​​ntal-layout"><span class="button">A</span><span class="app-name">B</span><span class="button">C</span><span class="button">D</span></header>

I'm trying to achieve a simple thing that we have in standard CSS.

Let's say that I have a grid system with 3 columns and box-sizing: border-box.

That means that I will fit 3 boxes and with a margin that will shrink the size to fit max 3 boxes.

But when I try to do that with FLEXBOX, it's a pain!!

So if I have div's with flex: 1 1 33.33%; margin: 10px; I was expecting to have 3 boxes per row... but if I use flex-wrap: wrap, that will not shrink to fit 3 boxes .

Here is a example.. the idea is that the second row would have 3 boxes in a row and fourth box would be in the last row.

Thanks

https://jsfiddle.net/mariohmol/pbkzj984/14/

.horizontal-layout {
  display: flex;
  flex-direction: row;
  width: 400px;
}

header>span {
  /* flex: 1 1 100%; */
  /* flex: 1 0 100%; */
  flex: 1 1 33.33%;
  margin: 10px;
}

header>.button {
  background-color: grey;
}

header>.app-name {
  background-color: orange;
}

header#with-border-padding {
  flex-wrap: wrap;
}

header#with-border-padding>span {
  flex: 1 1 33.33%;
  box-sizing: border-box;
  /* this is not useful at all */
}

header#with-border-padding>.button {
  border: 1px solid black;
  padding-left: 5px;
}

NO flex-wrap: wrap, so it not respects the flex 33% <br/>
<header class="horizontal-layout">
  <span class="button">A</span>
  <span class="app-name">B</span>
  <span class="button">C</span>
  <span class="button">D</span>
</header>
<br/><br/> WITH flex-wrap: wrap : I expect to have 3 boxes in first row and D box in a down<br/>
<header id="with-border-padding" class="horizontal-layout">
  <span class="button">A</span>
  <span class="app-name">B</span>
  <span class="button">C</span>
  <span class="button">D</span>
</header>

解决方案

Keep in mind that box-sizing: border-box brings padding and borders into the width / height calculation, but not margins. Margins are always calculated separately.

The box-sizing property takes two values:

  • content-box
  • border-box

It does not offer padding-box or margin-box.

Consider those terms when referring to the CSS Box Model.

source: W3C

3.1. Changing the Box Model: the box-sizing property

content-box

The specified width and height apply to the width and height respectively of the content box of the element. The padding and border of the element are laid out and drawn outside the specified width and height.

border-box

Length and percentages values for width and height on this element determine the border box of the element. That is, any padding or border specified on the element is laid out and drawn inside this specified width and height. The content width and height are calculated by subtracting the border and padding widths of the respective sides from the specified width and height properties.


Also, an initial setting of a flex container is flex-shrink: 1. This means that flex items can shrink in order to fit within the container.

Therefore, a specified width, height or flex-basis will not hold, unless flex-shrink is disabled.

You can override the default with flex-shrink: 0.

Here's a more complete explanation: What are the differences between flex-basis and width?


Here's a simple solution:

You have four boxes. You want three on row 1 and the last on row 2.

This is what you have:

flex: 1 1 33.33%;
margin: 10px;

This breaks down to:

  • flex-grow: 1
  • flex-shrink: 1
  • flex-basis: 33.33%

We know that box-sizing: border-box factors padding and borders into the flex-basis. That's not a problem. But what about the margins?

Well, since you have flex-grow: 1 on each item, there is no need for flex-basis to be 33.33%.

Since flex-grow will consume any free space on the row, flex-basis only needs to be large enough to enforce a wrap.

Since margins also consume free space, flex-grow will not intrude into the margin space.

So try this instead:

flex: 1 1 26%;
margin: 10px;

* {
  box-sizing: border-box;
}

.horizontal-layout {
  display: flex;
  width: 400px;
}

header > span { 
  flex: 1 0 26%;                    /* ADJUSTED */
  margin: 10px;
}

header#with-border-padding {
  flex-wrap: wrap;
}

header#with-border-padding>span {
  flex: 1 0 26%;                   /* ADJUSTED */
}

header#with-border-padding>.button {
  border: 1px solid black;
  padding-left: 5px;
}

header>.button {
  background-color: grey;
}

header>.app-name {
  background-color: orange;
}

NO flex-wrap: wrap, so it not respects the flex 33% <br/>
<header class="horizontal-layout">
  <span class="button">A</span>
  <span class="app-name">B</span>
  <span class="button">C</span>
  <span class="button">D</span>
</header>
<br/><br/> WITH flex-wrap: wrap : I expect to have 3 boxes in first row and D box in a down<br/>
<header id="with-border-padding" class="horizontal-layout">
  <span class="button">A</span>
  <span class="app-name">B</span>
  <span class="button">C</span>
  <span class="button">D</span>
</header>

这篇关于不考虑边距和框大小的 Flex 项目:边框框的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆