跳到主要内容

核心理念

理解 Tailwind CSS 的核心理念是高效使用它的关键。本章将深入讲解功能类优先的设计思想和 Tailwind 的工作方式。

功能类优先

Tailwind CSS 的核心思想是"功能类优先"(Utility-First)。这意味着你应该使用小型的、单一目的的工具类来构建界面,而不是编写自定义 CSS。

传统方式 vs Tailwind 方式

传统方式: 先定义 CSS 类,然后在 HTML 中使用

<style>
.notification {
background-color: white;
border-radius: 8px;
padding: 16px;
box-shadow: 0 4px 6px rgba(0, 0, 0, 0.1);
display: flex;
align-items: center;
gap: 16px;
max-width: 400px;
margin: 0 auto;
}
.notification-icon {
width: 48px;
height: 48px;
flex-shrink: 0;
}
.notification-title {
font-size: 18px;
font-weight: 600;
color: #1f2937;
}
.notification-text {
color: #6b7280;
margin-top: 4px;
}
</style>

<div class="notification">
<img class="notification-icon" src="icon.svg" alt="">
<div>
<div class="notification-title">通知标题</div>
<p class="notification-text">这是通知的内容描述</p>
</div>
</div>

Tailwind 方式: 直接在 HTML 中使用工具类

<div class="mx-auto flex max-w-sm items-center gap-4 rounded-lg bg-white p-4 shadow-md">
<img class="size-12 shrink-0" src="icon.svg" alt="">
<div>
<div class="text-lg font-semibold text-gray-800">通知标题</div>
<p class="mt-1 text-gray-500">这是通知的内容描述</p>
</div>
</div>

功能类优先的优势

开发速度快:不需要在 HTML 和 CSS 文件之间来回切换,也不需要思考类名。样式直接写在元素上,所见即所得。

修改更安全:每个工具类只影响当前元素,修改样式不会意外影响其他页面或组件。

维护更容易:六个月后回来维护代码,不需要回忆当初写的 CSS 是什么意思,直接看类名就明白。

代码更便携:结构和样式在同一个地方,复制粘贴组件时不会遗漏样式。

CSS 不会无限增长:工具类是可复用的,项目变大不会导致 CSS 文件线性增长。

命名约定

Tailwind CSS 的类名遵循一致的命名约定,掌握规律后很容易记忆。

基本格式

大多数工具类遵循 属性-值 的格式:

类名CSS 属性
text-centertext-aligncenter
font-boldfont-weightbold
bg-whitebackground-colorwhite
p-4padding1rem
m-2margin0.5rem

数值比例

间距、尺寸等使用数值比例系统:

<div class="p-1">padding: 0.25rem (4px)</div>
<div class="p-2">padding: 0.5rem (8px)</div>
<div class="p-4">padding: 1rem (16px)</div>
<div class="p-6">padding: 1.5rem (24px)</div>
<div class="p-8">padding: 2rem (32px)</div>

比例系统基于 4px 的基础单位,数值越大,间距越大。

方向修饰符

可以使用方向修饰符指定特定方向:

<div class="p-4">四个方向</div>
<div class="px-4">左右方向</div>
<div class="py-4">上下方向</div>
<div class="pt-4">上方</div>
<div class="pr-4">右侧</div>
<div class="pb-4">下方</div>
<div class="pl-4">左侧</div>

方向修饰符规则:

  • t = top(上)
  • r = right(右)
  • b = bottom(下)
  • l = left(左)
  • x = 水平方向(左右)
  • y = 垂直方向(上下)

常用工具类概览

布局类

<div class="flex">display: flex</div>
<div class="grid">display: grid</div>
<div class="block">display: block</div>
<div class="hidden">display: none</div>

<div class="flex items-center justify-center">
Flexbox 居中布局
</div>

<div class="grid grid-cols-3 gap-4">
三列网格布局
</div>

尺寸类

<div class="w-full">width: 100%</div>
<div class="w-1/2">width: 50%</div>
<div class="w-64">width: 16rem</div>
<div class="h-screen">height: 100vh</div>
<div class="max-w-md">max-width: 28rem</div>

间距类

