提问人:Michael Benjamin 提问时间:9/13/2015 最后编辑:TylerHMichael Benjamin 更新时间:5/26/2023 访问量:407183
在 CSS Flexbox 中,为什么没有 “justify-items” 和 “justify-self” 属性?
In CSS Flexbox, why are there no "justify-items" and "justify-self" properties?
问:
考虑柔性容器的主轴和十字轴:
来源:W3C
要沿主轴对齐 flex 项目,有一个属性:
要沿十字轴对齐弯曲项目,有三个属性:
在上图中,主轴是水平的,十字轴是垂直的。这些是 flex 容器的默认方向。
但是,这些方向可以很容易地与 flex-direction
属性互换。
/* main axis is horizontal, cross axis is vertical */
flex-direction: row;
flex-direction: row-reverse;
/* main axis is vertical, cross axis is horizontal */
flex-direction: column;
flex-direction: column-reverse;
(十字轴始终垂直于主轴。
我在描述轴的工作原理时的观点是,这两个方向似乎都没有什么特别之处。主轴、十字轴,它们在重要性方面都是相等的,可以很容易地来回切换。flex-direction
那么,为什么十字轴会获得两个额外的对齐属性呢?
为什么将 align-content
和 align-items
合并为主轴的一个属性?
为什么主轴没有获得对齐自
属性?
这些属性有用的方案:
将 Flex 物品放在 Flex 容器的一角
#box3 { align-self: flex-end; justify-self: flex-end; }
使一组 Flex 项目向右对齐 (),但将第一项向左对齐 (
justify-content: flex-end
justify-self: flex-start
)
考虑包含一组导航项和徽标的标题部分。使用 justify-self
,徽标可以向左对齐,而导航项保持在最右边,并且整个东西可以平滑地调整(“弯曲”)以适应不同的屏幕尺寸。
- 在一行三个柔性项目中,将中间项目固定在容器的中心 (),并将相邻项目与容器边缘 ( 和 ) 对齐。
justify-content: center
justify-self: flex-start
justify-self: flex-end
请注意,如果相邻项具有不同的宽度,则 justify-content
属性上的值 space-around 和 space-between
不会使中间项围绕容器居中。
#container {
display: flex;
justify-content: space-between;
background-color: lightyellow;
}
.box {
height: 50px;
width: 75px;
background-color: springgreen;
}
.box1 {
width: 100px;
}
.box3 {
width: 200px;
}
#center {
text-align: center;
margin-bottom: 5px;
}
#center > span {
background-color: aqua;
padding: 2px;
}
<div id="center">
<span>TRUE CENTER</span>
</div>
<div id="container">
<div class="box box1"></div>
<div class="box box2"></div>
<div class="box box3"></div>
</div>
<p>note that the middlebox will only be truly centered if adjacent boxes are equal width</p>
在撰写本文时,Flexbox 规范中没有提到 或。justify-self
justify-items
但是,在 CSS Box Alignment Module(这是 W3C 未完成的提案,旨在建立一组通用的对齐属性以用于所有 Box 模型)中,有如下内容:
来源:W3C
你会注意到这一点,并且正在考虑......但不适用于 Flexbox。justify-self
justify-items
最后,我将重申一个主要问题:
为什么没有“justify-items”和“justify-self”属性?
答:
这个问题在 www-style 列表中被问到,Tab Atkins(规范编辑器)给出了一个答案,解释了原因。我将在这里详细阐述这一点。
首先,我们首先假设我们的 flex 容器是单行 ()。在这种情况下,主轴和十字轴之间明显存在对齐差异 - 在主轴上堆叠了多个项目,但只有一个项目堆叠在十字轴上。因此,在十字轴中有一个可自定义的每个项目的“对齐自我”是有意义的(因为每个项目都是单独对齐的,单独对齐),而在主轴中没有意义(因为在那里,项目是集体对齐的)。flex-wrap: nowrap
对于多行 flexbox,相同的逻辑适用于每条“flex line”。在给定的行中,项目在十字轴中单独对齐(因为在十字轴中每行只有一个项目),而不是在主轴中整体对齐。
这是另一种表述方式:所以,所有的 和 属性都是关于如何在事物周围分配额外的空间。但关键的区别在于,版本适用于该轴中只有一个事物的情况,而版本适用于该轴中可能存在许多事物的情况。单事物方案与多事物方案是不同类型的问题,因此它们有不同类型的可用选项 -- 例如,/ 值对 有意义,但对 没有意义。*-self
*-content
*-self
*-content
space-around
space-between
*-content
*-self
SO:在弹性盒子的主轴中,有很多东西可以分配空间。因此,属性在那里有意义,但不是属性。*-content
*-self
相比之下,在十字轴上,我们同时具有 a 和 a 属性。一个确定我们如何在许多弯曲线 () 周围分配空间,而另一个 () 确定如何在给定弯曲线内的十字轴中分配单个弯曲项目周围的空间。*-self
*-content
align-content
align-self
(我在这里忽略了属性,因为它们只是为 .*-items
*-self
评论
justify-self
justify-self
justify-self
*-self
*-content
auto
我知道这不是一个答案,但我想为这件事做出贡献,因为它是值得的。如果他们能发布 flexbox 以使其真正灵活,那就太好了。justify-self
我相信,当轴上有多个项目时,最合乎逻辑的行为方式是将自身与其最近的邻居(或边缘)对齐,如下所示。justify-self
我真的希望 W3C 注意到这一点,并且至少会考虑它。=)
这样,无论左右框的大小如何,您都可以拥有真正居中的项目。当其中一个盒子到达中心盒子的点时,它只会推动它,直到没有更多的空间可以分配。
制作令人敬畏的布局的难易程度是无穷无尽的,看看这个“复杂”的例子。
评论
justify-self
justify-items
auto
justify-self
auto
justify-content
grid-template-columns: minmax(50px, 1fr) 1200px minmax(100px, 1fr)
min-content
沿主轴对齐 Flex 项目的方法
如问题所述:
要沿主轴对齐 flex 项目,有一个属性:
justify-content
要沿十字轴对齐 flex 项目,有三个属性:
align-content、align-items
和
align-self
。
然后问题问:
为什么没有和属性?
justify-items
justify-self
一个答案可能是:因为它们不是必需的。
flexbox 规范提供了两种沿主轴对齐 flex 项目的方法:
- 关键字属性,以及
justify-content
自动
保证金
对齐内容
justify-content
属性沿 flex 容器的主轴对齐 flex 项。
它应用于 flex 容器,但仅影响 flex 项目。
有五个对齐选项:
flex-start
~ Flex 物品被打包到生产线的起点。flex-end
~ Flex 物品被包装在生产线的末端。center
~ Flex 物品被打包到队伍的中心。间距
~ Flex 项目是均匀分布的,第一个项目与容器的一个边缘对齐,最后一个项目与相反的边缘对齐。第一项和最后一项使用的边缘取决于弯曲方向
和书写模式( 或 )。ltr
rtl
space-around
~ 除了两端有一半大小的空间外,与此相同。space-between
自动边距
使用自动
页边距,弹性项目可以居中、间隔或打包到子组中。
与应用于 flex 容器的 不同,flex 项目有边距。justify-content
auto
它们通过在指定方向上消耗所有可用空间来工作。
将一组 flex 项目向右对齐,但将第一个项目向左对齐
问题中的场景:
使一组 Flex 项目右对齐 () 但让第一项向左对齐 (
justify-content: flex-end
justify-self: flex-start
)考虑包含一组导航项和徽标的标题部分。使用
justify-self
,徽标可以左对齐,而导航项保持不变 最右边,整个事情平滑地调整(“弯曲”)到 不同的屏幕尺寸。
其他有用的方案:
在角落放置一个柔性项目
问题中的场景:
- 将 Flex 项目放在角落
.box { align-self: flex-end; justify-self: flex-end; }
垂直和水平居中 Flex 项目
margin: auto
是 和 的替代项。justify-content: center
align-items: center
而不是 flex 容器上的此代码:
.container {
justify-content: center;
align-items: center;
}
您可以在 flex 项目上使用它:
.box56 {
margin: auto;
}
当将溢出容器的 flex 项居中时,此替代方法非常有用。
将一个 flex 项目居中,并在第一个项目和边缘之间将第二个 flex 项目居中
弹性容器通过分配可用空间来对齐弹性项目。
因此,为了创造相等的平衡,以便中间物品可以在容器中居中,而单个物品并排,必须引入平衡。
在下面的例子中,引入了不可见的第三柔性项目(方框61和68),以平衡“真实”项目(方框63和66)。
当然,这种方法在语义方面并不是什么好事。
或者,您可以使用伪元素而不是实际的 DOM 元素。或者您可以使用绝对定位。此处介绍了所有三种方法: 居中和对齐的柔性项目
注意:上面的示例仅在最外层的物品高度/宽度相等时才有效 - 就真正的居中而言。当弹性项目长度不同时,请参阅下一个示例。
当相邻项目的大小不同时,将 Flex 项目居中
问题中的场景:
在一排三个柔性项目中,将中间项目固定在容器的中心 () 并将相邻的 项添加到容器边缘( 和 )。
justify-content: center
justify-self: flex-start
justify-self: flex-end
请注意,如果相邻项具有不同的宽度,
则 justify-content
属性上的值space-around 和 space-between
不会使中间项相对于容器保持居中(请参阅演示)。
如前所述,除非所有 flex 项目都具有相等的宽度或高度(取决于 ),否则中间项目无法真正居中。这个问题为属性(当然是为处理任务而设计的)提供了强有力的理由。flex-direction
justify-self
#container {
display: flex;
justify-content: space-between;
background-color: lightyellow;
}
.box {
height: 50px;
width: 75px;
background-color: springgreen;
}
.box1 {
width: 100px;
}
.box3 {
width: 200px;
}
#center {
text-align: center;
margin-bottom: 5px;
}
#center > span {
background-color: aqua;
padding: 2px;
}
<div id="center">
<span>TRUE CENTER</span>
</div>
<div id="container">
<div class="box box1"></div>
<div class="box box2"></div>
<div class="box box3"></div>
</div>
<p>The middle box will be truly centered only if adjacent boxes are equal width.</p>
以下是解决此问题的两种方法:
解决方案#1:绝对定位
flexbox 规范允许对柔性项目进行绝对定位。这允许中间项目完美地居中,而不管其兄弟姐妹的大小如何。
请记住,与所有绝对定位的元素一样,这些项目将从文档流中删除。这意味着它们不会占用容器中的空间,并且可以与它们的兄弟姐妹重叠。
在下面的示例中,中间项目以绝对定位居中,外部项目保持流动。但是,同样的布局可以以相反的方式实现:将中间物品居中,并绝对定位外部物品。justify-content: center
解决方案#2:嵌套Flex容器(无绝对定位)
.container {
display: flex;
}
.box {
flex: 1;
display: flex;
justify-content: center;
}
.box71 > span { margin-right: auto; }
.box73 > span { margin-left: auto; }
/* non-essential */
.box {
align-items: center;
border: 1px solid #ccc;
background-color: lightgreen;
height: 40px;
}
<div class="container">
<div class="box box71"><span>71 short</span></div>
<div class="box box72"><span>72 centered</span></div>
<div class="box box73"><span>73 loooooooooooooooong</span></div>
</div>
其工作原理如下:
- 顶级 div () 是一个 flex 容器。
.container
- 每个子 div () 现在都是一个 flex 项。
.box
- 给出每个项目是为了平均分配容器空间。
.box
flex: 1
- 现在,这些项目占用了行中的所有空间,并且宽度相等。
- 将每个项目设置为一个(嵌套的)flex 容器,并添加 .
justify-content: center
- 现在,每个元素都是一个居中的 flex 项目。
span
- 使用弯曲边距左右移动外部 s。
auto
span
您也可以放弃并专门使用边距。justify-content
auto
但可以在这里工作,因为利润率总是有优先权。从规格:justify-content
auto
在通过 和 对齐之前,任何 正自由空间分布到该维度中的自动边距。
justify-content
align-self
justify-content:空间相同(概念)
回到 justify-content
一分钟,这里有一个关于另一个选项的想法。
space-same
~ 和 的混合体。Flex 项目是均匀间隔的 (like ),除了两端的半大小空间 (like ) 之外,两端都有全尺寸的空间。space-between
space-around
space-between
space-around
这种布局可以通过 flex 容器上的 ::before
和 ::after
伪元素来实现。
更新:浏览器已经开始实现空间均匀
,从而实现了上述目标。有关详细信息,请参阅此帖子: 弹性项目之间的空间相等
PLAYGROUND(包含上述所有示例的代码)
评论
justify-content
auto
align-items
align-self
align-content
justify-self
auto
justify-self: center
space-same
space-evenly
space-evenly
我知道这不使用 flexbox,但对于三个项目(一个在左边,一个在中间,一个在右边)的简单用例,这可以很容易地在父项、子项上使用以及用于定位这些子项。display: grid
grid-area: 1/1/1/1;
justify-self
<div style="border: 1px solid red; display: grid; width: 100px; height: 25px;">
<div style="border: 1px solid blue; width: 25px; grid-area: 1/1/1/1; justify-self: left;"></div>
<div style="border: 1px solid blue; width: 25px; grid-area: 1/1/1/1; justify-self: center;"></div>
<div style="border: 1px solid blue; width: 25px; grid-area: 1/1/1/1; justify-self: right;"></div>
</div>
评论
我刚刚找到了我自己解决这个问题的方法,或者至少是我的问题。
我用而不是.justify-content: space-around
justify-content: space-between;
这样,结束元素将粘在顶部和底部,如果需要,您可以自定义边距。
评论
这是由于 flexbox 的一维性质,并且沿主轴可能有多个项目,因此无法证明单个项目的合理性。若要在 flexbox 中沿主内联轴对齐项目,请使用该属性。justify-content
评论
justify-self
justify-content: space-between
justify-self: center
justify-self
为 flex 项目工作?我想说的是,边距已经适用于弹性项目没有太大区别。在您的第二个示例中,在项目 d 上将其移动到远边缘。这本身就是一个很棒的功能,利润率已经可以做到。我发布了一个带有演示的答案。auto
justify-self: flex-end
auto
{justify|align} -self
值无关——在主轴上没有这样的盒子,用于对齐一个 flex 项目。justify-content
justify-self
{justify|align}-self
justify-self
justify-content
justify-content
justify-content