Html 当侧边项目具有不同的宽度时,保持中间项目居中
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/32378953/
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
Keep the middle item centered when side items have different widths
提问by Mark
Imagine the following layout, where the dots represent the space between the boxes:
想象一下以下布局,其中的点代表框之间的空间:
[Left box]......[Center box]......[Right box]
When I remove the right box, I like the center box to still be in the center, like so:
当我移除右边的盒子时,我喜欢中心盒子仍然在中心,就像这样:
[Left box]......[Center box].................
The same goes for if I would remove the left box.
如果我删除左框也是如此。
................[Center box].................
Now when the content within the center box gets longer, it will take up as much available space as needed while remaining centered. The left and right box will never shrink and thus when where is no space left the overflow:hidden
and text-overflow: ellipsis
will come in effect to break the content;
现在,当中心框内的内容变长时,它将根据需要占用尽可能多的可用空间,同时保持居中。左右框永远不会缩小,因此当没有空间留下时overflow:hidden
,text-overflow: ellipsis
将生效以破坏内容;
[Left box][Center boxxxxxxxxxxxxx][Right box]
All the above is my ideal situation, but I have no idea how to accomplish this effect. Because when I create a flex structure like so:
以上都是我的理想情况,但是我不知道如何实现这种效果。因为当我像这样创建一个 flex 结构时:
.parent {
display : flex; // flex box
justify-content : space-between; // horizontal alignment
align-content : center; // vertical alignment
}
If the left and right box would be exactly the same size, I get the desired effect. However when one of the two is from a different size the centered box is not truly centered anymore.
如果左右框的大小完全相同,我就会得到想要的效果。然而,当两者之一来自不同的尺寸时,居中的框不再真正居中。
Is there anyone that can help me?
有没有人可以帮助我?
Update
更新
A justify-self
would be nice, this would be ideal:
Ajustify-self
会很好,这将是理想的:
.leftBox {
justify-self : flex-start;
}
.rightBox {
justify-self : flex-end;
}
采纳答案by Michael Benjamin
If the left and right boxes would be exactly the same size, I get the desired effect. However when one of the two is a different size the centered box is not truly centered anymore. Is there anyone that can help me?
如果左右框的大小完全相同,我就会得到想要的效果。然而,当两者之一的大小不同时,居中的框不再真正居中。有没有人可以帮助我?
Here's a method using flexbox to center the middle item, regardless of the width of siblings.
这是一种使用 flexbox 将中间项居中的方法,无论兄弟姐妹的宽度如何。
Key features:
主要特点:
- pure CSS
- no absolute positioning
- no JS/jQuery
- 纯 CSS
- 没有绝对定位
- 没有 JS/jQuery
Use nested flex containers and auto
margins:
使用嵌套的 flex 容器和auto
边距:
.container {
display: flex;
}
.box {
flex: 1;
display: flex;
justify-content: center;
}
.box:first-child > span { margin-right: auto; }
.box:last-child > span { margin-left: auto; }
/* non-essential */
.box {
align-items: center;
border: 1px solid #ccc;
background-color: lightgreen;
height: 40px;
}
p {
text-align: center;
margin: 5px 0 0 0;
}
<div class="container">
<div class="box"><span>short text</span></div>
<div class="box"><span>centered text</span></div>
<div class="box"><span>loooooooooooooooong text</span></div>
</div>
<p>↑<br>true center</p>
Here's how it works:
这是它的工作原理:
- The top-level div (
.container
) is a flex container. - Each child div (
.box
) is now a flex item. - Each
.box
item is givenflex: 1
in order to distribute container space equally (more details). - Now the items are consuming all space in the row and are equal width.
- Make each item a (nested) flex container and add
justify-content: center
. - Now each
span
element is a centered flex item. - Use flex
auto
margins to shift the outerspan
s left and right.
- 顶层 div (
.container
) 是一个 flex 容器。 - 每个子 div (
.box
) 现在都是一个弹性项目。 .box
给出每个项目是flex: 1
为了平均分配容器空间(更多详细信息)。- 现在这些项目消耗了行中的所有空间并且宽度相等。
- 使每个项目成为(嵌套的)弹性容器并添加
justify-content: center
. - 现在每个
span
元素都是一个居中的弹性项目。 - 使用 flex
auto
margins 左右移动外部span
s。
You could also forgo justify-content
and use auto
margins exclusively.
您也可以放弃justify-content
并auto
专门使用边距。
But justify-content
can work here because auto
margins always have priority.
但justify-content
可以在这里工作,因为auto
利润率总是优先的。
8.1. Aligning with
auto
marginsPrior to alignment via
justify-content
andalign-self
, any positive free space is distributed to auto margins in that dimension.
在通过
justify-content
和对齐之前align-self
,任何正自由空间都会分配到该维度的自动边距。
回答by Oriol
- Use three flex items in the container
- Set
flex: 1
to the first and last ones. This makes them grow equally to fill the available space left by the middle one. - Thus, the middle one will tend to be centered.
However, if the first or last item has a wide content, that flex item will also grow due to the new
min-width: auto
initial value.Note Chrome doesn't seem to implement this properly. However, you can set
min-width
to-webkit-max-content
or-webkit-min-content
and it will work too.Only in that case the middle element will be pushed out of the center.
- 在容器中使用三个弹性项目
- 设置
flex: 1
为第一个和最后一个。这使它们均匀增长以填充中间的可用空间。 - 因此,中间的将趋于居中。
但是,如果第一个或最后一个项目具有广泛的内容,那么该弹性项目也将由于新的
min-width: auto
初始值而增长。注意 Chrome 似乎没有正确实现这一点。但是,您可以设置
min-width
为-webkit-max-content
or-webkit-min-content
并且它也可以工作。只有在这种情况下,中间元素才会被推出中心。
.outer-wrapper {
display: flex;
}
.item {
background: lime;
margin: 5px;
}
.left.inner-wrapper, .right.inner-wrapper {
flex: 1;
display: flex;
min-width: -webkit-min-content; /* Workaround to Chrome bug */
}
.right.inner-wrapper {
justify-content: flex-end;
}
.animate {
animation: anim 5s infinite alternate;
}
@keyframes anim {
from { min-width: 0 }
to { min-width: 100vw; }
}
<div class="outer-wrapper">
<div class="left inner-wrapper">
<div class="item animate">Left</div>
</div>
<div class="center inner-wrapper">
<div class="item">Center</div>
</div>
<div class="right inner-wrapper">
<div class="item">Right</div>
</div>
</div>
<!-- Analogous to above --> <div class="outer-wrapper"><div class="left inner-wrapper"><div class="item">Left</div></div><div class="center inner-wrapper"><div class="item animate">Center</div></div><div class="right inner-wrapper"><div class="item">Right</div></div></div><div class="outer-wrapper"><div class="left inner-wrapper"><div class="item">Left</div></div><div class="center inner-wrapper"><div class="item">Center</div></div><div class="right inner-wrapper"><div class="item animate">Right</div></div></div>
回答by Johan
Instead of defaulting to using flexbox, using grid solves it in 2 lines of CSS without additional markup inside the top level children.
与默认使用 flexbox 不同,使用 grid 可以在 2 行 CSS 中解决它,而无需在顶级子项中添加额外的标记。
HTML:
HTML:
<header class="header">
<div class="left">variable content</div>
<div class="middle">variable content</div>
<div class="right">variable content which happens to be very long</div>
</header>
CSS:
CSS:
.header {
display: grid;
grid-template-columns: [first] 20% auto [last] 20%;
}
.middle {
/* use either */
margin: 0 auto;
/* or */
text-align: center;
}
Flexbox rocks but shouldn't be the answer for everything. In this case grid is clearly the cleanest option.
Flexbox 摇滚,但不应该是一切的答案。在这种情况下,网格显然是最干净的选择。
Even made a codepen for your testing pleasure: https://codepen.io/anon/pen/mooQOV
甚至为您的测试乐趣制作了一个代码笔:https://codepen.io/anon/pen/mooQOV
回答by Michael Morton
You can do this like so:
你可以这样做:
.bar {
display: flex;
background: #B0BEC5;
}
.l {
width: 50%;
flex-shrink: 1;
display: flex;
}
.l-content {
background: #9C27B0;
}
.m {
flex-shrink: 0;
}
.m-content {
text-align: center;
background: #2196F3;
}
.r {
width: 50%;
flex-shrink: 1;
display: flex;
flex-direction: row-reverse;
}
.r-content {
background: #E91E63;
}
<div class="bar">
<div class="l">
<div class="l-content">This is really long content. More content. So much content.</div>
</div>
<div class="m">
<div class="m-content">This will always be in the center.</div>
</div>
<div class="r">
<div class="r-content">This is short.</div>
</div>
</div>
回答by Erfan Azary
you can also use this simple way to reach exact center alignment for middle element :
您还可以使用这种简单的方法来实现中间元素的精确居中对齐:
.container {
display: flex;
justify-content: space-between;
}
.container .sibling {
display: flex;
align-items: center;
height: 50px;
background-color: gray;
}
.container .sibling:first-child {
width: 50%;
display: flex;
justify-content: space-between;
}
.container .sibling:last-child {
justify-content: flex-end;
width: 50%;
box-sizing: border-box;
padding-left: 100px; /* .center's width divided by 2 */
}
.container .sibling:last-child .content {
text-align: right;
}
.container .sibling .center {
height: 100%;
width: 200px;
background-color: lightgreen;
transform: translateX(50%);
}
codepen: https://codepen.io/ErAz7/pen/mdeBKLG
代码笔:https://codepen.io/ErAz7/pen/mdeBKLG