第13天:CSS(二)| Grid 布局完全指南

今天系统复习了 Grid 布局的核心概念,包括二维布局模型、轨道尺寸与 fr 单位、网格线定位、对齐方式、响应式网格以及 auto-fillauto-fit 的区别。以下是当天的问答整理与知识总结。


一、Grid 基础概念与心智模型

1. Grid 与 Flexbox 的区别

| 特性 | Grid | Flexbox |
| 维度 | 二维(同时控制行和列) | 一维(主轴方向) |
| 布局思路 | 先定义网格结构,再放置项目 | 根据项目大小沿主轴排列 |

试用场景 整体页面布局、复杂网格、图片墙 导航栏、列表项、组件内对齐

2. 核心术语

  • **容器:**设置 display: grid 的父元素。
  • **项目:**容器的直接子元素。
  • **行:**水平方向的轨道。
  • **列:**垂直方向的轨道。
  • **单元格:**行和列交叉形成的最小单位。
  • **网格线:**分隔轨道的线,n 条轨道对应 n+1 条网格线。

二、轨道尺寸与 fr 单位

1. fr 单位

fr 表示剩余空间的一份比例,用于分配网格容器中未被固定宽度(或百分比)占用的空间。

css 复制代码
.grid {
  display: grid;
  grid-template-columns: 200px 1fr 2fr;
}
  • 第一列固定 200px。
  • 剩余空间分为 3 份,第二列占 1 份,第三列占 2 份。

2. 与百分比、auto 的区别

| 单位 | 计算依据 | 特点 |
| fr | 剩余空间(扣除固定、百分比、内容后) | 灵活分配,不产生溢出 |
| 百分比 | 容器总宽度(包含固定宽度和间隙) | 可能因间隙导致溢出 |

auto 内容宽度 由内容撑开,不参与剩余空间分配

3. minmax() 函数

css 复制代码
grid-template-columns: minmax(100px, 1fr) 2fr;

第一列最小 100px,最大占 1 份剩余空间;第二列固定占 2 份。常用于响应式,防止内容被压缩。


三、网格线定位、span 与网格命名

1. 基于网格线编号定位

网格线从 1 开始编号。grid-column 和 grid-row 可指定起始/结束线。

css 复制代码
.item {
  grid-column: 2 / 4;   /* 从第2条列线到第4条列线 */
  grid-row: 1 / 3;      /* 从第1条行线到第3条行线 */
}

使用 span 关键字跨越指定数量:

css 复制代码
.item {
  grid-column: 2 / span 3;  /* 从第2条线开始,跨越3列 */
}

2. grid-area 简写

顺序:row-start / column-start / row-end / column-end

css 复制代码
.item {
  grid-area: 2 / 3 / 4 / 5;
}
/* 等价于 */
grid-row-start: 2;
grid-column-start: 3;
grid-row-end: 4;
grid-column-end: 5;

3. 网格线命名

在定义轨道时给线起名:

css 复制代码
.grid {
  display: grid;
  grid-template-columns: [main-start] 1fr [main-end] 1fr;
}
.item {
  grid-column: main-start / main-end;
}

也可以使用 repeat 配合命名,如 repeat(3, [col] 1fr)。


四、对齐与间距控制

1. 项目对齐(*-items / *-self)

| 属性 | 作用 | 取值示例 |
| justify-items | 所有项目在行轴(水平)上的对齐 | start, end, center, stretch |
| align-items | 所有项目在列轴(垂直)上的对齐 | start, end, center, stretch |
| justify-self | 单个项目在行轴上的对齐 | 覆盖 justify-items |

align-self 单个项目在列轴上的对齐 覆盖 align-items

2. 网格整体对齐(*-content)

当网格总尺寸小于容器时,控制整个网格区域的对齐。

  • justify-content:水平方向
  • align-content:垂直方向

取值:start, end, center, space-between, space-around, space-evenly

3. 与 Flexbox 对齐的对比

| 概念 | Grid | Flexbox |
| 单行项目对齐 | justify-items / align-items | justify-content / align-items(注意:Flex 中 justify-content 控制主轴,align-items 控制交叉轴) |
| 整体对齐 | justify-content / align-content | 只有单行时 align-content 无效(需 flex-wrap: wrap 且多行) |

单个项目覆盖 justify-self / align-self align-self(无 justify-self,可用 margin: auto 替代)

4. 间距 gap

