shadcn-svelte

shadcn-svelte

熱門

管理 shadcn-svelte 元件與專案 — 新增、更新、修復、除錯、樣式設定與組合 UI。提供專案上下文、元件文件與使用範例。適用於使用 shadcn-svelte、CLI、設計系統預設或任何包含 components.json 檔案的專案。也會在「shadcn-svelte init」、「add component」或註冊表 URL 時觸發。

8994星標
559分支
更新於 2026/7/28
SKILL.md
唯讀
名稱
shadcn-svelte
描述

管理 shadcn-svelte 元件與專案 — 新增、更新、修復、除錯、樣式設定與組合 UI。提供專案上下文、元件文件與使用範例。適用於使用 shadcn-svelte、CLI、設計系統預設或任何包含 components.json 檔案的專案。也會在「shadcn-svelte init」、「add component」或註冊表 URL 時觸發。

shadcn-svelte

一個用於 Svelte 建立 UI、元件與設計系統的框架。元件透過 CLI 以原始碼形式加入使用者專案。

重要: 所有 CLI 指令請使用專案的套件執行器:npx shadcn-svelte@latestpnpm dlx shadcn-svelte@latestbunx --bun shadcn-svelte@latest — 根據專案的套件管理器選擇。以下範例使用 npx shadcn-svelte@latest,但請替換為專案適用的執行器。

當前專案上下文

讀取專案根目錄的 components.json,當需要即時檔案結構時,列出 aliases.ui 路徑(解析規則與 CLI 相同)所指定的目錄。

匯入(Svelte)

每個元件位於自己的資料夾,並包含一個 index.ts 匯出檔案。請遵循安裝文件

  • 多部分元件(dialog、select、card、field、tabs 等):import * as Dialog from "$lib/components/ui/dialog",然後使用 Dialog.ContentDialog.TitleCard.RootCard.Header 等 — 視匯出內容而定(短名稱和/或 Root as … 別名)。
  • 單一元件匯出(資料夾中只有一個有意義的元件):使用具名匯入import { Button } from "$lib/components/ui/button" 並使用 <Button>,而非 import * as Button 搭配 Button.Root{ Input }{ Badge }{ Spinner }{ Checkbox }{ Separator }{ Skeleton } 等也遵循相同模式。
import * as Dialog from "$lib/components/ui/dialog";
import { Button } from "$lib/components/ui/button";
import { Separator } from "$lib/components/ui/separator";

使用 components.json 中的實際別名(通常是 $lib/components/ui/...),而非硬編碼路徑。

原則

  1. 優先使用現有元件。 執行 npx shadcn-svelte@latest add 不帶參數以瀏覽可用元件,或在撰寫自訂 UI 前查閱元件
  2. 組合,不要重新發明。 設定頁面 = Tabs + Card + 表單控制項。儀表板 = Sidebar + Card + Chart + Table。
  3. 優先使用內建變體而非自訂樣式。 例如 variant="outline"size="sm" 等。
  4. 使用語意顏色。 例如 bg-primarytext-muted-foreground — 絕不使用原始值如 bg-blue-500

關鍵規則

這些規則始終強制執行。每個規則連結到一個包含錯誤/正確程式碼對照的檔案。

樣式與 Tailwind → styling.md

  • class 用於佈局,而非樣式。 絕不覆寫元件的顏色或字體。
  • 不使用 space-x-*space-y-* 使用 flex 搭配 gap-*。垂直堆疊使用 flex flex-col gap-*
  • 當寬高相等時使用 size-* 使用 size-10 而非 w-10 h-10
  • 使用 truncate 簡寫。 而非 overflow-hidden text-ellipsis whitespace-nowrap
  • 不要手動覆寫 dark: 顏色。 使用語意 token(bg-backgroundtext-muted-foreground)。
  • 使用 cn() 處理條件 class。 不要手寫模板字串三元運算式。
  • 不要在覆蓋層元件上手動設定 z-index Dialog、Sheet、Popover 等會自行處理堆疊。

表單與輸入 → forms.md

  • 表單使用 Field.FieldGroup + Field.Field 絕不使用原始 div 搭配 space-y-*grid gap-* 進行表單佈局。
  • InputGroup 使用 InputGroup.Input/InputGroup.Textarea 絕不在 InputGroup.Root 內使用原始 Input/Textarea
  • 輸入內部的按鈕使用 InputGroup.Root + InputGroup.Addon
  • 選項集合(2–7 個選項)使用 ToggleGroup 不要用迴圈產生 Button 並手動管理啟用狀態。
  • 使用 Field.FieldSet + Field.FieldLegend 來分組相關的核取方塊/選項按鈕。 不要使用 div 搭配標題。
  • 欄位驗證使用 data-invalid + aria-invalid data-invalid 放在 Field 上,aria-invalid 放在控制項上。禁用狀態:data-disabled 放在 Field 上,disabled 放在控制項上。

