【问题标题】:Pin element (flex item) to bottom of container将元素(弹性项目)固定到容器底部
【发布时间】:2016-01-11 21:57:39
【问题描述】:

我有一个容器作为整个窗口的高度/宽度。在这个容器内,我想要一个垂直和水平居中的表单。下面,我还想要在容器底部基线上的一份副本。类似于下面的糟糕插图。现在我只能让它们都垂直居中,并且找不到一个很好的方法来让底部的复制别针本身到容器的底部。

---------
|       |
|       |
|<form> |
|       |
|<copy> |
---------

.container {
  background-color: #eee;
  height: 100vh;
  width: 100vw;
  padding: 1em;
  display: flex;
  text-align: center;
  justify-content: center;
  flex-direction: column;
}

form {
  
}

.bot {
  align-self: flex-end;
}
<div class="container">
  <form>
    <input type="text" />
    <button type="submit">submit</button>
   </form>
  <p class="bot">Lorem ipsum dolor sit amet, consectetur adipisicing elit. Omnis quae quisquam neque cupiditate adipisci magnam facilis, distinctio suscipit possimus hic voluptatibus in illo est id alias unde sapiente ab eius.</p>
</div>

【问题讨论】:

    标签: html css flexbox


    【解决方案1】:

    更新答案

    使用auto margins,您可以在没有额外标记的情况下将弹性项目组合或打包在一起,或者通过在相反方向应用边距来移动元素(如我的原始答案所示)。在这种情况下,只需在表单上设置margin: auto;这将通知 flex 容器将表单置于所有剩余可用空间的中心:

    .flex-container {
      display: flex;
      flex-direction: column;
      text-align: center;
      height: 150px;
      width: 400px;
      background: #e7e7e7;
    }
     
    form {
      margin: auto;
    }
    
    p {
      margin: 0;
    }
    <div class="flex-container">
      <form>
        <input type="text" />
        <button type="submit">submit</button>
      </form>
      <p class="bot">
        Lorem ipsum dolor sit amet
      </p>
    </div>

    在此处查看其他答案以获得更多信息:

    In CSS Flexbox, why are there no "justify-items" and "justify-self" properties?

    Can't scroll to top of flex item that is overflowing container


    原答案

    “固定”一个 flex 子项的一种聪明方法是在与您希望它去的方向相反的方向上给它一个 auto 边距。在您的情况下,您需要设置

    p.bot {
        margin-top: auto;
    }
    

    并且段落将移动到父 flex 容器的底部。它适用于像这样的简单布局......

    html,
    body {
      margin: 0;
      padding: 0;
    }
    .container {
      background-color: #eee;
      height: 100vh;
      width: 100vw;
      display: flex;
      text-align: center;
      justify-content: center;
      flex-direction: column;
      position: relative;
    }
    form {
      height: 100%;
      display: flex;
      align-items: center;
      justify-content: center;
    }
    .bot {
      margin-top: auto;
    }
    <div class="container">
      <form>
        <input type="text" />
        <button type="submit">submit</button>
      </form>
      <p class="bot">Lorem ipsum dolor sit amet, consectetur adipisicing elit. Omnis quae quisquam neque cupiditate adipisci magnam facilis, distinctio suscipit possimus hic voluptatibus in illo est id alias unde sapiente ab eius.</p>
    </div>

    编辑 注意,我还在.container 中创建了form 嵌套弹性框并将其高度设置为100%,这基本上是在做同样的事情。 Michael_B 在 cmets 中有很好的解释。

    【讨论】:

    • 它真的不起作用。如果您将margin-top: auto 应用于.bot,它确实会将段落发送到底部。但它也将表单一直发送到顶部。您所做的是使form 成为带有height: 100% 的嵌套弹性框。正是这个 flexbox 也将段落保持在底部。在您的 sn-p 中,删除 margin-top: auto。你会看到段落停留在底部。并不是说嵌套的 flexbox 不是一个好的解决方案 ;-)
    • @Michael_B 嗯,你是对的 - 感谢您指出!我想我还有更多的学习要做:)
    • Margin auto 和 flexbox 不应该这样混用。读者:继续往下看正确答案。
    【解决方案2】:

    这是您遇到的问题:

    您已将flex-direction 设置为column。这意味着您已经转移了main axis to vertical, and the cross axis to horizontal

    align-* 属性沿交叉轴工作。所以当你告诉 .botalign-self: flex-end 时,你实际上是在告诉它向右移动,而不是向下移动。

    但在这种情况下它不会右移,因为该项目占据了容器的整个宽度,因此没有空间可以移动。但是,如果你限制它的宽度...http://jsfiddle.net/t7hap87o/

    想要将&lt;copy&gt; 固定到屏幕底部,flexbox 有一点限制:有no property similar to align-self for the main axis

    还有其他几个选项可以完成工作。您可以在当前容器中嵌套 flexbox,或者从该容器中移除 .bot 并将其放置在另一个容器中。

    Flexbox 也允许absolutely-positioned flex children。试试这个:

    .container {
        position: relative; /* establish nearest positioned ancestor for abs. positioning */
    }
    
    .bot {
        position: absolute;
        bottom: 0;
    }
    

    DEMO

    注意:.bot 上的 margin-top: auto 在当前 HTML 结构中不起作用。事实上,它会将目标元素固定在底部。但它也会将居中的元素一直推到顶部。

    【讨论】:

      【解决方案3】:

      align-self: flex-end; 没有达到预期的效果,因为 flex 子项按列排列。

      在不添加任何额外标记的情况下,根据需要进行排列的一种简单方法是:

      • 将页脚元素移出.container

        <div class="container"></div>
        <p class="bot"></p>
        
      • 将正文(或其他包装器,如果需要)提供display: flex,以便.container 和页脚是弹性子代(兄弟姐妹)。

      • .container 一个弹性属性flex: 1 1 100%;。这将导致它从其初始值 100% 增长和收缩。页脚被向下推,但它的高度在容器收缩时适应。

      • 给页脚一个 flex 属性 flex: 1 1 auto。这现在将被推到底部,但会随着内容的增加而增加高度。

      详细了解 flex 属性 over on the MDN

      示例

      * {
        margin: 0;
        padding: 0;
      
      }
      body {
        display: flex;
        flex-direction: column;
        height: 100vh;
        width: 100vw;
      }
      .container {
        display: flex;
        flex: 1 1 100%;
        flex-direction: column;
        justify-content: center;
        text-align: center;
        background: #EEE;
      }
      .bot {
        flex: 1 1 auto;
        text-align: center;
        background: #EEE;
        padding: 1em;
      }
      <div class="container">
        <form>
          <input type="text" />
          <button type="submit">submit</button>
        </form>
      </div>
      <p class="bot">Lorem ipsum dolor sit amet, consectetur adipisicing elit. Omnis quae quisquam neque cupiditate adipisci magnam facilis, distinctio suscipit possimus hic voluptatibus in illo est id alias unde sapiente ab eius.</p>

      【讨论】:

        【解决方案4】:

        您可以在容器上使用:before创建一个伪元素,使其分为三个部分,并使用justify-content: space-between;

        * {
            margin: 0;
        }
        .container {
            background-color: #eee;
            height: 100vh;
            width: 100vw;
            display: flex;
            justify-content: space-between;
            flex-direction: column;
            text-align: center;
        }
        .container:before {
            content: '';
        }
        <div class="container">
            <form><input type="text" /> <button type="submit">submit</button></form>
            <p>Lorem ipsum dolor sit amet, consectetur adipisicing elit. Omnis quae quisquam neque cupiditate adipisci magnam facilis, distinctio suscipit possimus hic voluptatibus in illo est id alias unde sapiente ab eius.</p>
        </div>

        jsfiddle

        【讨论】:

        • 此解决方案的唯一问题是伪元素和页脚 (.bot) 需要始终保持相同的高度。否则,表单将不会在容器中垂直居中。
        • 事实上,在再次阅读问题后,现有答案都不是正确的,注意OP希望
          在整个页面中垂直居中。
        • 正确。但我相信我的演示符合这个要求。
        • 哦,刚刚看到了,是的位置方法。唯一的问题是小视口高度上的重叠。
        • 您的解决方案很好。它只需要边缘项目的高度相等,中间项目就可以完美居中。只是想指出这一点。
        【解决方案5】:

        flex-direction 改回column,将其中一个容器设置为width: 100% 并使用flex-wrap: wrap 来实现此目的。

        类似这样的东西(它可以在带有供应商前缀的 Firefox 和 IE 10+ 中使用):

        .container {
          background-color: #333;
          width: 100%;
          height: 100vh;
          display: flex;
          flex-wrap: wrap;
          align-items: flex-end;
          justify-content: center;
        }
        
        .footer {
          width: 100px;
          height: 20px;
          margin-top: -20px; /* set the margin top to negative what the 
                                height is so the form is perfectly centered */
          background-color: #900;
          color: #fff;
          text-align: center;
        }
        
        .form-wrapper {
          width: 100%; /* needs to be 100% to force the items to wrap */
          height: 50px;
          background-color: #009;
          
          /* center the form inside the wrapper */
          display: flex;
          align-items: center;
          justify-content: center;
        }
        <div class="container">
          <div class="form-wrapper">
            <form>
              <input type="text">
              <button type="submit">submit</button>
            </form>
          </div>
          <div class="footer">footer content</div>
        </div>

        【讨论】:

          猜你喜欢
          • 2018-01-15
          • 2017-06-27
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          相关资源
          最近更新 更多