11.19 CSS 弹性布局的顺序和方向(Ordering/Orientation)

弹性容器的内容可以在任何方向以任何顺序放置

弹性容器的内容可以在任何方向以任何顺序放置。这种灵活性使得作者可以方便的实现以前所需要的复杂而容易出错的解决方案(如使用float和clear的一些hacks方法)。这个功能通过flex-direction, flex-wrap, 和 order 属性来实现。

和网格布局类似,order属性只是用来改变视觉顺序,不能用它来改变文档序,也不会影响语音序和无样式的访问顺序。

弹性流方向(Flex Flow Direction): 弹性方向(flex-direction)属性

flex-direction: row(初始值) | row-reverse | column | column-reverse

flex-direction属性通过设置弹性容器的主轴线(main axis)方向,来指定弹性项沿该方向在弹性容器中放置。

row
弹性容器的主轴(main axis)和当前书写模式(writing mode)的行内轴(inline axis)方向一致。main-start 和 main-end 方向分别等同于 inline-start 和 inline-end。
row-reverse
和row相同,除了main-start 和 main-end 的方向要交换下。
column
弹性容器的主轴(main axis)和当前书写模式的块轴(block axis)方向一致。main-start 和 main-end 方向分别等同于 block-start 和 block-end。
column-reverse
和column相同,除了main-start 和 main-end 的方向要交换下。

注意:reverse 值并不会反转box的排序,而只是改变文档流的放置方向。渲染顺序和语音序不受影响。

弹性包装:flex-wrap 属性

flex-wrap: nowrap(初始值) | wrap | wrap-reverse

flex-wrap 属性控制弹性容器是单行还是多行,以及cross-axis的方向,这将确定新行进栈的方向。

nowrap
弹性容器是单行。cross-start 方向等同于垂直轴线(cross axis)上,当前书写模式下的 inline-start 或 block-start 方向。cross-end 方向是 cross-start 的反方向。
wrap
弹性容器是单行。cross-start 方向等同于垂直轴线(cross axis)上,当前书写模式下的 inline-start 或 block-start 方向。cross-end 方向是 cross-start 的反方向。
wrap-reverse
和wrap一样,除了cross-start 和 cross-end 方向交换下。

弹性流:flex-flow 速写属性

flex-flow: <flex-direction> || <flex-wrap>

我们可以使用flex-flow属性来一次性定义上述的弹性方向(flex-direction)和包装(flex-wrap)两个属性,即该属性是前两者的速写方式,这两个属性合起来定义了弹性容器的主轴和垂直轴。

下面这个例子很好的演示了该属性的使用效果:

  • 上例中的第一个弹性项列表使用了默认属性也就是row且不拆行,弹性项的宽度在需要的时候会被压缩。
  • 第2个列表使用了column wrap,表示主轴方向是从上往下,而行拆分的方向是行内方向(向右)。
  • 而第3个列表使用了row-reverse wrap-reverse,表示主轴方向是行内相反方向(从右到左),新行向上拆分。

注意:flex-flow的方向是和书写模式相关的,比如日文是竖向书写的,那么弹性容器是从上往下放置内容,如下图所示:

English Japanese
flex-flow: row wrap;writing-mode: horizontal-tb;
flex-flow: row wrap;writing-mode: vertical-rl;

显示顺序:order属性

默认情况下,弹性项以源代码顺序来显示,order 属性用来改变这个顺序。

order属性适用于弹性项以及弹性容器中绝对定位的元素。order属性的取值是一个整数,用来指定弹性项目归属于哪个顺序组(ordinal group)。

弹性容器按调整后的文档序来放置其内容,从底到高。多个具有相同order值的项目归属于一个顺序组,将按照源代码序呈现。

下面的例子演示如何使用order来改变标签的显示顺序,当前激活的标签总是被显示在第一位:

排序和可访问性

order属性只影响视觉顺序,不影响非可视化媒体和无样式用户代理,这样既可以保证文档内容的可访问性(有一个稳定的逻辑顺序),也能给样式显示带来灵活性。

许多网页有类似的HTML代码,一个header和footer分别在文档顶部和底部,页面中间是内容区域和一个或两个附加列作为边栏。 一般情况下,页面源代码中的主体内容放在附加列前面比较理想。然而,这使得一些设计模式较难实现,比如圣杯布局(Holy Grail Layout,也就是经典三列布局)。 在过去这么多年里,该问题已经被使用多种方式所解决,但是弹性布局的order属性使得这个问题的解决变得极其自然和简单。

在上面的例子中文章(article)在中间(视觉顺序为第2位),左侧是菜单栏,右侧是推荐文章列表。不过在html标签中你可以看到标记代码,其中article的文档顺序是第一位。 通过order属性我们很容易实现了视觉和代码序的差异化处理。同时,这些列默认都是等高的,中间的内容将自动填充屏幕可用空间。 此外,读者还可以缩小预览窗口以观察小屏幕(移动设备)下该布局的响应式特性:行栈将切换为列栈,这是通过CSS样式代码中的media-query部分来实现。