关闭

Webkit Flex伸缩盒模型

标签: css3
521人阅读 评论(0) 收藏 举报
分类:


CSS3 display:flex和display:box有什么区别?

著作权归作者所有。
商业转载请联系作者获得授权,非商业转载请注明出处。
作者:一丝
链接:http://www.zhihu.com/question/22991944/answer/23302749
来源:知乎

前者是flex 2012年的语法,也将是以后标准的语法,大部分浏览器已经实现了无前缀版本。

后者是2009年的语法,已经过时,是需要加上对应前缀的。

所以兼容性的代码,大致如下

    display: -webkit-box; /* Chrome 4+, Safari 3.1, iOS Safari 3.2+ */
    display: -moz-box; /* Firefox 17- */
    display: -webkit-flex; /* Chrome 21+, Safari 6.1+, iOS Safari 7+, Opera 15/16 */
    display: -moz-flex; /* Firefox 18+ */
    display: -ms-flexbox; /* IE 10 */
    display: flex; /* Chrome 29+, Firefox 22+, IE 11+, Opera 12.1/17/18, Android 4.4+ */

一个元素被定义display:-webkit-flex;则此元素即为伸缩盒模型中的伸缩容器,其包含的子元素是伸缩项目。 flex是一个复合属性。Flexbox伸缩布局盒模型中的伸缩容器及伸缩特性定义。 由多个伸缩项目组成其具体的布局方式。 是为了呈现复杂的应用与页面而设计出来的。

display: -webkit-flex; 

-webkit-flex: none | [flex-grow flex-shrink || flex-basis] | initial | auto

none 在任何情况都不会发生伸缩
flex-grow 扩展比率
flex-shrink 收缩比率
flex-basis 伸缩基准值
initial 在有剩余空间的情况下不会有任何变化,但是在必要的情况下会被收缩
auto 会根据主轴自动伸缩以占用所有剩余空间,非常类似于普通流中的自动外边距

示例:

CSS