元件結構 → composition.md

  • 項目總是放在其 Group 內。 Select.ItemSelect.GroupDropdownMenu.ItemDropdownMenu.GroupCommand.ItemCommand.Group
  • 自訂觸發器。 將控制項包在 Dialog.Trigger / AlertDialog.Trigger 中,或使用 bind:open 在根元件上控制開啟狀態 — 請參閱元件文件。
  • Dialog、Sheet 和 Drawer 總是需要標題。 Dialog.TitleSheet.TitleDrawer.Title 是無障礙必備。若需視覺隱藏,使用 class="sr-only"
  • 使用完整的 Card 組合。 Card.Header/Card.Title/Card.Description/Card.Content/Card.Footer。不要把所有內容都塞進 Card.Content
  • Button 沒有 isPending/isLoadingButton 內部組合 Spinner 並加上 disabled;在 Spinner 上使用 data-icon="inline-start" / inline-end 以獲得正確間距(import { Button }import { Spinner })。
  • Tabs.Trigger 必須放在 Tabs.List 內。 絕不要直接在 Tabs 中渲染觸發器。
  • Avatar 總是需要 Avatar.Fallback 用於圖片載入失敗時。

使用元件,而非自訂標記 → composition.md

  • 優先使用現有元件而非自訂標記。 在撰寫樣式化的 div 之前,先檢查是否有對應元件。
  • 提示框使用 Alert 不要建立自訂的樣式化 div。
  • 空狀態使用 Empty 不要建立自訂的空狀態標記。
  • Toast 透過 svelte-sonner 使用 svelte-sonnertoast() 函式,搭配 UI 資料夾中的 Sonner 元件。
  • 使用 Separator 而非 <hr> 或僅有邊框 class 的 div
  • 使用 Skeleton 作為載入佔位符。不要使用自訂的 animate-pulse div。
  • 使用 Badge 而非自訂的樣式化 span。

圖示 → icons.md

  • <Button> 中的圖示使用 data-icon 在圖示上使用 data-icon="inline-start"data-icon="inline-end"
  • 元件內部的圖示不要加上尺寸 class。 元件透過 CSS 處理圖示尺寸。不要使用 size-4w-4 h-4
  • 將圖示作為元件傳入。 從設定的 iconLibrary(例如 @lucide/svelte)匯入,而非字串鍵。

CLI

  • 預設 — 從 shadcn-svelte.com 的設計系統建構器複製編碼字串,並傳遞給 npx shadcn-svelte@latest init --preset <code>

關鍵模式

以下是區分正確 shadcn-svelte 程式碼的最常見模式。邊緣情況請參閱上方連結的規則檔案。

<script lang="ts">
  import * as Field from "$lib/components/ui/field";
  import { Input } from "$lib/components/ui/input";
  import { Button } from "$lib/components/ui/button";
  import SearchIcon from "@lucide/svelte/icons/search";
  import { Badge } from "$lib/components/ui/badge";
  import * as Avatar from "$lib/components/ui/avatar";
</script>

<!-- 表單佈局:Field.FieldGroup + Field.Field,而非 div + Label。 -->
<Field.FieldGroup>
  <Field.Field>
    <Field.FieldLabel for="email">Email</Field.FieldLabel>
    <Input id="email" />
  </Field.Field>
</Field.FieldGroup>

<!-- 驗證:data-invalid 在 Field 上,aria-invalid 在控制項上。 -->
<Field.Field data-invalid>
  <Field.FieldLabel for="email">Email</Field.FieldLabel>
  <Input id="email" aria-invalid />
  <Field.FieldDescription>無效的 Email。</Field.FieldDescription>
</Field.Field>

<!-- 按鈕中的圖示:data-icon,無尺寸 class。 -->
<Button>
  <SearchIcon data-icon="inline-start" />
  搜尋
</Button>

<!-- 間距:gap-*,而非 space-y-*。 -->
<div class="flex flex-col gap-4"></div>

<!-- 等寬高:size-*,而非 w-* h-*。 -->
<Avatar.Root class="size-10">
  <Avatar.Image src="/u.png" alt="使用者" />
  <Avatar.Fallback>U</Avatar.Fallback>
</Avatar.Root>

<!-- 狀態顏色:Badge 變體或語意 token,而非原始顏色。 -->
<Badge variant="secondary">+20.1%</Badge>

元件選擇

