狀態與回饋系統

描邊膠囊步驟條

一條 SVG 描邊先畫出膠囊外框,再讓內部的步驟膠囊逐一點亮推進,適合設定精靈、任務進度與上線流程。

把多步驟流程收進一顆膠囊裡。進場時一條描邊從左側中間起筆、順時針畫出膠囊外框,描完後內部的步驟 pill 依序淡入;推進時已完成的步驟填上強調色並描出白勾,進行中的步驟帶著細微的呼吸光暈,同時第二條強調色描邊沿著外框前進到完成比例——外框本身就是一條進度條。精簡模式下只有進行中的步驟展開顯示文字,其餘只留圖示或序號。步驟索引支援受控/非受控雙模式,也能自動依序推進。

把這個效果裝進你的專案

在專案資料夾執行指令,CLI 會加入原始碼與依賴套件,再依下方使用範例引用元件。

npx webberui@latest add drawn-capsule-stepper

還沒有專案,或安裝遇到問題?看快速開始 →

Playground

即時調整 props、程式碼片段同步更新——直接試出你要的樣子再複製。

900
1400
編輯中的呼叫預設屬性
<DrawnCapsuleStepper/>

完整範例包含預覽的排版與資料。先安裝元件,再把範例檔貼入你的專案。

安裝

npx webberui@latest add https://webberui.com/r/drawn-capsule-stepper.json

或在 components.json 設定 registries 後,改用 @webberui/drawn-capsule-stepper 安裝。

使用

import { Package, Rocket, Store } from "lucide-react";
import { DrawnCapsuleStepper } from "@/components/ui/drawn-capsule-stepper";

const steps = [
  { id: "create", label: "建立商店", icon: <Store /> },
  { id: "upload", label: "上傳商品", icon: <Package /> },
  { id: "launch", label: "開始營業", icon: <Rocket /> },
];

// 非受控 + 自動推進
<DrawnCapsuleStepper steps={steps} autoPlay />

// 受控:由外部按鈕控制目前步驟
const [current, setCurrent] = React.useState(0);

<DrawnCapsuleStepper
  steps={steps}
  current={current}
  onCurrentChange={setCurrent}
  compact={false}
  clickable
/>

Props

Prop型別預設值說明
stepsDrawnCapsuleStep[]—步驟清單,建議 3–6 個
currentnumber—受控的進行中步驟索引(0 起算);等於 steps.length 表示全部完成
defaultCurrentnumber0非受控模式的初始步驟索引
onCurrentChange(current: number) => void—步驟改變時回呼,參數為新的步驟索引
autoPlaybooleanfalse自動依序推進步驟,走完後回到第一步重播
intervalnumber1400自動推進的間隔(毫秒)
trigger"mount" | "inView""inView"描邊進場時機:掛載後立即,或捲動進入視窗時
drawDurationnumber900外框描邊的時長(毫秒),寫入 --wb-drawn-capsule-draw
compactbooleantrue精簡模式:只有進行中的步驟展開顯示文字,其餘只顯示圖示或序號
clickablebooleanfalse允許點擊已完成的步驟跳回該步
accentstring"#3b82f6"強調色(已完成底色、進度描邊、進行中外框),寫入 --wb-drawn-capsule-accent
classNamestring—透傳到最外層容器

DrawnCapsuleStep

欄位型別預設值說明
idstring—步驟唯一識別,作為 React key
labelstring—步驟名稱;compact 模式下只有進行中的步驟會顯示文字
iconReact.ReactNode—自訂圖示;未提供時顯示步驟序號

細節

  • 外框是自組的膠囊 <path>(圓角 = 高度的一半),而不是 <rect rx>:這樣描邊才能從左側中間起筆、順時針繞行。容器尺寸由 ResizeObserver 量測,寬度改變時路徑跟著重算。
  • 描邊以 pathLength 0→1 畫出,easing 為 [0.65, 0, 0.35, 1];描完後步驟 pill 以 60ms 間隔依序淡入。進度描邊在這之後才開始,沿同一條路徑以 spring(stiffness 120、damping 20)前進到「已完成數 ÷ 總步驟數」。
  • 進行中步驟的寬度變化以 layout 動畫展開,已完成步驟的白勾以 240ms 描出。
  • CSS 變數:--wb-drawn-capsule-draw(預設 900ms,同 drawDuration)、--wb-drawn-capsule-stagger(60ms)、--wb-drawn-capsule-accent(同 accent),可在外層覆寫顏色以跟上你的主題。
  • autoPlay 從描邊與淡入結束後才開始計時;走到全部完成後,再等一個 interval 回到第一步。

可及性

  • 步驟容器為 role="list"、aria-label="設定進度",每個步驟為 role="listitem";進行中的步驟設定 aria-current="step"
  • 已完成步驟附有僅螢幕閱讀器可讀的「已完成」;精簡模式下隱藏的標籤仍以 sr-only 文字保留,不會遺失名稱
  • clickable 時已完成步驟是 type="button" 的原生按鈕,可用 Tab 聚焦、Enter/空白鍵觸發,並有 focus-visible 外框
  • 步驟變化寫入 aria-live="polite" 區域,例如「第 2 步,共 4 步:上傳商品」
  • 外框 SVG 與圖示、序號、脈動光暈皆設 aria-hidden
  • 使用者系統開啟「減少動態效果」時,外框直接出現、進度描邊直接跳到目標位置、步驟不淡入也沒有脈動光暈