本文是阅读《HTML5 与 CSS3 设计模式》时摘录的一篇读书笔记,内容主要是使用 table 标签设计列布局,这里讲的布局适用于表格式数据(tabular data),不建议用于页面布局,使用表格设计页面布局会降低内容的可访问性。在讲布局之前,先说两条 table 元素的特殊特性:

一是,表格单元格 td / th 的 height 属性只能指定单元格的最小高度,当内容过长超过容器容量时,容器高度就会自动增大。解决这个问题有两种方法:为单元格内的内容设置一层容器,比如 div,并为容器设置 height: 固定高度值;overflow: hidden 样式;为单元格内容设置 white-space: nowrap,杜绝自动换行行为,继而在水平方向隐藏溢出。

二是,单元格上设置 visibility: hidden 只会隐藏单元格内容,单元格的边框样式仍然存在。

使用表格布局主要有四种方案,而这四种方案由 table-layoutwidth 两个 CSS 样式决定。table-layout 支持两个值:autofixedauto 自动布局的表格会根据内容宽度、单元格宽度设置列宽,而 fixed 固定布局会忽略内容宽度,仅仅根据第一行单元格的宽度来设置列宽。width 支持三种值:auto、固定值和百分比。四种布局如下():

  • 表格 table-layout: auto 和单元格 width: auto,收缩适应型,表格会自动缩小到所有列宽之和,且不会超过容器宽度
  • 表格 table-layout: auto 和单元格 width: 固定宽度,设定尺寸型,表格会根据宽度值按比例分配列宽
  • 表格 table-layout: auto 和单元格 width: 100%,拉伸型,表格宽度会拉伸为父容器的宽度,并按比例分配列宽
  • 表格 table-layout: fixed 和单元格 width: 固定宽度,固定尺寸型,表格会忽略内容高度而设置列宽

除固定尺寸型表格外,其他类型的表格列宽都是由浏览器决定的,这里涉及到一个概念:最小内容宽度,指单元格中最宽单词的宽度,中文是一个字,英文是一个以空白符分割的词块,比如 ‘a alkdjsfka b’ 中的 ‘a’、’alkdjsfka’ 和 ‘b’ 都是词块,其中 ‘alkdjsfka’ 就是这个单元格的最宽词块。浏览器会按照如下规则设置列宽:

  1. 列默认设置为自动宽度,也就是根据宽度类型(width 的值类型)、最大宽度值、最小内容宽度和最大内容宽度自动设置列宽
  2. 如果 width 为固定值,比如 ‘100px’,那么这个固定宽度就会成为列宽(取当前列的最大固定宽度),替代当前列的默认值
  3. 如果 width 为百分比,比如 ‘10%’,那么这个百分比宽度就会成为列宽(去当前列的最大百分比),替代当前列的固定值和默认值
  4. 如果列宽小于最小内容宽度了,那么使用最小内容宽度成为列宽,替代当前列的百分比、固定值和默认值
  5. 如果列宽大于最大内容宽度了,那么使用最大内容宽度成为列宽,替代当前列的百分比、固定值和默认值

通过 width 设置的列宽并不会完全生效,当表格容器宽度过大或过小时,浏览器会按比例设置列宽。

收缩适应型表格

table {
width: auto;
table-layout: auto;
}
td {
width: auto;
}

表格中的单元格会自动收缩到最小宽度,但如果内容很长,又会扩展到容器的最大宽度,一旦出现这种情况,浏览器会按照内容比例配置列宽。

设定尺寸型表格

table {
width: auto;
table-layout: auto;
}
td {
width: <固定值> | <百分比>;
}

只有当同一行单元格的总宽度小于等于容器宽度,设置的固定值才会生效,否则浏览器会按宽度比例设定列宽,无论设置什么样的宽度值,列宽都不会小于最小内容宽度。

拉伸尺寸型表格

table {
width: auto;
table-layout: auto;
}
td {
width: 100%;
}

在拉伸尺寸型表格中,百分比宽度具有最高优先级,如果空间不足够,则会压缩固定宽度和自动宽度列到最小内容宽度。

固定尺寸型表格

table {
width: <固定值> | <百分比>;
table-layout: fixed;
}
td {
width: <固定值>;
}

在固定尺寸型表格中,固定值具有最高优先级,然后是百分比宽度和自动宽度,也就是说,如果空间不够,使用自动宽度和百分比宽度的列都会被折叠。

参考资料