Catalyst 隆重推出:一套现代化的 React UI 工具包

Adam Wathan
Overview of components included in Catalyst

今天就是这个日子 - 我们刚刚发布了 Catalyst 的第一个开发预览版,正好赶上你们的假期 hacking 环节。

¥Today's the day — we just published the first development preview of Catalyst, just in time for your holiday hacking sessions.

Catalyst 是我们第一个完全组件化、功能齐全的应用 UI 套件 - 真正的 React 组件,拥有精心设计的 API,它们相互依存,从而创建出一个真正的组件架构,就像我们在实际应用中所做的那样。

¥Catalyst is our first fully-componentized, batteries-included application UI kit — real React components with thoughtfully designed APIs that build on each other to create a real component architecture, the same way we'd do it in a real application.

查看 现场演示,阅读 documentation。如果你是 Tailwind UI All-Access 客户,请查看 下载 并在今天的新项目中试用。

¥Check out the live demo, read the documentation, and if you're a Tailwind UI All-Access customer, download it and try it out in a new project today.

Catalyst 目前处于开发预览阶段,未来还会有更多功能,但我们今天就发布它,以便你可以立即试用,因为我们会继续构建新的组件,并不断探索提升体验的方法。

¥Catalyst is currently in development preview and there's a lot more to come, but we're releasing it today so you can play with it right away as we continue to build new components and find ways to make it an even better experience.


你的组件,而非我们的(Your components, not ours)

¥Your components, not ours

借助 Catalyst,我们着手构建一个 UI 套件,让未来的 Stripe 或 Linear 乐于使用它来构建他们的产品 - 这些团队痴迷于设计,希望拥有自己的 UI 组件,并且永远不会选择现成的库。

¥With Catalyst, we set out to build a UI kit that tomorrow's Stripe or Linear would feel good about using to build their products — design-obsessed teams who want to own their UI components, and would never choose an off-the-shelf library.

因此,它不是你安装的依赖,而是下载源代码并将组件复制到你自己的项目中,在那里它们成为你自己的组件系统的起点:

¥So it's not a dependency you install, instead you download the source and copy the components into your own project where they become the starting point for your own component system:

想要更改按钮的边框半径吗?只需打开 button.tsx 并更改一些类即可。你无需提交 GitHub 问题并试图说服我们公开新的配置选项。

¥Want to change the border radius on your buttons? Just open button.tsx and change some classes. You don't need to open a GitHub issue and try to convince us to expose a new configuration option.

Catalyst 就是 "消失的 UI Kit" - 安装六个月后,你几乎会忘记最初的组件不是你自己构建的。

¥Catalyst is a "disappearing UI kit" — six months after you've installed it, you should almost forget it wasn't you who built the original components.


设计在于细节(Design is in the details)

¥Design is in the details

在这样的项目中获得正确的视觉样式非常困难。我们设定了几个目标:

¥Getting the visual style right on a project like this is hard. We went into it with a few goals:

  • 保持竞争力 - 我们希望设计出的产品能够与当今网络上一些最优秀的界面相媲美。

    ¥Be competitive — we wanted to design something that could hold its own next to some of the nicest interfaces on the web today.

  • 保持永恒 - 我们不想设计出一款在 6 个月后就会显得过时的产品,因为它过于依赖特定的趋势。

    ¥Be timeless — we didn't want to design something that would look dated in 6 months because it leaned too hard into specific trends.

  • 保持高效 - 无论我们设计什么,都必须让真实用户感到快速高效,而不仅仅是在 Dribbble 上看起来很棒。

    ¥Be productive — whatever we designed needed to feel fast and efficient to real users, not just look great in a Dribbble shot.

我们付出了很多努力,也进行了很多权衡,但我真的很喜欢我们最终的成果:

¥It took a lot of work and there were a lot of trade-offs to balance, but I'm really in love with where we ended up:

为了保持竞争力,我们在很多细节上投入了大量精力,例如下拉菜单上的微妙背景模糊效果、完善表单控件上阴影和边框的融合方式,以及在对话框和切换开关等元素中巧妙地运用动画。

¥To be competitive, we invested in lots of details like subtle backdrop blurs on dropdown menus, perfecting the way shadows and borders blend with each other on form controls, and thoughtful use of animation in things like dialogs and toggle switches.

为了保持经典,我们努力在扁平化和拟物化设计之间取得平衡,并赋予其恰到好处的深度,确保即使潮流稍有变化,我们的组件也能保持美观。