<div class="p-4">内边距 1rem</div>
<div class="m-4">外边距 1rem</div>
<div class="gap-4">间隙 1rem</div>
<div class="space-y-4">子元素垂直间距</div>

文字类

<p class="text-sm">小号文字</p>
<p class="text-lg">大号文字</p>
<p class="text-2xl">超大号文字</p>
<p class="font-bold">粗体文字</p>
<p class="text-center">居中文字</p>
<p class="text-gray-500">灰色文字</p>

背景和边框

<div class="bg-white">白色背景</div>
<div class="bg-blue-500">蓝色背景</div>
<div class="border">1px 边框</div>
<div class="border-2">2px 边框</div>
<div class="rounded">圆角</div>
<div class="rounded-lg">大圆角</div>
<div class="rounded-full">完全圆形</div>

组合使用

Tailwind 的强大之处在于组合多个工具类创建复杂组件。

按钮示例

<button class="bg-blue-500 hover:bg-blue-700 text-white font-bold py-2 px-4 rounded">
基础按钮
</button>

<button class="bg-transparent hover:bg-blue-500 text-blue-700 font-semibold hover:text-white py-2 px-4 border border-blue-500 hover:border-transparent rounded">
轮廓按钮
</button>

<button class="bg-red-500 hover:bg-red-700 text-white font-bold py-2 px-4 rounded-full">
圆形按钮
</button>

卡片示例

<div class="max-w-sm rounded overflow-hidden shadow-lg bg-white">
<img class="w-full" src="/img/card-top.jpg" alt="图片">
<div class="px-6 py-4">
<div class="font-bold text-xl mb-2">卡片标题</div>
<p class="text-gray-700 text-base">
这是卡片的描述内容,可以包含多行文字。
</p>
</div>
<div class="px-6 pt-4 pb-2">
<span class="inline-block bg-gray-200 rounded-full px-3 py-1 text-sm font-semibold text-gray-700 mr-2 mb-2">
标签1
</span>
<span class="inline-block bg-gray-200 rounded-full px-3 py-1 text-sm font-semibold text-gray-700 mr-2 mb-2">
标签2
</span>
</div>
</div>

处理重复样式

使用 Tailwind 时,你可能会遇到重复的类组合。有几种处理方式:

使用组件抽象

在 React、Vue 等框架中,可以创建组件来封装重复的样式:

function Button({ children, variant = 'primary' }) {
const baseClasses = 'font-bold py-2 px-4 rounded'
const variants = {
primary: 'bg-blue-500 hover:bg-blue-700 text-white',
secondary: 'bg-gray-500 hover:bg-gray-700 text-white',
outline: 'bg-transparent border border-blue-500 text-blue-500 hover:bg-blue-500 hover:text-white',
}

return (
<button className={`${baseClasses} ${variants[variant]}`}>
{children}
</button>
)
}

使用 @apply 指令

在 CSS 文件中使用 @apply 提取重复的类:

@layer components {
.btn {
@apply font-bold py-2 px-4 rounded;
}
.btn-primary {
@apply bg-blue-500 hover:bg-blue-700 text-white;
}
}
建议

优先使用组件抽象,@apply 仅在必要时使用。Tailwind 官方推荐保持工具类的使用方式。

状态变体

Tailwind 的一个核心特性是可以通过变体(variants)来控制样式应用的条件。

悬停和焦点状态

使用 hover:focus: 前缀为元素添加交互状态样式:

<!-- 悬停状态 -->
<button class="bg-sky-500 hover:bg-sky-700">
悬停时变深
</button>

<!-- 焦点状态 -->
<input class="border-gray-300 focus:border-blue-500 focus:ring-2">
聚焦时显示蓝色边框
</input>

变体的工作原理:每个变体只做一件事——在特定条件下应用样式。这与传统 CSS 不同,传统方式通常在一个类中定义多个状态:

<!-- 传统 CSS 方式 -->
<style>
.btn {
background-color: #0ea5e9;
}
.btn:hover {
background-color: #0284c7;
}
</style>

<!-- Tailwind 方式:分离关注 -->
<button class="bg-sky-500 hover:bg-sky-700">
保存更改
</button>

