Button
React button component with multiple variants, sizes, and states. Perfect for forms, navigation, and user actions with full accessibility support.
Need users to take action? Buttons are the foundation of every interface - from simple clicks to complex form submissions. The Button component handles everything from primary calls-to-action to subtle icon buttons.
Built with Radix UI Slot for maximum flexibility and class-variance-authority for type-safe styling.
npx shadcn@latest add button
Why buttons work everywhere
Users expect buttons to behave consistently across every app and website:
- Visual hierarchy - Primary, secondary, and destructive actions are instantly recognizable
- Touch and click targets - Properly sized for both mouse and finger interaction
- Keyboard navigation - Tab, Enter, and Space work exactly as expected
- Loading states - Clear feedback during async operations
- Accessibility first - Screen readers announce button purpose and state
- Flexible composition - Work as links, form submits, or custom components
- Consistent spacing - Icons and text align perfectly
Common button patterns you'll build
All visual variants
Six different styles for every use case:
Secondary actions
Subtle styling for less important actions:
Destructive actions
Clear warning for delete, remove, or cancel operations:
Outline style
Bordered buttons that work great on colored backgrounds:
Ghost buttons
Minimal styling that appears on hover and focus:
Link appearance
Button functionality with link styling:
Different sizes
From compact to prominent sizing:
Icon-only buttons
Compact buttons for toolbars and tight spaces:
Text with icons
Combining text and visual indicators:
Loading states
Feedback during async operations:
API Reference
Button
The main button component built on Radix UI Slot with comprehensive variant and size options.
Prop | Type | Default | Description |
---|---|---|---|
variant | "default" | "destructive" | "outline" | "secondary" | "ghost" | "link" | "default" | Visual style variant for different use cases |
size | "default" | "sm" | "lg" | "icon" | "default" | Size of the button for different contexts |
asChild | boolean | false | Render as a child component (e.g., Next.js Link) using Radix UI Slot |
disabled | boolean | false | Disables the button and applies disabled styling |
type | "button" | "submit" | "reset" | "button" | HTML button type for form integration |
onClick | (event: MouseEvent) => void | - | Click event handler |
className | string | - | Additional CSS classes for custom styling |
children | React.ReactNode | - | Button content including text, icons, and other elements |
Button Variants
Variant | Use Case | Appearance |
---|---|---|
"default" | Primary actions, main CTAs | Solid background with primary color |
"secondary" | Secondary actions, alternative options | Muted solid background |
"destructive" | Delete, remove, dangerous actions | Red background with warning styling |
"outline" | Secondary actions on colored backgrounds | Transparent with border |
"ghost" | Subtle actions, hover reveals background | Transparent, minimal styling |
"link" | Navigation that should look like links | Underlined text styling |
Button Sizes
Size | Use Case | Dimensions |
---|---|---|
"sm" | Compact spaces, secondary actions | Height: 32px, smaller padding |
"default" | Standard use cases | Height: 40px, balanced padding |
"lg" | Prominent actions, hero sections | Height: 44px, larger padding |
"icon" | Icon-only buttons | 40x40px square for single icons |
States and Styling
The button automatically handles various states:
State | Description | Styling |
---|---|---|
hover | Mouse hover interaction | Darker background, smooth transition |
focus-visible | Keyboard focus | Ring outline for accessibility |
active | Click/press state | Slightly pressed appearance |
disabled | Non-interactive state | Reduced opacity, no pointer events |
aria-invalid | Form validation error | Red border and ring |
Button best practices
What makes buttons feel intuitive and accessible:
- Clear action words - "Save", "Delete", "Submit" instead of "OK" or "Click here"
- Consistent sizing - Use the same size for buttons at the same importance level
- Visual hierarchy - Primary, secondary, ghost, and destructive variants guide users
- Touch targets - Minimum 44px height for mobile accessibility
- Loading feedback - Show progress during async operations
- Keyboard support - Tab, Enter, and Space work perfectly
- Icon alignment - Icons and text line up naturally with proper spacing
- Disabled states - Clear visual feedback when actions aren't available