¥To be timeless, we tried to strike the right balance between flat and skeuomorphic design, with just enough depth cues that our components will look great even if the trends change a bit in either direction.

我们还从浏览器中汲取灵感,使用了不带偏见的蓝色焦点环,以避免选择可能很快就会过时的处理方式。

¥We also took inspiration from the browser, and used unopinionated blue focus rings to avoid picking a treatment that might soon look out of fashion.

为了提高效率,我们仔细设计,确保留有足够的空白,但 UI 仍然足够密集,可以在屏幕上显示大量信息。

¥To be productive, we worked carefully to make sure there was still plenty of whitespace, but that the UI was still dense enough to fit plenty of information on the screen.

我们还将过渡和动画的使用限制在重要的地方,并尽量保持它们的快速运行,让你不会感觉在 UI 上等待。

¥We also limited our use of transitions and animations only to places where it felt important, and even then tried to keep them fast so it never feels like you're waiting on the UI.

Catalyst 还完全支持暗黑模式,你使用 Catalyst 组件构建的任何内容都会自动在亮黑模式之间切换。

¥Catalyst also ships with full dark mode support, and anything you build with Catalyst components automatically adapts between light and dark modes.

虽然不太明显,但为了使内容在暗黑模式下看起来最佳,我们不得不更改大量小细节,例如调整阴影、将外圈更改为内圈以模拟光照变化等等。

¥It's not obvious, but there are a ton of little details we had to change to make things look their best in dark mode, like adjusting shadows, changing outer rings to inner rings to mimic the change in lighting, and more.


基于 HTML 建模(Modeled after HTML)

¥Modeled after HTML

我们花了很多时间开发组件 API,努力让它变得非常容易上手并立即可用,同时又不影响灵活性。

¥We spent a lot of time working on the component APIs, trying very hard to make things really easy to drop in and use right away, without compromising on flexibility.

UI 库通常会使用如下 API:

¥It's common for UI libraries to use APIs like this:

JSX
function Example() {
return (
<TextField
name="product_name"
label="Product name"
description="Use the name you'd like people to see in their cart."
/>
);
}

但是,由于所有 props 都存在于同一个组件中,因此,像在 <input> 元素本身上添加 class 这样的操作开始变得困难。

¥But with all the props living on the same component, it starts to get difficult to do things like add a class just to the <input> element itself.

最终,我们开发了与 HTML 高度相似的 API,单个组件很少会渲染多个元素。

¥Ultimately that led us to APIs that closely mirrored HTML, where it's rare that a single component renders more than one element.

例如,使用 Catalyst 创建文本字段如下所示:

¥Creating a text field with Catalyst looks like this for example:

import { Description, Field, Label } from "@/components/fieldset";
import { Input } from "@/components/input";
function Example() {
return (
<Field>
<Label>Product name</Label>
<Description>Use the name you'd like people to see in their cart.</Description>
<Input name="product_name" />
</Field>
);
}

通过保持这样的可组合性,可以很容易地执行诸如限制输入宽度之类的操作,而无需限制任何其他元素的宽度:

¥By keeping things composable like this, it makes it really easy to do things like constrain the width of the input, without constraining the width of any of the other elements:

import { Description, Field, Label } from "@/components/fieldset";
import { Input } from "@/components/input";
function Example() {
return (
<Field>
<Label>Product name</Label>
<Description>Use the name you'd like people to see in their cart.</Description>
<Input name="product_name" />
<Input name="product_name" className="max-w-sm" />
</Field>
);
}

它还可以轻松地将描述移动到输入框下方,而不是上方:

¥It also makes it easy to move the description below the input, instead of above:

import { Description, Field, Label } from '@/components/fieldset'
import { Input } from '@/components/input'
function Example() {
return (
<Field>
<Label>Product name</Label>
<Description>Use the name you'd like people to see in their cart.</Description>
<Input name="product_name" className="max-w-sm" />
<Description>Use the name you'd like people to see in their cart.</Description>
</Field>
)
}

为了找到让这些 API 正常工作的正确方法,我们进行了大量的实验,尤其是在为正确的子组件添加布局样式等细节方面,但最终的回报是值得的,这些组件使用起来真的非常愉快。

¥It took a lot of experimenting to figure out the right way to make these APIs work, especially around details like adding layout styles to the right children, but the payoff was worth it, and these components are really a delight to use.


由下一代 Headless UI 提供支持(Powered by the next generation of Headless UI)

