shadcn-patterns
shadcn/ui component patterns including CVA variants, OKLCH theming, cn() utility, and composition. Use when adding shadcn components, building variant systems, or customizing themes.
Installation
Suivez les instructions du dépôt pour votre agent. Consultez les fichiers et dépendances avant l’installation.
Voir la source ↗GuidesInstructions
shadcn/ui Patterns
Beautifully designed, accessible components you own and customize.
Core Pattern: CVA (Class Variance Authority)
Declarative, type-safe variant definitions:
import { cva, type VariantProps } from 'class-variance-authority'
const buttonVariants = cva(
// Base classes (always applied)
'inline-flex items-center justify-center rounded-md font-medium transition-colors',
{
variants: {
variant: {
default: 'bg-primary text-primary-foreground hover:bg-primary/90',
destructive: 'bg-destructive text-destructive-foreground',
outline: 'border border-input bg-background hover:bg-accent',
ghost: 'hover:bg-accent hover:text-accent-foreground',
},
size: {
default: 'h-10 px-4 py-2',
sm: 'h-9 px-3',
lg: 'h-11 px-8',
icon: 'h-10 w-10',
},
},
compoundVariants: [
{ variant: 'outline', size: 'lg', className: 'border-2' },
],
defaultVariants: {
variant: 'default',
size: 'default',
},
}
)
// Type-safe props
interface ButtonProps
extends React.ButtonHTMLAttributes<HTMLButtonElement>,
VariantProps<typeof buttonVariants> {}
Core Pattern: cn() Utility
Combines clsx + tailwind-merge for conflict resolution:
import { clsx, type ClassValue } from 'clsx'
import { twMerge } from 'tailwind-merge'
export function cn(...inputs: ClassValue[]) {
return twMerge(clsx(inputs))
}
// Usage - later classes win
cn('px-4 py-2', 'px-6') // => 'py-2 px-6'
cn('text-red-500', condition && 'text-blue-500')
OKLCH Theming (2026 Standard)
Modern perceptually uniform color space:
:root {
--background: oklch(1 0 0);
--foreground: oklch(0.145 0 0);
--primary: oklch(0.205 0 0);
--primary-foreground: oklch(0.985 0 0);
--destructive: oklch(0.577 0.245 27.325);
--border: oklch(0.922 0 0);
--ring: oklch(0.708 0 0);
--radius: 0.625rem;
}
.dark {
--background: oklch(0.145 0 0);
--foreground: oklch(0.985 0 0);
--primary: oklch(0.985 0 0);
--destructive: oklch(0.396 0.141 25.723);
}
Why OKLCH?
- Perceptually uniform (equal steps look equal)
- Better dark mode contrast
- Wide gamut support
- Format:
oklch(lightness chroma hue)
Component Extension Strategy
Wrap, don't modify source:
import { Button as ShadcnButton } from '@/components/ui/button'
// Extend with new variants
const Button = React.forwardRef<
React.ElementRef<typeof ShadcnButton>,
React.ComponentPropsWithoutRef<typeof ShadcnButton> & {
loading?: boolean
}
>(({ loading, children, disabled, ...props }, ref) => (
<ShadcnButton ref={ref} disabled={disabled || loading} {...props}>
{loading && <Spinner className="mr-2" />}
{children}
</ShadcnButton>
))
Quick Reference
# Add components
npx shadcn@latest add button
npx shadcn@latest add dialog
# Initialize in project
npx shadcn@latest init
Key Decisions
| Decision | Recommendation |
|---|---|
| Color format | OKLCH for perceptually uniform theming |
| Class merging | Always use cn() for Tailwind conflicts |
| Extending components | Wrap, don't modify source files |
| Variants | Use CVA for type-safe multi-axis variants |
Related Skills
-
radix-primitives- Underlying accessibility primitives -
design-system-starter- Design system patterns -
biome-linting- Code quality for components
References
- CVA Variant System - CVA patterns
- OKLCH Theming - Modern color space
- cn() Utility - Class merging
- Component Extension - Extending components
- Dark Mode - next-themes integration
Exemples
Consultez les exemples du dépôt source.
Voir la source ↗Historique source
- Date d’indexation
- 2026-03-11
- Mise à jour de l’index
- 2026-03-11
- Branch
- main
Les dates concernent ce répertoire. Consultez le dépôt pour l’historique du code.
GitHub ↗chat Comments (0)
Sign in to join the discussion and leave a comment.
No comments yet. Be the first to share your thoughts!