需求 使用
按鈕/動作 Button 搭配適當的變體(import { Button }
表單輸入 InputSelectComboboxSwitchCheckboxRadioGroupTextareaInputOTPSlider
切換 2–5 個選項 ToggleGroup.Root + ToggleGroup.Item
資料顯示 TableCardBadgeAvatar
導航 SidebarNavigationMenuBreadcrumbTabsPagination
覆蓋層 Dialog(模態框)、Sheet(側邊面板)、Drawer(底部面板)、AlertDialog(確認對話框)
回饋 svelte-sonner(toast)、AlertProgressSkeletonSpinner
指令面板 Command 放在 Dialog
圖表 Chart(LayerChart)
佈局 CardSeparatorResizableScrollAreaAccordionCollapsible
空狀態 Empty
選單 DropdownMenuContextMenuMenubar
工具提示/資訊 TooltipHoverCardPopover

關鍵欄位

使用 components.json 和檔案系統 — 而非獨立的 info 指令:

  • aliases → 使用設定中的實際別名前綴(例如 $lib/),絕不硬編碼其他專案的路徑。
  • tailwind.css → 全域 CSS 檔案,主題變數存放於此。編輯此檔案進行主題調整;除非使用者已使用第二個全域檔案,否則不要新增。
  • style → 視覺處理(例如 novavega 等)以及註冊表樣式路徑。
  • iconLibrary → 決定圖示套件(@lucide/svelte@tabler/icons-svelte 等)。絕不預設為 @lucide/svelte
  • registry → CLI 取得元件的位置;預設官方註冊表為 shadcn-svelte.com
  • resolvedPaths(概念性)→ CLI 將 aliases 解析為絕對路徑;列出磁碟上的 aliases.ui 以查看已安裝的元件。

請參閱 cli.md 了解指令與旗標。

元件文件、範例與使用方式

開啟 https://shadcn-svelte.com/docs/components/<name>.md 查看文件與範例。在建立、修復、除錯或使用元件時,請先閱讀官方頁面,以遵循文件化的 API。

工作流程

  1. 取得專案上下文 — 讀取 components.json,並在需要時列出 UI 元件目錄。
  2. 先檢查已安裝的元件 — 在執行 add 之前,列出已解析 ui 路徑下的檔案。不要匯入尚未新增的元件,也不要重新新增已存在的元件(除非要更新)。
  3. 探索元件npx shadcn-svelte@latest add 不帶參數(互動式列表),或使用文件網站。
  4. 安裝或更新npx shadcn-svelte@latest add <name> 或註冊表 URL。若要從註冊表重新整理現有檔案,使用 npx shadcn-svelte@latest update(參閱 cli.md)。
  5. 修復第三方/URL 新增項目的匯入 — 從自訂註冊表 URL 新增後,檢查是否有硬編碼路徑不符合專案的 aliases。將匯入改寫為使用 components.json 中的專案 ui / lib 別名。
  6. 檢視新增的元件 — 新增後,讀取新增的檔案並驗證組合(群組、標題、驗證屬性)。將圖示匯入對齊 iconLibrary
  7. 遠端註冊表項目 — 透過 URL 新增是明確的;如果使用者想要來自未知來源的元件,請在執行 add 前確認註冊表 URL 或項目。

更新元件

使用 update 指令從註冊表拉取已安裝元件的最新版本。在 update 後使用 git diff 檢視變更。

  1. 提交或暫存本地工作。
  2. 執行 npx shadcn-svelte@latest update [component]--all
  3. 如果曾自訂檔案,解決合併衝突。
  4. 未經使用者明確同意,絕不在 add 上使用 --overwrite,因為這會破壞有意的編輯。

快速參考

# 在專案中初始化 shadcn-svelte。
npx shadcn-svelte@latest init

# 使用文件網站建構器中的預設字串初始化。
npx shadcn-svelte@latest init --preset <code>

# 新增元件(不帶名稱時為互動模式)。
npx shadcn-svelte@latest add
npx shadcn-svelte@latest add button card dialog
npx shadcn-svelte@latest add --all

# 更新已安裝的元件。
npx shadcn-svelte@latest update button
npx shadcn-svelte@latest update --all --yes

# 建立自訂註冊表(註冊表作者)。
npx shadcn-svelte@latest registry build

註冊表: 預設為 https://shadcn-svelte.com/registry — 如有需要可在 components.json 中覆寫。
文件: shadcn-svelte.com

詳細參考

  • rules/forms.md — Field.FieldGroup、Field.Field、InputGroup、ToggleGroup、Field.FieldSet、驗證狀態
  • rules/composition.md — 群組、覆蓋層、Card、Tabs、Avatar、Alert、Empty、Toast、Separator、Skeleton、Badge、按鈕載入
  • rules/icons.md — data-icon、圖示尺寸、傳入圖示元件
  • rules/styling.md — 語意顏色、變體、class、間距、尺寸、truncate、深色模式、cn()、z-index
  • cli.md — 指令、旗標、註冊表
  • customization.md — 主題、CSS 變數、擴充元件