
去年夏天在 Tailwind Connect 大会上,我分享了 Oxide 的预览——我们一直在开发的一种新的高性能 Tailwind CSS 引擎,旨在简化开发者体验,并充分利用近年来 Web 平台的发展。
新引擎最初计划作为 v3.x 版本发布,但即使我们致力于向后兼容,但这感觉显然是该框架的新一代版本,因此值得命名为 v4.0。
现在还处于早期阶段,我们还有大量工作要做,但今天我们公开了我们的开发进展,并标记了第一个公开 v4.0.0-alpha 版本,以便您可以开始试用它,并帮助我们在今年晚些时候发布稳定版本。
我会尽量简短,为稳定版本发布保留一些激动人心的内容,但如果您喜欢尝试非常早期和实验性的东西,这里应该有足够的信息让您入门。
一个为速度而生的新引擎
新引擎是从头开始重写的,它利用我们现在对该框架的所有了解,更好地为问题空间建模,从而以更少的代码使事情变得更快。
- 速度提升高达 10 倍——我们可以用 105 毫秒而不是 960 毫秒完成 Tailwind CSS 网站的完整构建,或者用 55 毫秒而不是 341 毫秒完成我们的 Catalyst UI 工具包的构建。
- 更小的体积——即使包含我们发布的更重的原生包(例如我们用 Rust 和 Lightning CSS 重写的部分),新引擎的安装体积也缩小了 35% 以上。
- 在关键部分使用 Rust——我们将框架中最昂贵和可并行化的部分迁移到了 Rust,同时将框架的核心保留在 TypeScript 中以实现可扩展性。
- 一个依赖项——新引擎唯一依赖的是 Lightning CSS。
- 自定义解析器——我们编写了自己的 CSS 解析器,并设计了适合我们需求的自定义数据结构,使我们的解析速度比使用 PostCSS 快 2 倍以上。
统一的工具链
Tailwind CSS v4 不再只是一个插件——它是一个用于处理 CSS 的一体化工具。我们已将 Lightning CSS 直接集成到框架中,因此您无需配置任何关于 CSS 管道的内容。
- 内置
@import
处理——无需设置和配置像postcss-import
这样的工具。 - 内置供应商前缀——您不再需要在您的项目中添加
autoprefixer
。 - 内置嵌套支持——无需插件即可展平嵌套的 CSS,开箱即用。
- 语法转换——现代 CSS 功能(如
oklch()
颜色和媒体查询范围)被转换为具有更好浏览器支持的语法。
我们仍然发布 PostCSS 插件,但我们也正在探索第一方 bundler 插件,并且我们在此第一个 alpha 版本中发布了一个官方 Vite 插件,您今天就可以试用。
为现代 Web 设计
我们正在展望 Tailwind CSS v4 的未来,并努力构建一个在未来几年内都会感觉前沿的框架。
- 原生级联层——我们现在使用真正的
@layer
规则,这解决了我们过去一直困扰的大量特异性问题。 - 显式定义的自定义属性——我们使用
@property
来定义我们的内部自定义属性,并具有适当的类型和约束,从而可以实现诸如过渡背景渐变之类的功能。 - 使用
color-mix
进行不透明度修饰符——当使用 CSS 变量进行颜色设置时,甚至在调整currentColor
的不透明度时,比以往任何时候都更容易使用我们的不透明度修饰符语法。 - 核心中的容器查询——我们已将容器查询的支持直接添加到核心,并添加了新的
@min-*
和@max-*
变体以支持容器查询范围。
我们还在努力使用广色域颜色刷新我们的调色板,并引入对其他现代 CSS 功能的支持,例如 @starting-style
、锚点定位等等。
可组合的变体
新的架构使得可以将作用于其他选择器的变体组合在一起,例如 group-*
、peer-*
、has-*
以及我们为 v4 引入的新 not-*
变体。
在早期版本中,像 group-has-*
这样的变体在框架中是显式定义的,但现在 group-*
可以与现有的 has-*
变体组合,而 has-*
变体又可以与其他变体(如 focus
)组合。
<div class="group"> <div class="group-has-[&:focus]:opacity-100"> <div class="group-has-focus:opacity-100"> <!-- ... --> </div> </div></div>
这种可组合性没有限制,您甚至可以编写类似 group-not-has-peer-not-data-active:underline
这样的代码,如果出于某种可怕的原因这是您需要做的。
零配置内容检测
您会注意到,至少在这些早期的 alpha 版本中,甚至无法配置您的 content
路径。对于大多数项目,您永远不需要再次执行此操作——Tailwind 会为您找到您的模板文件。
我们使用以下两种方式之一来完成此操作,具体取决于您如何将 Tailwind 集成到您的项目中
-
使用 PostCSS 插件或 CLI,Tailwind 将爬取您的整个项目以查找模板文件,并使用我们内置的大量启发式方法来保持速度,例如不爬取
.gitignore
文件中的目录,以及忽略二进制文件格式。 -
使用 Vite 插件,我们依赖模块图。这非常棒,因为我们确切地知道您实际使用的文件,因此它是性能最高的,并且没有误报或漏报。我们希望将来通过其他 bundler 插件将这种方法扩展到 Vite 生态系统之外。
我们将来肯定会引入一种显式配置内容路径的方法,但我们很好奇这种自动方法对大家的效果如何——它在我们自己的项目中效果非常好。
CSS 优先配置
Tailwind CSS v4.0 的主要目标是使框架感觉更像原生 CSS,而不是 JavaScript 库。
安装后,您可以使用常规 CSS @import
语句将其添加到您的项目中
@import "tailwindcss";
您只需使用 CSS 变量,而不是在 JavaScript 配置文件中设置所有自定义项
@import "tailwindcss";@theme { --font-family-display: "Satoshi", "sans-serif"; --breakpoint-3xl: 1920px; --color-neon-pink: oklch(71.7% 0.25 360); --color-neon-lime: oklch(91.5% 0.258 129); --color-neon-cyan: oklch(91.3% 0.139 195.8);}
特殊的 @theme
指令告诉 Tailwind 根据这些变量创建新的实用程序和变体,让您可以在标记中使用类似 3xl:text-neon-lime
这样的类
<div class="max-w-lg 3xl:max-w-xl"> <h1 class="font-display text-4xl"> Data to <span class="text-neon-cyan">enrich</span> your online business </h1></div>
添加新的 CSS 变量的行为类似于早期版本框架中的 extend
,但您可以通过在使用类似 --color-*: initial
这样的语法定义所有自定义值之前清除命名空间来覆盖整组变量
@import "tailwindcss";@theme { --color-*: initial; --color-gray-50: #f8fafc; --color-gray-100: #f1f5f9; --color-gray-200: #e2e8f0; /* ... */ --color-green-800: #3f6212; --color-green-900: #365314; --color-green-950: #1a2e05;}
我们仍在微调一些命名约定,但您可以在 GitHub 上探索默认主题,以查看有哪些内容可以自定义。
如果您不想显式清除默认主题,而是希望从头开始,您可以直接导入 "tailwindcss/preflight"
和 "tailwindcss/utilities"
以跳过导入默认主题
@import "tailwindcss";@import "tailwindcss/preflight" layer(base);@import "tailwindcss/utilities" layer(utilities);@theme { --color-*: initial; --color-gray-50: #f8fafc; --color-gray-100: #f1f5f9; --color-gray-200: #e2e8f0; /* ... */ --color-green-800: #3f6212; --color-green-900: #365314; --color-green-950: #1a2e05;}
我们还将您的所有主题值作为原生 CSS 变量在您的自定义 CSS 中提供
:root { --color-gray-50: #f8fafc; --color-gray-100: #f1f5f9; --color-gray-200: #e2e8f0; /* ... */ --color-green-800: #3f6212; --color-green-900: #365314; --color-green-950: #1a2e05;}
这使您可以轻松地在任意值中引用您的任何主题值,而无需使用 theme()
函数
<div class="p-[calc(var(--spacing-6)-1px)]"> <!-- ... --></div>
这也使得在使用像 Framer Motion 这样的 UI 库时可以使用您的主题值,而无需使用 resolveConfig()
函数
import { motion } from "framer-motion";export const MyComponent = () => ( <motion.div initial={{ y: "var(--spacing-8)" }} animate={{ y: 0 }} exit={{ y: "var(--spacing-8)" }}> {children} </motion.div>);
发生了什么变化
我们不会轻易进行重大更改,但到目前为止,我们在 v4 中做了一些不同的事情,值得分享
- 移除了已弃用的实用程序——我们移除了我们很久以前就停止记录的实用程序,例如
text-opacity-*
、flex-grow-*
和decoration-slice
,转而使用它们的现代替代品,例如text-{color}/*
、grow-*
和box-decoration-slice
。 - PostCSS 插件和 CLI 是单独的软件包——主要的
tailwindcss
软件包不再包含这些,因为并非每个人都需要它们,而是应该使用@tailwindcss/postcss
和@tailwindcss/cli
单独安装它们。 - 没有默认边框颜色——
border
实用程序过去默认使用gray-200
,但现在它像浏览器一样默认使用currentColor
。我们进行此更改是为了让您在使用zinc
或slate
或其他灰色作为主要灰色时,更难意外地在您的项目中引入错误的灰色。 - 默认情况下,Ring 为 1px——
ring
实用程序过去默认是一个 3px 蓝色环,现在它是一个使用currentColor
的 1px 环。我们发现在我们的项目中使用ring-*
实用程序作为边框的替代方案,并使用outline-*
作为焦点环,因此我们认为在这里保持一致是一个有益的更改。
还有一些其他的非常底层的实现细节更改,可能会以某种方式在您的项目中浮出水面,但没有任何像这些更改那样是故意的。如果您遇到任何令人惊讶的事情,请告诉我们。
v4.0 路线图
这个新引擎是从头开始重写的,到目前为止,我们一直专注于使用新的配置方法来重新构想开发者体验。
我们非常重视向后兼容性,这才是我们在今年晚些时候标记稳定版 v4.0 之前工作的大部分内容所在。
- 支持 JavaScript 配置文件——重新引入与经典
tailwind.config.js
文件的兼容性,以使迁移到 v4 变得容易。 - 显式内容路径配置——当自动内容检测不足以满足您的设置时,可以明确告诉 Tailwind 您的模板在哪里。
- 支持其他暗黑模式——目前我们仅支持使用媒体查询的暗黑模式,并且仍然需要重新实现选择器和变体策略。
- 插件和自定义实用程序——我们尚不支持插件,也不支持编写自动与变体一起使用的自定义实用程序。显然,我们会在稳定版本发布之前使其工作。
- 前缀支持——目前还没有办法为您的类配置前缀,但我们肯定会将其带回来。
- 安全列表和阻止列表——无法强制 Tailwind 生成某些类或阻止其生成其他类。
- 支持
important
配置——目前还没有办法使所有实用程序都使用!important
生成,但我们计划实现它。 - 支持
theme()
函数——新项目不需要此函数,因为您现在可以使用var()
,但我们将实现它以实现向后兼容性。 - 独立 CLI——我们尚未开发新引擎的独立 CLI,但绝对会在 v4.0 版本发布之前拥有它。
除此之外,我相信我们会发现很多错误需要修复,一些令人兴奋的新 CSS 功能需要偷偷加入,并改进一些需要更多润色的新 API,然后才能发布正式版本。
我不想对具体的发布时间表做出承诺,但我个人希望在夏季假期开始之前将 v4.0 标记为稳定版。
试用 alpha 版
我们已经标记了几个 alpha 版本,您可以立即开始在您的项目中试用它。
如果您正在使用 VS Code 的 Tailwind CSS IntelliSense 扩展,请确保从扩展页面切换到预发布版本,如果您正在使用我们的 Prettier 插件,请确保安装最新版本。
如果您发现问题,请在 GitHub 上告知我们。我们真的希望这个东西在标记为稳定版本之前是万无一失的,并且报告您发现的任何问题都将对我们有很大帮助。
使用 Vite
安装 Tailwind CSS v4 alpha 和我们新的 Vite 插件
npm install tailwindcss@next @tailwindcss/vite@next
然后将我们的插件添加到您的 vite.config.ts
文件中
import tailwindcss from "@tailwindcss/vite";import { defineConfig } from "vite";export default defineConfig({ plugins: [tailwindcss()],});
最后,在您的主 CSS 文件中导入 Tailwind
@import "tailwindcss";
使用 PostCSS
安装 Tailwind CSS v4 alpha 和单独的 PostCSS 插件包
npm install tailwindcss@next @tailwindcss/postcss@next
然后将我们的插件添加到您的 postcss.config.js
文件中
module.exports = { plugins: { "@tailwindcss/postcss": {}, },};
最后,在您的主 CSS 文件中导入 Tailwind
@import "tailwindcss";
使用 CLI
安装 Tailwind CSS v4 alpha 和单独的 CLI 包
npm install tailwindcss@next @tailwindcss/cli@next
接下来,在您的主 CSS 文件中导入 Tailwind
@import "tailwindcss";
最后,使用 CLI 工具编译您的 CSS
npx @tailwindcss/cli@next -i app.css -o dist/app.css