CSS 零基础教程

CSS Grid 布局入门

CSS Grid 是一个强大的布局系统,它为网页结构的控制提供了前所未有的能力。它允许你轻松创建复杂的、响应式的布局,在某些场景下,它的能力超越了像浮动 (floats) 甚至 Flexbox 这样的旧布局方法。

本章节将向你介绍 CSS Grid,解释其核心概念,并演示为什么它是现代 Web 开发的必备工具。我们将探讨 Grid 和 Flexbox 之间的根本区别,重点介绍 Grid 擅长的情况。

1. 理解 CSS Grid

CSS Grid Layout,通常简称为 CSS Grid(网格布局),是一个用于 Web 的二维布局系统。这意味着它擅长同时控制行和列,这与主要是一维(要么是行,要么是列)的 Flexbox 不同。

Grid 允许你将网页划分为多个区域,定义这些区域的大小和位置,然后将内容放置在其中。

1.1 核心概念

  • Grid Container (网格容器): 声明了 display: grid 或 display: inline-grid 的父元素。这为其所有直接子元素创建了网格上下文。
  • Grid Items (网格项): 网格容器的直接子元素。这些是将被定位在网格内的元素。
  • Grid Lines (网格线): 定义网格结构的水平和垂直线。它们带有编号,从 1 开始。
  • Grid Tracks (网格轨道): 两条相邻网格线之间的空间。这些可以是行(水平轨道)或列(垂直轨道)。
  • Grid Cell (网格单元格): 网格布局中的最小单位,由行轨道和列轨道的交叉点形成。
  • Grid Area (网格区域): 跨越一个或多个网格单元格的矩形区域。网格项被放置在网格区域内。
  • Gaps / Gutters (间距/沟槽): 网格轨道(行和列)之间的空间。

2. 为什么要使用 CSS Grid?

与传统布局方法甚至 Flexbox 相比,CSS Grid 在某些情况下提供了几个优势:

  • 二维布局: Grid 专为二维布局设计,非常适合创建具有行和列的复杂页面结构。Flexbox 虽然强大,但主要是为一维布局(行或列)设计的。
  • 显式布局控制: Grid 提供了对元素放置和尺寸的显式控制。你可以定义每个网格项的确切大小和位置,从而精确控制布局。
  • 响应式设计: Grid使得创建适应不同屏幕尺寸的响应式布局变得容易。你可以使用媒体查询 (Media Queries) 根据视口大小更改网格结构和项目位置。
  • 语义化 HTML: Grid 允许你将布局与内容分离,从而产生更清晰、更语义化的 HTML。你可以在不修改 HTML 结构的情况下更改布局。
  • 简化代码: 对于复杂布局,与其他布局方法相比,Grid 通常能减少代码量。其强大的功能允许你用更少的 CSS 代码实现复杂的布局。

3. Grid vs. Flexbox: 选择合适的工具

虽然 CSS Grid 和 Flexbox 都是强大的布局工具,但它们的设计目的不同。了解它们的优缺点将帮助你为工作选择正确的工具。

特性CSS GridFlexbox
维度二维 (行和列)一维 (行或列)
主要用例页面布局,复杂的 UI 组件组件布局,在一个方向上对齐项目
控制方式对行和列的大小及放置进行显式控制基于内容的尺寸和空间的灵活分配
最适合创建整体页面结构在容器内对齐项目

3.1 何时使用 Grid:

  • 复杂的页面布局: 当你需要创建一个包含多行多列的布局时,例如一个包含页头、侧边栏、内容区域和页脚的网站。
  • 精确控制: 当你需要精确控制布局中元素的大小和位置时。
  • 二维对齐: 当你需要同时在行和列中对齐项目时。

3.2 何时使用 Flexbox:

  • 组件布局: 当你需要在一个组件内布局项目时,例如导航栏或项目列表。
  • 单向对齐: 当你需要在单个方向(水平或垂直)上对齐项目时。
  • 动态内容: 当内容的大小未知或可变,并且你希望布局自动适应时。

3.3 场景示例:

