核心概念
添加自定义样式
在 Tailwind 项目中添加你自己的自定义样式的最佳实践。
使用框架时最大的挑战通常是弄清楚当你需要某些东西而框架无法为你处理时你应该做什么。
¥Often the biggest challenge when working with a framework is figuring out what you’re supposed to do when there’s something you need that the framework doesn’t handle for you.
Tailwind 从一开始就被设计为可扩展和可定制的,因此无论你构建什么,你都不会觉得自己在与框架作斗争。
¥Tailwind has been designed from the ground up to be extensible and customizable, so that no matter what you’re building you never feel like you’re fighting the framework.
本指南涵盖的主题包括自定义你的设计标记、如何在必要时打破这些限制、添加你自己的自定义 CSS 以及使用插件扩展框架。
¥This guide covers topics like customizing your design tokens, how to break out of those constraints when necessary, adding your own custom CSS, and extending the framework with plugins.
自定义主题(Customizing your theme)
¥Customizing your theme
如果你想要更改调色板、间距比例、排版比例或断点等内容,请使用 CSS 中的 @theme
指令添加自定义项:
¥If you want to change things like your color palette, spacing scale, typography scale, or breakpoints, add your customizations using the @theme
directive in your CSS:
@theme { --font-display: "Satoshi", "sans-serif"; --breakpoint-3xl: 120rem; --color-avocado-100: oklch(0.99 0 0); --color-avocado-200: oklch(0.98 0.04 113.22); --color-avocado-300: oklch(0.94 0.11 115.03); --color-avocado-400: oklch(0.92 0.19 114.08); --color-avocado-500: oklch(0.84 0.18 117.33); --color-avocado-600: oklch(0.53 0.12 118.34); --ease-fluid: cubic-bezier(0.3, 0, 0, 1); --ease-snappy: cubic-bezier(0.2, 0, 0, 1); /* ... */}
了解有关在 主题变量文档 中自定义主题的更多信息。
¥Learn more about customizing your theme in the theme variables documentation.
使用任意值(Using arbitrary values)
¥Using arbitrary values
虽然你通常可以使用一组受限的设计标记来构建大量精心设计的设计,但有时你需要突破这些限制以获得像素完美的东西。
¥While you can usually build the bulk of a well-crafted design using a constrained set of design tokens, once in a while you need to break out of those constraints to get things pixel-perfect.
当你发现自己真的需要像 top: 117px
这样的东西来在正确的位置获得背景图片时,使用 Tailwind 的方括号符号来动态生成一个具有任意值的类:
¥When you find yourself really needing something like top: 117px
to get a background image in just the right spot, use Tailwind's square bracket notation to generate a class on the fly with any arbitrary value:
<div class="top-[117px]"> <!-- ... --></div>
这基本上类似于内联样式,主要好处是你可以将它与交互式修饰符(如 hover
)和响应式修饰符(如 lg
)结合使用:
¥This is basically like inline styles, with the major benefit that you can combine it with interactive modifiers like hover
and responsive modifiers like lg
:
<div class="top-[117px] lg:top-[344px]"> <!-- ... --></div>
这适用于框架中的所有内容,包括背景颜色、字体大小、伪元素内容等:
¥This works for everything in the framework, including things like background colors, font sizes, pseudo-element content, and more:
<div class="bg-[#bada55] text-[22px] before:content-['Festivus']"> <!-- ... --></div>
如果你将 CSS 变量引用为任意值,则可以使用自定义属性语法:
¥If you're referencing a CSS variable as an arbitrary value, you can use the custom property syntax:
<div class="fill-(--my-brand-color) ..."> <!-- ... --></div>
这只是 fill-[var(--my-brand-color)]
的简写,可自动为你添加 var()
功能。
¥This is just a shorthand for fill-[var(--my-brand-color)]
that adds the var()
function for you automatically.
任意属性(Arbitrary properties)
¥Arbitrary properties
如果你需要使用 Tailwind 不包含开箱即用工具的 CSS 属性,你还可以使用方括号表示法来编写完全任意的 CSS:
¥If you ever need to use a CSS property that Tailwind doesn't include a utility for out of the box, you can also use square bracket notation to write completely arbitrary CSS:
<div class="[mask-type:luminance]"> <!-- ... --></div>
这真的很像内联样式,但同样的好处是你可以使用修饰符:
¥This is really like inline styles, but again with the benefit that you can use modifiers:
<div class="[mask-type:luminance] hover:[mask-type:alpha]"> <!-- ... --></div>
这对于 CSS 变量之类的东西也很有用,尤其是当它们需要在不同条件下更改时:
¥This can be useful for things like CSS variables as well, especially when they need to change under different conditions:
<div class="[--scroll-offset:56px] lg:[--scroll-offset:44px]"> <!-- ... --></div>
任意变体(Arbitrary variants)
¥Arbitrary variants
任意变体类似于任意值,但用于进行即时选择器修改,就像你可以使用内置伪类变体(如 hover:{utility}
)或响应式变体(如 md:{utility}
)一样,但直接在 HTML 中使用方括号表示法。
¥Arbitrary variants are like arbitrary values but for doing on-the-fly selector modification, like you can with built-in pseudo-class variants like hover:{utility}
or responsive variants like md:{utility}
but using square bracket notation directly in your HTML.
<ul role="list"> {#each items as item} <li class="lg:[&:nth-child(-n+3)]:hover:underline">{item}</li> {/each}</ul>
在 任意变体 文档中了解更多信息。
¥Learn more in the arbitrary variants documentation.
处理空格(Handling whitespace)
¥Handling whitespace
当任意值需要包含空格时,请改用下划线 (_
),Tailwind 会在构建时自动将其转换为空格:
¥When an arbitrary value needs to contain a space, use an underscore (_
) instead and Tailwind will automatically convert it to a space at build-time:
<div class="grid grid-cols-[1fr_500px_2fr]"> <!-- ... --></div>
在下划线很常见但空格无效的情况下,Tailwind 将保留下划线而不是将其转换为空格,例如在 URL 中:
¥In situations where underscores are common but spaces are invalid, Tailwind will preserve the underscore instead of converting it to a space, for example in URLs:
<div class="bg-[url('/what_a_rush.png')]"> <!-- ... --></div>
在极少数情况下,你实际上需要使用下划线,但由于空格也有效而导致歧义,请使用反斜杠转义下划线,Tailwind 不会将其转换为空格:
¥In the rare case that you actually need to use an underscore but it's ambiguous because a space is valid as well, escape the underscore with a backslash and Tailwind won't convert it to a space:
<div class="before:content-['hello\_world']"> <!-- ... --></div>
如果你使用的是像 JSX 这样的东西,其中反斜杠从渲染的 HTML 中剥离,请使用 String.raw() 这样反斜杠就不会被视为 JavaScript 转义字符:
¥If you're using something like JSX where the backslash is stripped from the rendered HTML, use String.raw() so the backslash isn't treated as a JavaScript escape character:
<div className={String.raw`before:content-['hello\_world']`}> <!-- ... --></div>
解决歧义(Resolving ambiguities)
¥Resolving ambiguities
Tailwind 中的许多工具共享一个公共命名空间,但映射到不同的 CSS 属性。例如 text-lg
和 text-black
都共享 text-
命名空间,但一个用于 font-size
,另一个用于 color
。
¥Many utilities in Tailwind share a common namespace but map to different CSS properties. For example text-lg
and text-black
both share the text-
namespace, but one is for font-size
and the other is for color
.
使用任意值时,Tailwind 通常可以根据你传入的值自动处理这种歧义:
¥When using arbitrary values, Tailwind can generally handle this ambiguity automatically based on the value you pass in:
<!-- Will generate a font-size utility --><div class="text-[22px]">...</div><!-- Will generate a color utility --><div class="text-[#bada55]">...</div>
有时它确实是模棱两可的,例如在使用 CSS 变量时:
¥Sometimes it really is ambiguous though, for example when using CSS variables:
<div class="text-(--my-var)">...</div>
在这些情况下,你可以通过在值前添加 CSS 数据类型 将基础类型 "hint" 为 Tailwind:
¥In these situations, you can "hint" the underlying type to Tailwind by adding a CSS data type before the value:
<!-- Will generate a font-size utility --><div class="text-(length:--my-var)">...</div><!-- Will generate a color utility --><div class="text-(color:--my-var)">...</div>
使用自定义 CSS(Using custom CSS)
¥Using custom CSS
虽然 Tailwind 旨在满足你的大部分样式需求,但没有什么可以阻止你在需要时只编写纯 CSS:
¥While Tailwind is designed to handle the bulk of your styling needs, there is nothing stopping you from just writing plain CSS when you need to:
@import "tailwindcss";.my-custom-style { /* ... */}
添加基本样式(Adding base styles)
¥Adding base styles
如果你只想为页面设置一些默认值(如文本颜色、背景颜色或字体系列),最简单的选择就是向 html
或 body
元素添加一些类:
¥If you just want to set some defaults for the page (like the text color, background color, or font family), the easiest option is just adding some classes to the html
or body
elements:
<!doctype html><html lang="en" class="bg-gray-100 font-serif text-gray-900"> <!-- ... --></html>
这会将你的基本样式决策与所有其他样式一起保存在标记中,而不是将它们隐藏在单独的文件中。
¥This keeps your base styling decisions in your markup alongside all of your other styles, instead of hiding them in a separate file.
如果你想为特定的 HTML 元素添加自己的默认基本样式,请使用 @layer
指令将这些样式添加到 Tailwind 的 base
层:
¥If you want to add your own default base styles for specific HTML elements, use the @layer
directive to add those styles to Tailwind's base
layer:
@layer base { h1 { font-size: var(--text-2xl); } h2 { font-size: var(--text-xl); }}
添加组件类(Adding component classes)
¥Adding component classes
将 components
层用于你想要添加到你的项目中的任何更复杂的类,你仍然希望能够使用工具类覆盖这些类。
¥Use the components
layer for any more complicated classes you want to add to your project that you'd still like to be able to override with utility classes.
传统上,这些将是像 card
、btn
、badge
这样的类。
¥Traditionally these would be classes like card
, btn
, badge
— that kind of thing.
@layer components { .card { background-color: var(--color-white); border-radius: var(--rounded-lg); padding: var(--spacing-6); box-shadow: var(--shadow-xl); }}
通过在 components
层定义组件类,必要时仍然可以使用实用类来覆盖它们:
¥By defining component classes in the components
layer, you can still use utility classes to override them when necessary:
<!-- Will look like a card, but with square corners --><div class="card rounded-none"> <!-- ... --></div>
使用 Tailwind,你可能并不像你想象的那样经常需要这些类型的类。阅读我们关于 管理重复 的指南,了解我们的建议。
¥Using Tailwind you probably don't need these types of classes as often as you think. Read our guide on managing duplication for our recommendations.
components
层也是为你使用的任何第三方组件放置自定义样式的好地方:
¥The components
layer is also a good place to put custom styles for any third-party components you're using:
@layer components { .select2-dropdown { /* ... */ }}
添加自定义工具(Adding custom utilities)
¥Adding custom utilities
简单工具(Simple utilities)
¥Simple utilities
除了使用 Tailwind 附带的工具外,你还可以添加自己的自定义工具。当你希望在项目中使用某个 CSS 功能,而 Tailwind 不包含开箱即用的工具时,这会很有用。
¥In addition to using the utilities that ship with Tailwind, you can also add your own custom utilities. This can be useful when there's a CSS feature you'd like to use in your project that Tailwind doesn't include utilities for out of the box.
使用 @utility
指令将自定义工具添加到你的项目:
¥Use the @utility
directive to add a custom utility to your project:
@utility content-auto { content-visibility: auto;}
你现在可以在 HTML 中使用此工具:
¥You can now use this utility in your HTML:
<div class="content-auto"> <!-- ... --></div>
它还可以与 hover
、focus
和 lg
等变体一起使用:
¥It will also work with variants like hover
, focus
and lg
:
<div class="hover:content-auto"> <!-- ... --></div>
自定义工具会与框架中的所有内置工具一起自动插入到 utilities
层中。
¥Custom utilities are automatically inserted into the utilities
layer along with all of the built-in utilities in the framework.
复杂工具(Complex utilities)
¥Complex utilities
如果你的自定义工具比单个类名更复杂,请使用嵌套来定义工具:
¥If your custom utility is more complex than a single class name, use nesting to define the utility:
@utility scrollbar-hidden { &::-webkit-scrollbar { display: none; }}
功能工具(Functional utilities)
¥Functional utilities
除了使用 @utility
指令注册简单工具外,你还可以注册接受参数的功能工具:
¥In addition to registering simple utilities with the @utility
directive, you can also register functional utilities that accept an argument:
@utility tab-* { tab-size: --value(--tab-size-*);}
特殊的 --value()
函数用于解析效用值。
¥The special --value()
function is used to resolve the utility value.
匹配主题值(Matching theme values)
¥Matching theme values
使用 --value(--theme-key-*)
语法根据一组主题键解析实用值:
¥Use the --value(--theme-key-*)
syntax to resolve the utility value against a set of theme keys:
@theme { --tab-size-2: 2; --tab-size-4: 4; --tab-size-github: 8;}@utility tab-* { tab-size: --value(--tab-size-*);}
这将匹配 tab-2
、tab-4
和 tab-github
等工具。
¥This will match utilities like tab-2
, tab-4
, and tab-github
.
裸值(Bare values)
¥Bare values
要将值解析为裸值,请使用 --value({type})
语法,其中 {type}
是你要将裸值验证为的数据类型:
¥To resolve the value as a bare value, use the --value({type})
syntax, where {type}
is the data type you want to validate the bare value as:
@utility tab-* { tab-size: --value(integer);}
这将匹配 tab-1
和 tab-76
等工具。
¥This will match utilities like tab-1
and tab-76
.
任意值(Arbitrary values)
¥Arbitrary values
要支持任意值,请使用 --value([{type}])
语法(注意方括号)告诉 Tailwind 支持哪些类型作为任意值:
¥To support arbitrary values, use the --value([{type}])
syntax (notice the square brackets) to tell Tailwind which types are supported as an arbitrary value:
@utility tab-* { tab-size: --value([integer]);}
这将匹配 tab-[1]
和 tab-[76]
等工具。如果你想要支持任何数据类型,则可以使用 --value([*])
。
¥This will match utilities like tab-[1]
and tab-[76]
. If you want to support any data type, you can use --value([*])
.
同时支持主题、裸值和任意值(Supporting theme, bare, and arbitrary values together)
¥Supporting theme, bare, and arbitrary values together
--value()
函数的所有三种形式都可以在规则中用作多个声明,并且任何无法解析的声明都将在输出中省略:
¥All three forms of the --value()
function can be used within a rule as multiple declarations, and any declarations that fail to resolve will be omitted in the output:
@theme { --tab-size-github: 8;}@utility tab-* { tab-size: --value([integer]); tab-size: --value(integer); tab-size: --value(--tab-size-*);}
这使得可以根据需要在不同情况下以不同方式处理值,例如将裸整数转换为百分比:
¥This makes it possible to treat the value differently in each case if necessary, for example translating a bare integer to a percentage:
@utility opacity-* { opacity: --value([percentage]); opacity: calc(--value(integer) * 1%); opacity: --value(--opacity-*);}
如果你不需要在不同情况下以不同方式处理返回值,--value()
函数还可以接受多个参数并从左到右解析它们:
¥The --value()
function can also take multiple arguments and resolve them left to right if you don't need to treat the return value differently in different cases:
@theme { --tab-size-github: 8;}@utility tab-* { tab-size: --value(--tab-size-*, integer, [integer]);}@utility opacity-* { opacity: calc(--value(integer) * 1%); opacity: --value(--opacity-*, [percentage]);}
否定值(Negative values)
¥Negative values
要支持负值,请将单独的正值和负值工具注册到单独的声明中:
¥To support negative values, register separate positive and negative utilities into separate declarations:
@utility inset-* { inset: calc(var(--spacing) * --value([percentage], [length]));}@utility -inset-* { inset: calc(var(--spacing) * --value([percentage], [length]) * -1);}
修饰符(Modifiers)
¥Modifiers
修饰符使用 --modifier()
函数处理,该函数的工作原理与 --value()
函数完全相同,但如果存在修饰符,则对其进行操作:
¥Modifiers are handled using the --modifier()
function which works exactly like the --value()
function but operates on a modifier if present:
@utility text-* { font-size: --value(--text-*, [length]); line-height: --modifier(--leading-*, [length], [*]);}
如果不存在修饰符,则任何依赖于修饰符的声明都不会包含在输出中。
¥If a modifier isn't present, any declaration depending on a modifier is just not included in the output.
分数(Fractions)
¥Fractions
要处理分数,我们依赖 CSS ratio
数据类型。如果将其与 --value()
一起使用,则向 Tailwind 发送信号,将值和修饰符视为单个值:
¥To handle fractions, we rely on the CSS ratio
data type. If this is used with --value()
, it's a signal to Tailwind to treat the value and modifier as a single value:
@utility aspect-* { aspect-ratio: --value(--aspect-ratio-*, ratio, [ratio]);}
这将匹配 aspect-square
、aspect-3/4
和 aspect-[7/9]
等工具。
¥This will match utilities like aspect-square
, aspect-3/4
, and aspect-[7/9]
.
添加自定义变体(Adding custom variants)
¥Adding custom variants
使用 @variant
指令在自定义 CSS 中应用 Tailwind 变体:
¥Use the @variant
directive to apply a Tailwind variant within custom CSS:
.my-element { background: white; @variant dark { background: black; }}
如果你需要同时应用多个变体,请使用嵌套:
¥If you need to apply multiple variants at the same time, use nesting:
.my-element { background: white; @variant dark { @variant hover { background: black; } }}