生成的 CSS 如下,注意样式只在悬停时生效:

.bg-sky-500 {
background-color: var(--color-sky-500);
}

.hover\:bg-sky-700:hover {
background-color: var(--color-sky-700);
}

变体堆叠

可以组合多个变体来创建复杂条件:

<!-- 悬停且禁用时的样式 -->
<button class="bg-blue-500 disabled:hover:bg-blue-500 opacity-50">
特殊状态
</button>

<!-- 深色模式下悬停 -->
<a class="text-gray-600 dark:hover:text-white">
链接
</a>

常用状态变体

变体触发条件示例
hover:鼠标悬停hover:bg-blue-500
focus:元素聚焦focus:ring-2
active:元素被激活(点击)active:scale-95
disabled:元素禁用disabled:opacity-50
first:父元素的第一个子元素first:mt-0
last:父元素的最后一个子元素last:mb-0
odd:奇数位置子元素odd:bg-gray-100
even:偶数位置子元素even:bg-gray-50
checked:复选框/单选框选中checked:bg-blue-500

响应式设计理念

移动优先原则

Tailwind 采用移动优先(Mobile-First)的断点系统。这意味着:

  • 无前缀的工具类在所有屏幕尺寸生效
  • 带断点前缀的工具类只在指定断点及以上生效
<!-- 正确理解移动优先 -->
<div class="text-center sm:text-left">
移动端居中,sm 及以上屏幕左对齐
</div>

<!-- 常见错误:sm 不是"小屏幕" -->
<div class="sm:text-center">
错误!这只在 640px 及以上居中,小屏幕无样式
</div>

断点系统

Tailwind 默认提供五个断点:

前缀最小宽度典型设备
sm:640px大手机/小平板
md:768px平板电脑
lg:1024px笔记本电脑
xl:1280px桌面显示器
2xl:1536px大屏幕显示器

断点范围控制

使用 max-* 变体限制样式在特定断点以下生效:

<!-- 只在 md 断点以下生效 -->
<div class="flex max-md:flex-col">
中等屏幕以下垂直排列
</div>

<!-- 只在 md 到 lg 之间生效 -->
<div class="hidden md:max-lg:block">
仅中等屏幕可见
</div>

响应式最佳实践

<!-- 推荐:从移动端样式开始,逐步添加大屏样式 -->
<div class="grid grid-cols-1 sm:grid-cols-2 lg:grid-cols-3 xl:grid-cols-4">
响应式网格
</div>

<!-- 不推荐:试图"只在小屏幕生效" -->
<div class="sm:hidden">
这种写法表示"640px及以上隐藏"
</div>

<!-- 正确写法:小屏幕显示,大屏幕隐藏 -->
<div class="block sm:hidden">
仅小屏幕可见
</div>

暗黑模式

Tailwind 内置了对暗黑模式的完整支持。

基本使用

使用 dark: 前缀为暗黑模式定义样式:

<div class="bg-white dark:bg-gray-800 text-gray-900 dark:text-white">
<p class="text-gray-600 dark:text-gray-300">
自适应主题的文字
</p>
</div>

暗黑模式的触发方式

方式一:跟随系统偏好(默认)

<!-- 自动跟随操作系统的深色模式 -->
<html class="dark">

方式二:手动切换

// 通过 JavaScript 切换
document.documentElement.classList.toggle('dark')

方式三:CSS 配置

/* 使用 CSS 变量控制 */
@import "tailwindcss";

@custom-variant dark (&:where(.dark, .dark *)) {
@slot;
}

暗黑模式最佳实践

<!-- 完整的暗黑模式组件 -->
<div class="bg-white dark:bg-gray-900 rounded-lg shadow-lg dark:shadow-none p-6">
<h3 class="text-gray-900 dark:text-white font-bold">
标题
</h3>
<p class="text-gray-600 dark:text-gray-400">
这是一段描述文字,会根据主题自动切换颜色。
</p>
<button class="mt-4 bg-blue-500 hover:bg-blue-600 dark:bg-blue-600 dark:hover:bg-blue-700 text-white px-4 py-2 rounded">
按钮
</button>
</div>

任意值

当需要使用主题之外的值时,可以使用方括号语法指定任意值。

