iT邦幫忙

2026 iThome 鐵人賽

DAY 3
0
自我挑戰組

30 天打造 Accessible UI Kit:從 shadcn/ui 到自己的 Design System系列 第 3

Day 3: shadcn/ui 到底是什麼?它和一般元件庫有什麼不同?

  • 分享至 

  • xImage
  •  

Day 2 建好了 React + TypeScript + Vite 的基本環境
在開始第一個component之前---
shadcn/ui 到底是什麼?

開官網,可以看到 Button、Input、Dialog、Tabs、Select...各種常見元件,看起來和一般 Component Library 沒什麼不同

官方對自己的定位卻很有意思:

This is not a component library. It is how you build your component library.

shadcn/ui 並不把自己定位成傳統的 Component Library,而是一套用來建立自己 Component Library 的方式。


一般的 Component Library 是怎麼使用的?

平常:
npm install some-ui-library

接著從套件中 import 需要的 Component:

import { Button } from "some-ui-library"

function App() {
  return <Button>儲存</Button>
}

Component 的主要實作由 Library 維護

但當客製化需求越來越多時,有時候也會開始出現:

Override Style

再包一層 Component

再補一些 CSS

為了特殊需求再包一層


shadcn/ui 的做法不太一樣

shadcn/ui 最核心的差異之一,就是 Open Code

例如加入一個 Button:

npx shadcn@latest add button

它並不是要我們之後這樣使用:

import { Button } from "shadcn-ui"

而是直接把 Button 的 Component Code 加進自己的專案。

之後使用的是:

import { Button } from "@/components/ui/button"

概念變成:

shadcn Registry


add button


我的 Project

└─ components/
└─ ui/
└─ button.tsx

button.tsx 就在自己的專案裡。
可以直接打開它、閱讀它,也可以修改它。

所以 shadcn/ui 和一般 Component Library 最大的差異之一,可以簡單理解成:
不是只把 Component 給你「使用」,而是把 Component 的 Code 交給你。


shadcn/ui 的底層又是什麼?

如果看過比較早期的 shadcn/ui 文章,可能常常會看到:

shadcn/ui 的 Component 是建立在 Radix UI 上。

這在早期確實是 shadcn/ui 很重要的架構。

不過現在已經不只有 Radix UI。

目前 shadcn/ui 支援三種 Component Base:

 shadcn/ui
              │
   ┌──────────┼──────────┐
   ▼          ▼          ▼
Base UI     Radix     React Aria

2026 年 7 月開始,新建立的 shadcn/ui Project 預設使用 Base UI。

Radix 仍然持續支援,也可以選擇 React Aria。

它們負責的事情和我們看到的視覺樣式並不完全相同

Keyboard Interaction
Focus Management
ARIA Attributes
Component State
Interaction Behavior

這些底層行為可以由 Base UI、Radix 或 React Aria 等 Component Base 提供,再由 shadcn/ui 在上面建立一致的 Component API 與 Style!


Code 是自己的,也代表維護是自己的

但當 Component Code 已經進到自己的專案,而且開始修改
這時候它就不再只是「shadcn/ui 的 Button」

自己也開始對這份 Code 負責。

例如原本 Component 已經處理好 Focus Style,客製化時卻直接寫:

button:focus {
  outline: none;
}

那最後鍵盤使用者看不到 Focus,可不能再回頭怪 shadcn/ui~

同樣地,上游 Component 有新的修改時,也不一定能像一般 npm package 一樣,更新版本就直接結束。

控制權變多,Ownership 也跟著變多。

這點對要建立自己的 UI Kit 來說,反而是一件需要先知道的事情。

和一般 Component Library 比較看看

整理一下目前理解的差異:

一般 Component Library shadcn/ui
Component Code 主要存在 Package 中 Source Code 加入自己的 Project
使用方式 從 Package Import 從自己的 Components Import
客製化 Props、Theme、Override 等 可以直接修改 Source
更新方式 跟著 Package Version 需要處理自己的 Code 與上游變更
控制權 依 Library 提供的 API 而定
維護責任 Library 維護主要實作 自己承擔更多 Ownership
主要定位 使用現成元件庫 建立自己 Component Library 的基礎

所以兩種方式並沒有誰一定比較好。

如果需求和某套 Component Library 非常接近,直接使用成熟的 Library,反而可以省下大量維護成本。

而 shadcn/ui 適合的是另一種需求:

需要一個成熟的起點,但同時希望 Component 最後真正屬於自己的 Design System。


Day 3 Done

今天還是沒有真正做出任何 Component:)

但至少搞懂了一件很重要的事情:

從 shadcn/ui 取得一個 Component 的起點,再慢慢把它變成自己的 UI Kit。

而現在下一個問題就很直接了。

當執行:

npx shadcn@latest add button

到底有哪些東西被加進 Project?

Button 裡面有哪些 Dependencies?

Variant 怎麼處理?

Style 又放在哪裡?

下一篇就真的抓一顆 Button 進來拆開看看。

Day 4: 拆開 shadcn/ui Button:一顆元件裡到底有什麼?


上一篇
Day2: 開工!用 Vite + React + TypeScript 建立 UI Kit
系列文
30 天打造 Accessible UI Kit:從 shadcn/ui 到自己的 Design System3
圖片
  熱門推薦
圖片
{{ item.channelVendor }} | {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言