HTML5 / CSS对齐列表项,取决于其他列的相互高度 [英] HTML5/CSS align list-items depending on other columns mutual height

查看:79
本文介绍了HTML5 / CSS对齐列表项,取决于其他列的相互高度的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有以下用例:





您可以看到三个相同的框:
每个框开始于一个大矩形框,具有图片和变量内容,因此具有可变的高度。
其余的包括一个列表,这是垂直对齐的底部,所以他们应该得到相同的高度。



我的目标是同步高度的, li>在每个框中。所以你不应该重要你输入多少文本, li>标签,设计应该自动处理单词拆分并将内容对齐为一行。



换句话说,像Abhitalks所说,



现在,我使用了display flex来将列表垂直对齐到元素的底部。
您可以在这里找到我使用的解决方案:
垂直对齐的浮动div



但现在我遇到了问题,如果列表没有相同的内容(每个listitem多于两行,整个事情都会转移到顶部。



但是,是不是有可能用flexbox模拟一个行行为,但实际上有一个列结构?





希望你能理解我的问题



提前感谢!



更新:



这里是小提琴:
http://jsfiddle.net/a1yr4u84/3/



您可以看到,我在li的内容中做了< br />,以使内容适合。

 < li> one< br />两个< / li> 
< li> one< br /两个< br />三个< / li>
< li>一个< br />< br />< / li>

但是,我无法控制li中有多少文字。我不想让用户使用< br /> s但是让设计处理内容,所以我希望列里面的列表现得像一行

解决方案


...三个相同的框:第一个大矩形部分有
变量内容,因此变量高度。其余部分由一个
列表,即垂直对齐的底部,以便他们应该得到
相同的高度。


这里需要嵌套 flex 。给定此标记:

 < div class =wrap> 
< div class =col left>
< img src =.../>
< div class =content>
< p> ...< / p>
< / div>
< / div>
< div class =col middle>
< img src =/>
< ul class =content>
< li> ...< / li>
< li> ...< / li>
< / ul>
< / div>
< div class =col right>
< img src =.../>
< ul class =content>
< li> ...< / li>
< / ul>
< / div>
< / div>

首先 flex 列,并给出 flex-basis 的 33%(大约)到列以允许变量内容在第一列空出。:

  .wrap {display:flex; } 
.wrap .col {flex:1 0 33%; }

接下来, flex 列中的图像和内容列表。此时 flex-basis 不是必需的:

  .wrap .col {flex:1 0 33%;显示:flex; flex-direction:column; } 
.col img,.col .content {flex:0 0 auto; }

为了保持列表与底部垂直对齐,只需提供 margin-top:auto 到列表内容:

  .col .content {margin-top :auto; } 

这是一个完整的例子..



小提琴: http://jsfiddle.net/abhitalks/a1yr4u84/1/ : : : data-lang =jsdata-hide =true>

  * {box-sizing:border-box; } .wrap {width:80%; margin:16px auto; padding:12px; border:1px solid gray; display:flex;}。wrap .col {flex:1 0 33%;显示:flex; flex-direction:column;}。col img,.col .content {flex:0 0 auto; } .col img {width:128px;显示:block; margin:2px auto; } .col .content {margin:auto 12px 0px 12px; }  

 < div class =wrap> < div class =col left> < img src =// lorempixel.com/128/128/> < div class =content> < p> Lorem ipsum dolor sit amet,consectetur adipisicing elit。 Ab,阻碍。 Lorem ipsum dolor sit amet,consectetur adipisicing elit。 < / p> < / div> < / div> < div class =col middle> < img src =// lorempixel.com/128/128/> < ul class =content> < li>一个< / li> < li>一个< / li> < li>一个< / li> < li>一个< / li> < / ul> < / div> < div class =col right> < img src =// lorempixel.com/128/128/> < ul class =content> < li>一个< / li> < li>一个< / li> < / ul> < / div>< / div>  






编辑:



(根据op的评论)



如果您希望列表项与其他内容列中的对等关系根据相互的高度进行对齐,那么您不能使用CSS执行此操作。我看到你已经用 jQuery 标记了问题,所以我提出了一个使用jQuery的快速解决方案。



计算列表项的 height ,并将该高度应用于其他列中的所有相应项:



小提琴2: http://jsfiddle.net/abhitalks/a1yr4u84/4/



snippetdata-lang =jsdata-hide =true>

  var $ lists = $('ul.content'); for(i = 0; i <10; i ++){var highest = 0; $ lists.each(function(idx,elem){var h = $(elem).children()。eq(i).outerHeight(); if(h> highest)highest = h; $ lists.each(function(idx,elem){$(elem).children()。eq(i).outerHeight(highest);}); }  

  * {box-sizing:border-box; } .wrap {width:80%; margin:16px auto; padding:12px; border:1px solid gray; display:flex;}。wrap .col {flex:1 0 33%;显示:flex; flex-direction:column;}。col img,.col .content {flex:0 0 auto; } .col img {width:128px;显示:block; margin:2px auto; } .col .content {margin:0px 12px 0px 12px; }  

 < script src =https:// ajax .googleapis.com / ajax / libs / jquery / 2.1.1 / jquery.min.js>< / script>< div class =wrap> < div class =col left> < img src =// lorempixel.com/128/128/> < ul class =content> < li> one< br />两个< / li> < li> one< br />两个< br />三个< / li> < li>一个< / li> < li>一个< / li> < / ul> < / div> < div class =col middle> < img src =// lorempixel.com/128/128/> < ul class =content> < li>一个< / li> < li>一个< / li> < li>一个< / li> < li>一个< / li> < / ul> < / div> < div class =col right> < img src =// lorempixel.com/128/128/> < ul class =content> < li> one< br />两个< / li> < li>一个< / li> < / ul> < / div>< / div>  



注意:我使用了任意数量的 10 循环列表项。在生产代码中,您必须计算最大列表中的列表项的数量。


I got the following use case:

You can see three identical boxes: Each box beginns with a big rectangle box, that has a picture and variable content and thus has variable height. the rest consists of a list, that is vertical aligned bottom, so that they should get the same height.

My goal is to "synchronize" the height of the < li >'s in each of these boxes. So it should not be important how many text you enter in such a < li > tag, the design should automatically handle the word-break and align the content like it was a row.

In other words, like Abhitalks stated, I want to align list-items to their peers in other content columns depending on the mutual heights.

Now, I used display flex in order to vertical align the list to bottom of the element. You can find my used solution here: Vertical alignment of floating divs

But now I got the problem, that if the list has no identical content (e.x. more than two rows per listitem, the whole thing shifts to the top.

However, is it somehow possible to simulate a row behavior with flexbox, but actually having a column structure?

I need a column structure, so I can easily get a responsive layout.

hope you understand my problem

thanks in advance!

UPDATE:

Here is the fiddle: http://jsfiddle.net/a1yr4u84/3/

You can see, that I made < br / >'s inside the li's content, in order to make the content fit.

<li>one <br /> two</li>
<li>one <br /> two <br /> three</li>
<li>one<br /><br /></li>

However, I can't control how many text there is going to be in the li's. And I don't want the user to hack with < br / >s but let the design handle the content, so I want the list inside the columns to behave like a row

解决方案

...three identical boxes: first big rectangle part has variable content and thus variable height. the rest consists of a list, that is vertical aligned bottom, so that they should get the same height.

You need nested flex here. Given this markup:

<div class="wrap">
  <div class="col left">
    <img src="..." />
    <div class="content">
        <p>...</p>
    </div>
  </div>
  <div class="col middle">
      <img src="" />
    <ul class="content">
        <li>...</li>
        <li>...</li>
    </ul>
  </div>
  <div class="col right">
      <img src="..." />
    <ul class="content">
        <li>...</li>
    </ul>
  </div>
</div>

First flex the wrapper which will layout the columns in a row, and give a flex-basis of 33% (approx) to the columns to allow for variable content in first columns to space out.:

.wrap { display: flex; }
.wrap .col { flex: 1 0 33%; }

Next, flex the columns to layout the image and content list in columns. This time flex-basis is not required:

.wrap .col { flex: 1 0 33%; display: flex; flex-direction: column; }
.col img, .col .content { flex: 0 0 auto; }

In order to keep the lists vertically aligned to the bottom, just provide a margin-top:auto to the list content:

.col .content { margin-top: auto; }

Here is a complete example..

Fiddle: http://jsfiddle.net/abhitalks/a1yr4u84/1/

Snippet:

* { box-sizing: border-box; }
.wrap {
  width: 80%; margin: 16px auto; padding: 12px; border: 1px solid grey;
  display: flex;
}
.wrap .col {
    flex: 1 0 33%; display: flex; flex-direction: column;
}
.col img, .col .content { flex: 0 0 auto; }
.col img { width: 128px; display: block; margin: 2px auto; }
.col .content { margin: auto 12px 0px 12px; }

<div class="wrap">
  <div class="col left">
    <img src="//lorempixel.com/128/128" />
    <div class="content">
        <p>Lorem ipsum dolor sit amet, consectetur adipisicing elit. Ab, impedit. Lorem ipsum dolor sit amet, consectetur adipisicing elit.
        </p>
    </div>
  </div>
  <div class="col middle">
      <img src="//lorempixel.com/128/128" />
    <ul class="content">
        <li>one</li>
        <li>one</li>
        <li>one</li>
        <li>one</li>
    </ul>
  </div>
  <div class="col right">
      <img src="//lorempixel.com/128/128" />
    <ul class="content">
        <li>one</li>
        <li>one</li>
    </ul>
  </div>
</div>


Edit:

(based on op's comment)

If you want the list-items to align to their peers in other content columns depending on the mutual heights, then you cannot do this with CSS. I see that you have tagged the question with jQuery, so I am proposing a quick-and-dirty solution using jQuery.

Calculate the height of the list items, and apply that height to all the corresponding items in other columns:

Fiddle 2: http://jsfiddle.net/abhitalks/a1yr4u84/4/

Snippet 2:

var $lists = $('ul.content');

for (i=0; i < 10; i++) {
    var highest = 0;
    $lists.each(function(idx, elem) {
        var h = $(elem).children().eq(i).outerHeight();
        if (h > highest) highest = h;
    });
    $lists.each(function(idx, elem) {
        $(elem).children().eq(i).outerHeight(highest);
    });    
}

* { box-sizing: border-box; }
.wrap {
  width: 80%; margin: 16px auto; padding: 12px; border: 1px solid grey;
  display: flex;
}
.wrap .col {
    flex: 1 0 33%; display: flex; flex-direction: column;
}
.col img, .col .content { flex: 0 0 auto; }
.col img { width: 128px; display: block; margin: 2px auto; }
.col .content { margin: 0px 12px 0px 12px; }

<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div class="wrap">
  <div class="col left">
    <img src="//lorempixel.com/128/128" />
    <ul class="content">
        <li>one <br /> two</li>
        <li>one <br /> two <br /> three</li>
        <li>one</li>
        <li>one</li>
    </ul>
  </div>
  <div class="col middle">
      <img src="//lorempixel.com/128/128" />
    <ul class="content">
        <li>one</li>
        <li>one</li>
        <li>one</li>
        <li>one</li>
    </ul>
  </div>
  <div class="col right">
      <img src="//lorempixel.com/128/128" />
    <ul class="content">
        <li>one <br /> two</li>
        <li>one</li>
    </ul>
  </div>
</div>

Note: I have used an arbitrary number of 10 to loop thru the list-items. In production code, you must calculate the number of the list items in the largest list.

这篇关于HTML5 / CSS对齐列表项,取决于其他列的相互高度的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