基本语法

<!-- 任意颜色 -->
<button class="bg-[#1da1f2] text-white">
Facebook 蓝
</button>

<!-- 任意尺寸 -->
<div class="w-[320px] h-[240px]">
固定尺寸
</div>

<!-- 任意间距 -->
<div class="mt-[13px] mb-[27px]">
精确间距
</div>

主题值引用

在任意值中引用主题变量:

<!-- 使用主题颜色 -->
<div class="bg-[var(--color-blue-500)]">
引用主题变量
</div>

<!-- 使用 calc 计算 -->
<div class="max-h-[calc(100vh-4rem)]">
计算高度
</div>

<!-- 使用主题间距函数 -->
<div class="p-[--spacing(8)]">
使用主题间距
</div>

任意属性

使用 [属性名:值] 语法设置任意 CSS 属性:

<!-- 设置 CSS 变量 -->
<div class="[--gutter:1rem]">
定义变量
</div>

<!-- 任意 CSS 属性 -->
<div class="[mask-image:url('gradient.png')]">
遮罩效果
</div>

任意值最佳实践

<!-- 不推荐:复杂值难以阅读 -->
<div class="grid-cols-[repeat(auto-fit,minmax(200px,1fr))]">
</div>

<!-- 推荐:使用内联样式或自定义 CSS -->
<div style="grid-template-columns: repeat(auto-fit, minmax(200px, 1fr))">
更清晰的复杂样式
</div>

样式冲突处理

当多个工具类设置相同的 CSS 属性时,需要理解如何处理冲突。

冲突规则

后定义的类优先:当两个类设置同一属性时,CSS 文件中后出现的生效:

<!-- grid 会覆盖 flex,因为它在 CSS 中后出现 -->
<div class="flex grid">
这是网格布局
</div>

生成的 CSS 顺序:

.flex { display: flex; }
.grid { display: grid; } /* 后出现,优先级更高 */

避免冲突

最佳做法是不要添加冲突的类,而是根据条件选择正确的类:

// React 示例
function Layout({ useGrid }) {
return (
<div className={useGrid ? 'grid' : 'flex'}>
{/* 内容 */}
</div>
);
}

重要修饰符

需要强制覆盖时,可以在类名末尾添加 !

<!-- bg-red-500! 会覆盖 bg-teal-500 -->
<div class="bg-teal-500 bg-red-500!">
强制红色背景
</div>

生成的 CSS:

.bg-teal-500 {
background-color: var(--color-teal-500);
}

.bg-red-500\! {
background-color: var(--color-red-500) !important;
}
慎用 !important

只在确实需要覆盖第三方样式或无法控制的高优先级选择器时使用。过度使用会破坏 CSS 的可维护性。

全局重要标志

导入 Tailwind 时设置 important 标志,使所有工具类都带 !important

@import "tailwindcss" important;

这在与现有高优先级 CSS 集成时非常有用。

类组合技术

多类组合

Tailwind 使用 CSS 变量实现多个类的组合效果:

<!-- 多个滤镜效果组合 -->
<div class="blur-sm grayscale">
模糊 + 灰度
</div>

生成的 CSS 原理:

.blur-sm {
--tw-blur: blur(var(--blur-sm));
filter: var(--tw-blur,) var(--tw-grayscale,);
}

.grayscale {
--tw-grayscale: grayscale(100%);
filter: var(--tw-blur,) var(--tw-grayscale,);
}

每个类设置自己的 CSS 变量,最终的 filter 属性组合所有变量。这种模式也用于:

  • 渐变颜色
  • 阴影颜色
  • 变换效果

复杂选择器

使用任意变体创建复杂选择器:

<!-- 父元素悬停时子元素样式 -->
<div class="group">
<span class="group-hover:underline">
悬停父元素时下划线
</span>
</div>

<!-- 兄弟元素选择器 -->
<div>
<span data-active></span>
<span class="[&>[data-active]+span]:text-blue-600">
紧跟 data-active 后的 span 变蓝
</span>
</div>

组件抽象策略

循环渲染

当重复元素通过循环渲染时,类列表只写一次:

