【问题标题】:Height is not correct in flexbox items in Chrome [duplicate]Chrome 中 flexbox 项目的高度不正确 [重复]
【发布时间】:2016-02-08 22:31:40
【问题描述】:

对于任何 CSS 专家,我都有一个棘手的问题。 我的绿色 div 有一个灵活的高度,占据了剩余的高度。 现在我想在那个 div 里面放一个 div,它应该是绿色 div 的一半。但似乎 Chrome 将其视为整个页面的一半而不是弹性项目。

http://jsfiddle.net/unh5rw9t/1/

HTML

<body>
    <div id="wrapper">
        <div id="menu">
            1
        </div>
        <div id="content">2
            <div id="half_of_content">2.1</div>
        </div>
        <div id="footer" style="">
            3
        </div>
    </div>
</body>

CSS

html,body {
    height: 100%;
    margin: 0;
}

#wrapper {
    display: flex;
  flex-flow: column;
    height: 100%;
}

#menu {
    height: 70px; 
    background-color: purple
}

#content {
    flex: 1;
    height: 100%;
    background-color: green;
}

#half_of_content {
    height: 50%;
    background-color: yellow;
}

#footer {
    height: 100px; 
    background-color: cyan
}

【问题讨论】:

    标签: html css flexbox


    【解决方案1】:

    @Michael_Bexplained 为什么 Chrome 会这样:

    你给了body 一个height: 100%。然后给了它的孩子(.wrapperheight: 100%。然后给它的孩子(.content)一个height: 100%所以它们的高度都是一样的。 给下一个孩子 (#half_of_content) height: 50% 自然是 50% 的高度 body.

    但是,Firefox 不同意,因为事实上.content 中的height: 100% 被忽略了,它的高度是根据flex: 1 计算的。

    也就是说,Chrome 会根据父级的height 属性的值来解析百分比。 Firefox 会根据父级的已解析灵活高度来执行此操作。

    正确的行为是 Firefox 的行为。根据Definite and Indefinite Sizes

    如果要根据flex item 解决百分比 main sizeflex item 有一个definiteflex basisflex container 有一个definitemain sizeflex itemmain size 必须被视为 definite 用于解析百分比,以及 百分比必须针对 flexed main sizeflex item(也就是下面的布局算法经过 flex itemflex container 已完成,flex item 已获得其最终大小。

    以下是 Chrome 的解决方法:

    #content {
      display: flex;
      flex-direction: column;
    }
    #content::after {
      content: '';
      flex: 1;
    }
    #half_of_content {
      flex: 1;
      height: auto;
    }
    

    这样#content 中的可用空间将在#half_of_content::after 伪元素之间平均分配。

    假设#content 没有其他内容,#half_of_content 将是50%。在你的例子中,你有一个2,所以它会比50%少一点。

    html,
    body {
      height: 100%;
      margin: 0;
    }
    #wrapper {
      display: flex;
      flex-flow: column;
      height: 100%;
    }
    #menu {
      height: 70px;
      background-color: purple
    }
    #content {
      flex: 1;
      height: 100%;
      background-color: green;
      display: flex;
      flex-direction: column;
    }
    #content::after {
      content: '';
      flex: 1;
    }
    #half_of_content {
      flex: 1;
      background-color: yellow;
    }
    #footer {
      height: 100px;
      background-color: cyan
    }
    <div id="wrapper">
      <div id="menu">
        1
      </div>
      <div id="content">2
        <div id="half_of_content">2.1</div>
      </div>
      <div id="footer" style="">
        3
      </div>
    </div>

    【讨论】:

    • 我能否在#half_of_content 容器中使用正常的高度百分比计算而不进行丑陋的修复?因为我以后要划分空​​间..
    • @Doodlemeat 由于#half_of_content 具有height: auto,因此您不能在其子代的height 中使用百分比。但是您可以再次使用相同的技巧,例如如果你想让一个孩子成为70% 设置flex: 70 并添加一个带有flex: 100 的伪元素。
    • 这是 Chrome 和 FF 之间的一个有趣的区别。我认为传统上,在计算百分比高度时,浏览器将spec 解释为由height 属性定义的高度。当dealing with percentage heights 时,我从未见过min-heightmax-heightflex-basis(直到现在)在父母身上工作。
    • 该规范,正如您所指出的,它有点旧,似乎需要一个高度(通用术语)而不是 height,尽管 height 是主要的实现。看起来 FF 正在放松其解释。
    • @Michael_B IMO 使用解析高度而不是 height 的值的 Firefox 实现更有意义。前几天我发现了另一个有趣的案例,容器的高度并不直接取决于内容的高度,而是通过min-height: auto 实现的。我想我们将不得不等到新的规范澄清这些情况。
    【解决方案2】:

    你绝对可以定位div id="half_of_content"

    #content {
        flex: 1;
        height: 100%;
        background-color: green;
        position: relative; /* new */
    }
    
    #half_of_content {
        height: 50%;
        background-color: yellow;
        position: absolute; /* new */
        width: 100%; /* new */
    }
    

    DEMO

    关于你的陈述:

    但似乎 Chrome 将其视为整个页面的一半 而不是弹性项目。

    你给了body 一个height: 100%。然后给它的孩子(.wrapper)一个height: 100%。然后给它的孩子(.content)一个height: 100%所以它们的高度都是一样的。 给下一个孩子 (#half_of_content) 一个 height: 50% 自然会是 body 的 50% 的高度。

    但是,对于绝对定位,you don't need to specify parent heights

    【讨论】:

    • 这实际上看起来比 Oriols 解决方案更好,尽管我认为这看起来更难看。但在 Chrome 修复错误之前,我将使用最简单的方法。
    • 好吧,如果可以的话,我想避免在#wrapper 上设置 height:100%,因为它已经从 flexbox 接收到一个高度。但后来我不能在子元素上做 50% 的高度,因为......我不知道为什么......所以我们可以正式地说 增长的弹性项目没有收到它们的实际高度
    • Ugly?? 我在那个解决方案中看到了一个美妙的东西 :-) 50% div 在父 div 中漂亮、优雅、精确地扩展和收缩.
    • 澄清一下,因为我不确定你说的是哪个div#half_of_height 不是弹性项目。
    • 50% 表示占父母身高的一半。但在这种情况下,它不会。
    【解决方案3】:

    嵌套弹性盒有点麻烦。我通过添加带有display: flex; 的内部包装器对您的标记进行了一些修改,这似乎可以完成这项工作。这是fiddle(也使用类名而不是id)。

    <div class="content">
      <div class="wrapper-inner">
        2
        <div class="half">
          2.1
        </div>
      </div>
    </div>
    
    .wrapper-inner {
        position: absolute;
        display: flex;
        flex-direction: column;
        height: 100%;
        width: 100%;
    }
    

    【讨论】:

      【解决方案4】:

      修复:

      开启#content设置

      display: flex; 
      flex-flow: column nowrap; 
      justify-content: flex-end
      

      #half_of_content 上设置flex: 0 0 50%;

      警告:您需要添加一个extra div 作为#content 的子级。

      这是完整的例子:

      html,body {
          height: 100%;
          margin: 0;
      }
      
      #wrapper {
          display: flex;
        flex-flow: column;
          height: 100%;
      }
      
      #menu {
          height: 70px; 
          background-color: purple
      }
      
      #content {
          flex: 1;
          height: 100%;
          display:flex;
          flex-flow: column nowrap;
          justify-content: flex-end;
          background-color: green;
      }
      
      #half_of_content {
          flex: 0 0 50%;
          background-color: yellow;
      }
      
      #footer {
          height: 100px; 
          background-color: cyan
      }
      <body>
          <div id="wrapper">
              <div id="menu">
                  1
              </div>
              <div id="content">2
                  <div id="half_of_content">2.1</div>
              </div>
              <div id="footer" style="">
                  3
              </div>
          </div>
      </body>

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2018-11-25
        • 2014-09-11
        • 2015-12-08
        • 2020-01-20
        • 1970-01-01
        • 2020-06-14
        • 2018-10-22
        相关资源
        最近更新 更多