想象你正在为一个摄影作品集建立一个网站。

  • Grid: 你会使用 Grid 来创建整体页面结构:顶部的页头,中间的图片画廊,底部的页脚。画廊本身可能就是一个网格,将图片按行和列排列。
  • Flexbox: 在页头内部,你可能会使用 Flexbox 将 Logo 对齐到左侧,将导航链接对齐到右侧。每个导航链接也可以使用 Flexbox 来垂直居中链接内的文本。

4. 创建一个基础 Grid 布局

让我们创建一个简单的例子来说明 CSS Grid 的基本概念。我们将创建一个包含三列两行的网格。

HTML:

<div class="container">
  <div class="item item-1">Item 1</div>
  <div class="item item-2">Item 2</div>
  <div class="item item-3">Item 3</div>
  <div class="item item-4">Item 4</div>
  <div class="item item-5">Item 5</div>
  <div class="item item-6">Item 6</div>
</div>

CSS:

.container {
  display: grid; /* 将容器声明为网格 */
  grid-template-columns: 1fr 1fr 1fr; /* 定义三列等宽的列 */
  grid-template-rows: 150px 150px; /* 定义两行,每行 150px 高 */
  grid-gap: 10px; /* 在行和列之间添加 10px 的间距 */
}
.item {
  background-color: #eee;
  padding: 20px;
  font-size: 20px;
  text-align: center;
}

代码解释:

  • display: grid;: 将 container div 变成一个网格容器。
  • grid-template-columns: 1fr 1fr 1fr;: 定义了三列。fr 单位代表可用空间的一部分 (fraction)。在这种情况下,每一列占据容器宽度的三分之一。
  • grid-template-rows: 150px 150px;: 定义了两行,每行 150 像素高。
  • grid-gap: 10px;: 在网格项之间添加 10 像素的间距。

在这个例子中,六个 item div 会自动放入网格单元格中,从左到右、从上到下填充网格。

5. 在 Grid 中放置项目

虽然网格项的自动放置很有用,但 Grid 也允许你将项目显式地放置在特定的网格单元格中。你可以使用 grid-column-startgrid-column-endgrid-row-startgrid-row-end 属性来实现。

让我们修改前面的例子,将 Item 1 放在第一行,并让它跨越所有三列。

CSS:

.container {
  display: grid;
  grid-template-columns: 1fr 1fr 1fr;
  grid-template-rows: 150px 150px;
  grid-gap: 10px;
}
.item {
  background-color: #eee;
  padding: 20px;
  font-size: 20px;
  text-align: center;
}
.item-1 {
  grid-column-start: 1; /* 从第 1 条列网格线开始 */
  grid-column-end: 4; /* 到第 4 条列网格线结束 (跨越三列) */
}

代码解释:

  • grid-column-start: 1;: 告诉 Item 1 从第一条列网格线开始。
  • grid-column-end: 4;: 告诉 Item 1 在第四条列网格线结束。因为我们有三列,这意味着 Item 1 将跨越所有三列。

你也可以使用简写属性 grid-columngrid-row 来达到同样的效果:

.item-1 {
  grid-column: 1 / 4; /* 等同于 grid-column-start: 1; grid-column-end: 4; */
}

语法 1 / 4 意思是“从列网格线 1 开始,到列网格线 4 结束”。

6. 假设场景

想象你正在设计一个电商产品页面的布局。你希望在左侧突出显示产品图片,在右侧显示产品详情(名称、描述、价格)。在产品详情下方,你希望显示客户评论。

使用 CSS Grid,你可以轻松创建此布局:

  1. Grid Container: 主产品容器将是网格容器。
  2. Grid Columns: 你会定义两列:一列用于图片,一列用于产品详情和评论。
  3. Grid Rows: 你会为产品详情和客户评论定义行。
  4. Placement (放置): 你将产品图片放在第一列,跨越两行。将产品详情放在第二列的第一行,将客户评论放在第二列的第二行。

这个场景演示了 Grid 如何用于为产品页面创建结构化且视觉上吸引人的布局。