1 .flexBox{ display:-webkit-flex;-webkit-flex-flow: row;-webkit-flex-wrap: nowrap; width:600px; margin:50px auto; background-color:#9CF}
2 .flexBox div{ height:100px;}
3 .flexBox .item1{-webkit-flex:1;background:#ff9900;}
4 .flexBox .item2{-webkit-flex:1;background:#936;}
5 .flexBox .item3{-webkit-flex:1;background:#39C;}

HTML:

1 <div class="flexBox">
2  <div class="item1">1</div>
3  <div class="item2">2</div>
4  <div class="item3">3</div>
5  <div style=" width:300px; background-color:#96F">固定宽度300px</div>
6 </div>

结果:

总宽度,600px,给子元素4定义了width:300px,子元素1、2、3定义了flex伸缩属性,那么剩余空间就会按照1:1:1分割给这三个子元素

-webkit-flex-basis: 用来设置「flex-basis」长度并指定伸缩基准值,也就是根据可伸缩比率计算出剩余空间的分布之前,伸缩项目主轴长度的起始数值,若在「flex」缩写省略了此部件,则「flex-basis」的指定值是长度零。 若「flex-basis」的指定值是「auto」,则伸缩基准值的指定值是元素主轴长度属性的值。(这个值可能是关键字「auto」,代表元素的长度取决于其内容。)

有点绕,即是说对子元素设置了-webkit-flex-basis基准值,在计算剩余空间前,该项在基准值上进行伸缩,例如

<div class="flexBox">
 <div class="item1" style="-webkit-flex-basis:150px;">1</div>
 <div class="item2">2</div>
 <div class="item3">3</div>
 <div style=" width:300px; background-color:#96F">固定宽度300px</div>
</div>

CSS同上面的例子,仅仅修改了HTML的第一个子元素,为这个子元素添加了一个样式属性-webkit-flex-basis:150px;,设置第一个元素的基准值为150px,结果如下:

未设基准值以前,1、2、3 三个元素的长度都是200px,也就是容器总宽度600px减去固定宽度300px后剩余300xp再1:1:1进行伸缩的结果。

设置第一个子元素-webkit-flex-basis:150px;后,1、2、3三个元素的宽度分别为:200px、50px、50px。

个人理解在计算出剩余空间300px后,先算出每个元素的伸缩基准值(不写默认为0px),剩余空间减去每个元素的伸缩基准值后的空间再按比例进行分配,所以上面的结果是

300px-150px=150px,这150px按照1:1:1分配应该给1、2、3号元素各分50px,由于1号子元素的基准值是150px,所以1号元素的宽度为150+50=200px,2、3号元素为50+0=50px.

如果给元素设置了width属性,-webkit-flex-basis的值就是width值

-webkit-flex-direction :row(子元素优先排成一行)|row-reverse(反转)|column(子元素优先排成多行,每行排列一个)|column-reverse(反转)

具体实例地址:http://ued.ctrip.com/blog/wp-content/webkitcss/demo/flex-direction.html

-webkit-flex-grow :指定扩展比率,也就是剩余空间是正值的时候此伸缩项目相对于伸缩容器里其他伸缩项目能分配到空间比例。若省略了此部件,则它会被设为「1」,如果设置为0,则该元素将不会参与空间分配,必须加上auto参数(-webkit-flex:0 auto;),其宽度依据内容而定,如果不加auto参数,宽度将会是0px,导致内容不可见。

-webkit-flex-shrink :指定收缩比率,也就是剩余空间是负值的时候此伸缩项目相对于伸缩容器里其他伸缩项目能收缩的空间比例。若省略了此部件,则它会被设为「1」。在收缩的时候收缩比率会以伸缩基准值加权。

收缩示例:

CSS/HTML:

 1 .flexBox{ display:-webkit-flex;-webkit-flex-flow: row;-webkit-flex-wrap: nowrap; width:600px; margin:50px auto; background-color:#9CF}
 2 .flexBox div{ height:100px; width:150px}
 3 .flexBox .item1{background:#ff9900;}
 4 .flexBox .item2{background:#936;}
 5 .flexBox .item3{background:#39C;}
 6 
 7 <div class="flexBox">
 8  <div class="item1">1</div>
 9  <div class="item2">2</div>
10  <div class="item3">3</div>
11  <div style=" width:300px; background-color:#96F">固定宽度300px</div>
12 </div>

结果:

初始设定1、2、3号元素的宽度为150px,4号元素宽度为300px。而实际1、2、3、4号元素的宽度分别是120px、120px、120px、240px。这是伸缩盒缩的结果。

容器总宽度为600px,如果按照实际,4个子元素的总宽度应该为750px,所以容器应该差150px才能满足要求,而容器宽度不会自动增大,为了满足现实,就必须缩小每个子元素的宽度。

由于未设-webkit-flex-basis基准值,所以每一个子元素的基准值就是它的宽度,所以1、2、3、4的基准值分别为150px,150px,150px和300px;。

在收缩的时候收缩比率会以伸缩基准值加权,初始收缩比率是1:1:1:1,由于4号元素的基准值是300px,所以收缩率要加权,结果300/150=2,所以它们的收缩比率分别为1:1:1:2。

计算收缩宽度为(差值*比率)1:150*1/5=30px、2:150*1/5=30px、3:150*1/5=30px、4:150*2/5=60px;

四个元素的宽度分别为150-30=120、150-30=120、150-30=120、300-60=240。

-webkit-flex-wrap :控制伸缩容器是单行还是多行,也决定了侧轴方向 ― 新的一行的排列方向

nowrap 伸缩容器为单行。侧轴起点方向等同于当前书写模式的起点或前/头在侧轴的那一边,而侧轴终点方向是侧轴起点的相反方向
wrap 伸缩容器可以创建多行,新增的伸缩行根据侧轴的方向添加
wrap-reverse 除了侧轴起点与侧轴终点方向交换以外同「wrap」

示例地址:http://ued.ctrip.com/blog/wp-content/webkitcss/demo/flex-wrap.html

在属性设置为wrap时,容器会自动判断子元素的宽度决定是否换行,可以给子元素设置min-width或width属性配合使用。

接着上一个例子收缩来说,如果设定了子元素宽度而又不愿意收缩,可以设置-webkit-flex-wrap:wrap

结果为:

1、2、3、4号元素宽度就是实际的值150、150、150、300px。一行排不下时自动换行,由于未设置-webkit-flex属性,所以不会自动拉伸。

-webkit-align-content :基于Flex布局,用来指定多行伸缩容器的对齐。在使用 wrap 关键字的多行伸缩容器上,你也可以指定行与行之间空白的分配方法。仅在伸缩容器在侧轴占有固定的空间时(例:伸缩子元素横排的时候伸缩容器有固定高)才有作用

flex-start 将伸缩行捆在主轴起始端,将空白留到结尾端
flex-end 将伸缩行捆在主轴结尾端,将空白留到起始端
center 将伸缩行捆在主轴的中间位置,将空白平均分到两端
stretch 将所有项目伸长,让项目占据了整个侧轴的长度
space-around 沿着侧轴将空白均分到伸缩行之间与外侧(行之间空白的二分之一)
space-between 跟 space-around 的效果很相像,但是分配到开始、结尾两端的空间比较少

基于上一个例子,设置容器属性<div class="flexBox" style="-webkit-flex-wrap:wrap; height:300px;-webkit-align-content:space-between ">,给一个固定的高度。

flex-start:                             flex-end:                            center:                                space-around:                      space-between:

flex-startcenter


0
0

查看评论
* 以上用户言论只代表其个人观点,不代表CSDN网站的观点或立场
    个人资料
    • 访问:39656次
    • 积分:580
    • 等级:
    • 排名:千里之外
    • 原创:5篇
    • 转载:91篇
    • 译文:0篇
    • 评论:0条
    文章分类