6.7 KiB
6.7 KiB
DramaLing 組件設計規範
設計原則
1. 一致性 (Consistency)
- 所有組件遵循統一的設計語言
- 相同功能使用相同的交互模式
- 保持視覺元素的一致性
2. 可訪問性 (Accessibility)
- 符合 WCAG 2.1 AA 標準
- 支援鍵盤導航
- 適當的 ARIA 標籤
3. 響應式 (Responsive)
- Mobile-first 設計
- 適配各種螢幕尺寸
- 觸控友好的交互
核心組件庫
基礎組件 (Base Components)
Button 按鈕
// 變體 (Variants)
- default: 主要操作
- destructive: 危險操作
- outline: 次要操作
- secondary: 輔助操作
- ghost: 最小化操作
- link: 連結樣式
// 尺寸 (Sizes)
- sm: 小型 (h-9 px-3)
- default: 預設 (h-10 px-4)
- lg: 大型 (h-11 px-8)
- icon: 圖標按鈕 (h-10 w-10)
// 狀態 (States)
- hover: 懸停效果
- active: 點擊效果
- disabled: 禁用狀態
- loading: 載入中
Input 輸入框
// 類型 (Types)
- text: 文字輸入
- email: 郵箱輸入
- password: 密碼輸入
- search: 搜尋輸入
- textarea: 多行輸入
// 狀態 (States)
- default: 預設
- focus: 聚焦
- error: 錯誤
- disabled: 禁用
Card 卡片
// 結構
- CardHeader
- CardTitle
- CardDescription
- CardContent
- CardFooter
// 變體
- default: 預設卡片
- elevated: 陰影卡片
- outlined: 邊框卡片
業務組件 (Business Components)
FlashCard 詞卡組件
interface FlashCardProps {
word: string
translation: string
example: string
difficulty: 1 | 2 | 3 | 4 | 5
isFlipped?: boolean
onFlip?: () => void
onRate?: (rating: number) => void
}
// 設計規格
- 尺寸: 350px × 200px (桌面), 100% × 250px (手機)
- 翻轉動畫: 0.6s ease-in-out
- 陰影: 0 4px 6px rgba(0, 0, 0, 0.1)
- 圓角: 12px
StudyProgress 學習進度
interface StudyProgressProps {
totalCards: number
reviewedCards: number
newCards: number
date: Date
}
// 視覺元素
- 進度環: 圓形進度指示器
- 統計數字: 大字體顯示
- 趨勢圖標: 上升/下降箭頭
ReviewCard 複習卡片
interface ReviewCardProps {
flashcard: FlashCard
mode: 'flip' | 'quiz' | 'type'
onAnswer: (correct: boolean) => void
}
// 交互模式
- flip: 點擊翻轉查看答案
- quiz: 選擇題模式
- type: 輸入答案模式
佈局組件 (Layout Components)
Navigation 導航欄
// 桌面版
- Logo (左側)
- 主導航 (中間)
- 用戶選單 (右側)
// 手機版
- Logo (左側)
- 漢堡選單 (右側)
- 抽屜式導航
Sidebar 側邊欄
// 內容區塊
- 用戶資訊
- 主要導航
- 次要功能
- 設定連結
// 收合狀態
- 展開: 240px 寬度
- 收合: 60px 寬度 (僅圖標)
Container 容器
// 寬度斷點
- sm: 640px
- md: 768px
- lg: 1024px
- xl: 1280px
- 2xl: 1536px
// 內邊距
- 手機: 16px
- 平板: 24px
- 桌面: 32px
交互模式
載入狀態
// Skeleton 骨架屏
- 用於內容載入
- 保持佈局穩定
- 漸進式顯示
// Spinner 旋轉載入
- 用於操作等待
- 中心顯示
- 半透明遮罩
// Progress Bar 進度條
- 用於長時間操作
- 顯示具體進度
- 可取消操作
空狀態
// 設計元素
- 插圖或圖標
- 標題文字
- 描述文字
- 行動按鈕
// 場景
- 無數據
- 搜尋無結果
- 錯誤狀態
- 成功狀態
錯誤處理
// Toast 通知
- 位置: 右上角
- 持續: 3-5 秒
- 可關閉
// Alert 警告
- 內嵌顯示
- 不同級別 (info, warning, error, success)
- 可包含操作
// Error Boundary
- 全頁錯誤
- 提供重試選項
- 友好的錯誤信息
動畫規範
時長 (Duration)
--animation-fast: 150ms
--animation-base: 250ms
--animation-slow: 350ms
--animation-slower: 500ms
緩動函數 (Easing)
--ease-in: cubic-bezier(0.4, 0, 1, 1)
--ease-out: cubic-bezier(0, 0, 0.2, 1)
--ease-in-out: cubic-bezier(0.4, 0, 0.2, 1)
--ease-bounce: cubic-bezier(0.68, -0.55, 0.265, 1.55)
常用動畫
// Fade 淡入淡出
@keyframes fadeIn {
from { opacity: 0; }
to { opacity: 1; }
}
// Slide 滑動
@keyframes slideUp {
from { transform: translateY(10px); opacity: 0; }
to { transform: translateY(0); opacity: 1; }
}
// Scale 縮放
@keyframes scaleIn {
from { transform: scale(0.95); opacity: 0; }
to { transform: scale(1); opacity: 1; }
}
// Flip 翻轉
@keyframes flip {
from { transform: rotateY(0); }
to { transform: rotateY(180deg); }
}
圖標系統
圖標庫
使用 Lucide React 圖標庫
常用圖標映射
const icons = {
// 導航
home: Home,
dashboard: LayoutDashboard,
cards: Layers,
// 操作
add: Plus,
edit: Edit,
delete: Trash2,
save: Save,
// 狀態
success: CheckCircle,
error: XCircle,
warning: AlertTriangle,
info: Info,
// 學習
study: BookOpen,
review: RefreshCw,
star: Star,
trophy: Trophy,
}
尺寸規範
// 圖標尺寸
- xs: 12px
- sm: 16px
- md: 20px (預設)
- lg: 24px
- xl: 32px
表單設計
表單佈局
// 垂直佈局 (預設)
Label
Input
Helper Text / Error Message
// 水平佈局 (適合簡短標籤)
Label | Input | Helper
驗證規則
// 即時驗證
- onBlur: 失焦時驗證
- onChange: 輸入時驗證 (僅錯誤修正)
// 錯誤顯示
- 紅色邊框
- 錯誤圖標
- 錯誤信息文字
// 成功顯示
- 綠色勾選圖標
- 可選的成功信息
響應式斷點
斷點定義
/* 手機 */
@media (max-width: 639px) { }
/* 平板 */
@media (min-width: 640px) and (max-width: 1023px) { }
/* 桌面 */
@media (min-width: 1024px) { }
/* 大屏 */
@media (min-width: 1280px) { }
適配策略
- 內容優先: 確保核心內容在所有設備上可讀
- 觸控優化: 手機端增加點擊區域 (最小 44×44px)
- 佈局調整: 網格系統自動適配
- 功能降級: 複雜交互在手機端簡化
暗色模式
設計考量
- 使用 CSS 變數實現主題切換
- 保持足夠的對比度
- 避免純黑背景 (使用 #0a0a0a)
- 調整陰影透明度
實作方式
// 自動檢測系統主題
const prefersDark = window.matchMedia('(prefers-color-scheme: dark)').matches
// 手動切換
const toggleTheme = () => {
document.documentElement.classList.toggle('dark')
localStorage.setItem('theme', isDark ? 'dark' : 'light')
}
性能優化
組件優化
- 使用 React.memo 避免不必要的重渲染
- 實施虛擬滾動對於長列表
- 延遲載入非關鍵組件
- 圖片懶加載和優化
樣式優化
- 使用 Tailwind JIT 模式
- 移除未使用的 CSS
- 合併相似的樣式類
- 使用 CSS-in-JS 僅在需要時