css 复制代码
.grid {
  gap: 16px;        /* 行和列间距均为16px */
  gap: 16px 24px;   /* 行间距16px,列间距24px */
}
  • gap 只控制项目之间的间距,不会导致父容器塌陷,比 margin 更简洁。
  • 边缘间距需要用父容器的 padding 实现。

五、响应式网格与自动布局

1. 自动填充 repeat(auto-fill, minmax(200px, 1fr))

css 复制代码
.grid {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(200px, 1fr));
  gap: 16px;
}
  • 浏览器根据容器宽度自动计算能容纳多少列,每列最小 200px,最大占 1fr。
  • 当宽度不足时,列数减少,每列自动拉伸。

2. auto-fill vs auto-fit

| 关键字 | 行为 | 视觉效果 |
| auto-fill | 尽可能多地填充轨道,即使没有项目也会保留空轨道 | 右侧可能留白 |

auto-fit 填充轨道后,拉伸已有项目填满容器 无留白,项目更宽

**示例:**容器宽度 600px,minmax(200px, 1fr),最多能放 3 列。

只有 2 个项目时:

  • auto-fill:仍然保留 3 个轨道位置,第 3 个轨道空白。
  • auto-fit:只有 2 个轨道,每个占 300px。

3. 媒体查询适配

css 复制代码
/* 移动端:希望项目尽量宽,不留白 */
.grid {
  grid-template-columns: repeat(auto-fit, minmax(200px, 1fr));
}

/* 桌面端:希望保留空白或固定列数 */
@media (min-width: 1024px) {
  .grid {
    grid-template-columns: repeat(4, 1fr);
  }
}

4. display: grid 与 inline-grid

  • display: grid:块级网格容器,独占一行。
  • display: inline-grid:行内网格容器,宽度由内容或 grid-template-columns 决定。

今日知识点总结

| 概念 | 要点 |
| 二维布局 | 先定义网格结构,再放置项目;适合整体页面、复杂网格 |
| fr 单位 | 剩余空间的一份比例,与百分比、auto 的区别 |
| minmax( ) | 定义轨道的最小/最大尺寸,响应式核心 |
| 网格线定位 | 基于编号或命名,使用 span 跨越;grid-area 简写 |
| 对齐方式 | *-items(单元格内对齐)、*-content(网格整体对齐)、*-self(单个项目覆盖) |
| 间距 gap | 仅控制项目间间距,边缘用 padding |
| 响应式 | repeat(auto-fill/auto-fit, minmax(min, max)) 实现弹性网格 |

auto-fill vs auto-fit auto-fill 保留空轨道,auto-fit 拉伸项目填满

常见追问

1. 如何实现一个不等高卡片网格?

Grid 默认每行高度由该行最高卡片决定,无需特殊处理。若想实现瀑布流(各卡片高度独立),原生 Grid 不支持,可用 column-count 或 Masonry 库。

2. grid-template-areas 的作用?

通过命名区域直观定义布局,适合固定模板的页面(如 header、main、sidebar、footer)。

css 复制代码
.container {
  display: grid;
  grid-template-areas:
    "header header"
    "sidebar main"
    "footer footer";
}


.header { grid-area: header; }
.sidebar { grid-area: sidebar; }
.main { grid-area: main; }
.footer { grid-area: footer; }

3. 如何让某个子项跨越所有列?

grid-column: 1 / -1;(-1 表示最后一条网格线)。

4. minmax(100px, max-content) 与 minmax(100px, auto) 的区别?

max-content 取内容的最大宽度(不换行),auto 受 min-width / max-width 影响,通常更常用 auto。

相关推荐
黑金IT2 小时前
AI带‘脑’摒弃前端硬编码实现浏览器自动化系统
前端·人工智能·自动化
牧杉-惊蛰2 小时前
修改表格选中时的背景色与鼠标滑过时的背景色
前端·javascript·css·vue.js·elementui·html
彧翎Pro2 小时前
前端状态管理进化史:从Redux到Zustand的范式转变
前端·javascript
bjzhang752 小时前
使用 HTML + JavaScript 实现表格滚动效果
前端·javascript·html·表格滚动效果
ZStack开发者社区2 小时前
ZSTACK · 答客问 | 高频问题合集
前端·网络·php
林恒smileZAZ7 小时前
Vue<前端页面版本检测>
前端·javascript·vue.js
码事漫谈10 小时前
当AI开始“思考”:我们是否真的准备好了?
前端·后端
许杰小刀11 小时前
ctfshow-web文件包含(web78-web86)
android·前端·android studio
我是Superman丶11 小时前
Element UI 表格某行突出悬浮效果
前端·javascript·vue.js