// React 示例
function AvatarList({ users }) {
return (
<div class="flex -space-x-2">
{users.map(user => (
<img
key={user.id}
class="inline-block h-12 w-12 rounded-full ring-2 ring-white"
src={user.avatar}
alt={user.name}
/>
))}
</div>
);
}

多光标编辑

对于同一文件内的重复,使用编辑器的多光标功能:

<!-- 使用 Alt+Click 或 Ctrl+D 选择多个相同类列表 -->
<nav class="flex justify-center space-x-4">
<a href="#" class="px-3 py-2 rounded-lg font-medium text-gray-700 hover:bg-gray-100">
首页
</a>
<a href="#" class="px-3 py-2 rounded-lg font-medium text-gray-700 hover:bg-gray-100">
产品
</a>
<a href="#" class="px-3 py-2 rounded-lg font-medium text-gray-700 hover:bg-gray-100">
关于
</a>
</nav>

组件封装

对于跨文件复用的样式,创建组件:

// React 组件封装
export function Button({ variant = 'primary', size = 'md', children }) {
const baseClasses = 'font-medium rounded-lg transition-colors';

const variants = {
primary: 'bg-blue-500 hover:bg-blue-600 text-white',
secondary: 'bg-gray-200 hover:bg-gray-300 text-gray-900',
outline: 'border-2 border-blue-500 text-blue-500 hover:bg-blue-50',
};

const sizes = {
sm: 'px-3 py-1.5 text-sm',
md: 'px-4 py-2 text-base',
lg: 'px-6 py-3 text-lg',
};

return (
<button className={`${baseClasses} ${variants[variant]} ${sizes[size]}`}>
{children}
</button>
);
}

自定义 CSS(传统方式)

对于简单场景,可以编写自定义 CSS:

<button class="btn-primary">保存</button>
@import "tailwindcss";

@layer components {
.btn-primary {
border-radius: calc(infinity * 1px);
background-color: var(--color-violet-500);
padding-inline: --spacing(5);
padding-block: --spacing(2);
font-weight: var(--font-weight-semibold);
color: var(--color-white);

&:hover {
@media (hover: hover) {
background-color: var(--color-violet-700);
}
}
}
}

Tailwind CSS v4.0 的核心理念更新

v4.0 在核心理念上带来了一些重要变化:

CSS-first 配置

不再需要 JavaScript 配置文件,直接在 CSS 中配置:

@import "tailwindcss";

@theme {
--font-display: "Satoshi", sans-serif;
--color-brand-500: oklch(0.7 0.15 250);
--breakpoint-xs: 30rem;
}

原生 CSS 变量

所有设计令牌自动暴露为 CSS 变量:

:root {
--color-blue-500: oklch(0.7 0.15 250);
--font-family-sans: Inter, sans-serif;
--spacing: 0.25rem;
}

在任意地方使用:

<div style="background-color: var(--color-blue-500)">
使用主题变量
</div>

动态值支持

间距和尺寸工具类现在动态生成,无需预定义:

<!-- 无需在主题中定义 17 -->
<div class="p-17 mt-29 w-42">
动态间距和尺寸
</div>

小结

本章深入讲解了 Tailwind CSS 的核心理念:

设计思想

  • 功能类优先:使用小型、单一目的的工具类构建界面
  • 分离关注:每个类只做一件事,在特定条件下生效
  • 移动优先:从小屏幕样式开始,逐步增强大屏体验

技术机制

  • 状态变体:hover、focus、active 等条件前缀
  • 响应式断点:sm、md、lg、xl、2xl 断点系统
  • 暗黑模式:dark: 前缀实现主题切换
  • 任意值:方括号语法突破主题限制

最佳实践

  • 避免冲突:不添加冲突的类,根据条件选择
  • 组件封装:循环、多光标、组件抽象处理重复
  • 慎用 important:只在必要时使用强制覆盖

v4.0 新特性

  • CSS-first 配置:直接在 CSS 中定义主题
  • 原生 CSS 变量:设计令牌全局可用
  • 动态值:间距和尺寸类按需生成

下一章,我们将学习 Tailwind CSS 的布局系统,包括 Flexbox、Grid 和容器查询等现代布局技术。