¥Powered by the next generation of Headless UI

我们于 2020 年夏季发布了 Headless UI 的第一个版本,但由于我们一直专注于 Tailwind CSS 本身的工作,距离上次重要功能发布已经过去了一年多。

¥We released the first version of Headless UI back in the summer of 2020, but it's been just over a year now since the last significant feature release because of all the work we've been focused on with Tailwind CSS itself.

Catalyst 是我们再次尝试 Headless UI 的绝佳机会,我们很快找到了许多改进项目的方法,从而简化了 Catalyst 本身的代码。

¥Catalyst was the perfect excuse to get our hands dirty with Headless UI again, and we quickly found lots of ways to improve the project to simplify the code in Catalyst itself.

我们刚刚发布了 Headless UI v2.0.0-alpha.1,其中包含大量新内容:

¥We just published Headless UI v2.0.0-alpha.1, which includes a ton of new stuff:

  • 内置锚点定位 - 使用 浮动 UIMenuListbox 等组件现在可以自动将其弹出窗口锚定到触发器上,并根据需要适应视口的变化。

    ¥Built-in anchor positioning — using Floating UI, components like Menu, Listbox, and more can now automatically position their popovers to be anchored to their trigger, adapting as needed to changes in the viewport.

  • Headless 复选框组件 — 我们添加了一个 Headless Checkbox 组件来补充我们现有的 RadioGroup 组件,从而可以轻松构建完全自定义的复选框控件。

    ¥Headless checkbox component — we've added a headless Checkbox component to complement our existing RadioGroup component, making it easy to build totally custom checkbox controls.

  • HTML 表单组件 - 我们添加了 InputSelectTextareaLabelDescriptionFieldsetLegend 组件,用于处理连接表单字段所需的所有 ID 生成和 aria-* 属性映射。

    ¥HTML form components — we've added Input, Select, Textarea, Label, Description, Fieldset, and Legend components that handle all of the ID generation and aria-* attribute mapping you need to do to connect form fields together.

  • 改进了悬停和焦点可见检测 - 使用来自强大的 React Aria 库的钩子,Headless UI 现在为你的控件添加了更智能的 data-hoverdata-focus 属性,这些属性在不同设备上的行为比原生伪类更加一致。

    ¥Improved hover and focus-visible detection — using hooks from the awesome React Aria library under the hood, Headless UI now adds smarter data-hover and data-focus attributes to your controls that behave more consistently across different devices than the native pseudo-classes.

  • 组合框列表虚拟化 - 下一个版本的 Headless UI 现在可以处理巨大的组合框选项列表,而不会出现性能问题。

    ¥Combobox list virtualization — the next version of Headless UI can now handle giant lists of combobox options with no performance issues.

...还有许多其他改进即将推出,包括日期选择器、工具提示等等。

¥...with plenty of other improvements to come, including a date picker, tooltips, and more.

目前,在早期 alpha 测试阶段,这些改进仅适用于 React,但我们计划在 v2.0 版本发布之前,将所有改进也引入 Vue。

¥These improvements are React-only for now during this early alpha period, but we plan to bring all of these improvements to Vue as well before tagging v2.0.

我们很快就会发布这些内容的文档,但我们还是忍不住要在假期前发布 Catalyst,即使这意味着 Headless UI 文档要晚几天发布。

¥We'll have documentation published for this stuff really soon, but couldn't resist getting Catalyst out before the holidays, even if it meant publishing the Headless UI docs a few days later.


试用(Try it out)

¥Try it out

Catalyst 是面向所有 Tailwind UI 全面访问 用户的免费更新,你可以立即升级到 下载 并开始使用这个首个版本。

¥Catalyst is a free update for all Tailwind UI All-Access customers, and you can download it and start playing with this first release today.

为了收集所有信息,我们付出了更多努力。我们渴望得到反馈和改进方法,所以用它构建一些东西,并告诉我们你的想法。

¥More work went into getting everything we're releasing today just right than you could ever imagine, but we're eager for feedback and ways it could be improved, so build some stuff with it and let us know what you think.

我们将利用假期的几周时间进行休整,但新年伊始,我们将立即回归 Catalyst,开发新的组件,例如应用布局、组合框、命令面板、工具提示等等。

¥We're going to take a couple weeks to recharge over the holidays, but we'll be right back into Catalyst in the new year, working on new components like application layouts, comboboxes, command palettes, tooltips, and more.

TailwindCSS v4.1 中文网 - 粤ICP备13048890号