在 2 个不同宽度的弹性项目之间水平居中弹性项目

Horizontally center flex item between 2 flex items of different widths

假设我有 3 个 div 水平显示 flexbox

 |     |-div1-| |-center-div-| |-wider-div-|     |

我希望中心 div 与父对象的中间对齐。我怎样才能做到这一点? justify-content 将根据所有宽度的总和将所有 3 个 div 居中,并将 align-self: center 应用到中间 div 什么都不做,因为对齐 属性操纵另一个轴上的定位。

是否有响应式 CSS 解决方案,或者我应该求助于 jQuery?

ul {
    display: flex;
    justify-content: center;
    width: 100%;
    background-color: purple;
}
li {
    background-color: red;
    border: 5px solid blue;
    list-style: none;
}
<ul>
    <li><a href = "#">short</a></li>
    <li><a href = "#">want center</a></li>
    <li><a href = "#">loooooooooooooooooong</a></li>
</ul>

这个问题的说明: https://jsfiddle.net/7w8mp8Lj/2/

可以使用绝对定位,让非居中的项脱离流,这样就不会影响居中了。

ul {
  display: flex;
  justify-content: center;
  background-color: purple;
  padding: 0;
  list-style: none;
}
li {
  position: relative;
}
li > a {
  display: block;
  background-color: red;
  border: 5px solid blue;
}
li:first-child > a {
  position: absolute;
  right: 0;
}
li:last-child > a {
  position: absolute;
  left: 0;
}
<ul>
  <li><a href="#">short</a></li>
  <li><a href="#">want center</a></li>
  <li><a href="#">loooooooooooooooooong</a></li>
</ul>

但是,请注意,您将失去灵活性,因为 flex 容器的绝对定位子元素不参与 flex 布局(重新排序步骤除外)。

您可以将第一个和最后一个 li 设置为增长 flex: 1,将 a 设置为内嵌块,并将文本对齐 1/2/3 li 设置为 right/center/left.

jsfiddle

ul {
    display: flex;
    justify-content: center;
    width: 100%;
    background-color: purple;
    list-style: none;
    padding: 0;
}
li:nth-child(1) {
    text-align: right;
    flex: 1;
}
li:nth-child(2) {
    text-align: center;
}
li:nth-child(3) {
    text-align: left;
    flex: 1;
}
li a {
    display: inline-block;
    background-color: red;
    border: 5px solid blue;
}
<ul>
    <li><a href="#">short</a></li>
    <li><a href="#">want center</a></li>
    <li><a href="#">loooooooooooooooooong</a></li>
</ul>

这里有一个 flex 方法可以完美地将中间项目居中:

  • 没有jQuery
  • 无绝对定位
  • HTML
  • 没有变化

ul {
  display: flex;
  padding: 0;
}
li {
  display: flex;
  justify-content: center;
  flex: 1;
  background-color: red;
  border: 2px solid blue;
}
li:first-child > a {
  margin-right: auto;
}
li:last-child > a {
  margin-left: auto;
}
<ul>
  <li>
    <a href="#">short</a>
  </li>
  <li>
    <a href="#">want center</a>
  </li>
  <li>
    <a href="#">loooooooooooooooooong</a>
  </li>
</ul>

jsFiddle

工作原理如下:

  • ul 是主弹性容器。
  • 每个 li 弹性项目被赋予 flex: 1 容器 space 的平等分配。
  • 现在 li 占用了行中的所有 space 并且宽度相等。
  • 使每个 li 成为弹性容器并添加 justify-content: center
  • 现在每个锚元素都是一个居中的弹性项目。
  • 使用弹性 auto 边距左右移动外部锚点。

我用的是一个弹性容器,里面有三个盒子,其中两个——左右——宽度相同,本身就是弹性容器,包裹着任意宽度的内容:

[(a box)        ]     [centered content]    [    (a longer box)]
  left wrapper                                 right wrapper

代码如下:

<div class="test">
    <div class="wrapper left">
        <div class="box one"></div>
    </div>
    <div class="box two"></div>
    <div class="wrapper right">
        <div class="box three"></div>
    </div>
</div>

CSS:

.test {
    height: 50px;
    display: flex;
    justify-content: center;
}

.wrapper {
    width: 33%;
    display: flex;
}

.wrapper.left {
    justify-content: flex-end;
}

.box {
    border: 1px solid red;
}

.one {
    width: 100px;
}

.two {
    width: 50px;
}

.three {
    width: 150px;
}