Button
Clickable button with multiple variants and sizes.
$ npx @beaket/ui add buttonSource
import { Button } from "@/components/ui/button";
export default function AllVariantsExample() {
return (
<div className="flex flex-wrap gap-2">
<Button variant="primary">Primary</Button>
<Button variant="secondary">Secondary</Button>
<Button variant="destructive">Destructive</Button>
<Button variant="outline">Outline</Button>
<Button variant="ghost">Ghost</Button>
<Button variant="link">Link</Button>
<Button variant="success">Success</Button>
<Button variant="warning">Warning</Button>
</div>
);
}Examples
All Sizes
Source
import { Button } from "@/components/ui/button";
export default function AllSizesExample() {
return (
<div className="flex items-center gap-2">
<Button size="sm">Small</Button>
<Button size="md">Medium</Button>
<Button size="lg">Large</Button>
<Button size="icon">+</Button>
</div>
);
}All States
primary
Rest
Held-open
Pressed
Disabled
Loading
outline
Rest
Held-open
Pressed
Disabled
Loading
Source
import { Button } from "@/components/ui/button";
import type { ReactNode } from "react";
function StateCell({ label, children }: { label: string; children: ReactNode }) {
return (
<div className="flex flex-col items-center gap-2">
{children}
<span className="text-fg-subtle text-xs">{label}</span>
</div>
);
}
function StateRow({
variant,
pressedClassName,
}: {
variant: "primary" | "outline";
pressedClassName: string;
}) {
return (
<div className="flex flex-col gap-3">
<span className="text-fg-muted text-sm font-medium">{variant}</span>
<div className="flex flex-wrap items-start gap-6">
<StateCell label="Rest">
<Button variant={variant}>Button</Button>
</StateCell>
<StateCell label="Held-open">
<Button variant={variant} data-state="open">
Button
</Button>
</StateCell>
<StateCell label="Pressed">
<Button
variant={variant}
className={pressedClassName}
style={{ boxShadow: "none", transform: "translate(1px, 1px)" }}
>
Button
</Button>
</StateCell>
<StateCell label="Disabled">
<Button variant={variant} disabled>
Button
</Button>
</StateCell>
<StateCell label="Loading">
<Button variant={variant} loading>
Button
</Button>
</StateCell>
</div>
</div>
);
}
export default function AllStatesExample() {
return (
<div className="flex flex-col gap-8">
<StateRow variant="primary" pressedClassName="bg-bg-emphasis-active" />
<StateRow variant="outline" pressedClassName="bg-bg-active" />
</div>
);
}Props
| Name | Type | Default | Description |
|---|---|---|---|
| variant | undefined | link | primary | danger | destructive | outline | secondary | ghost | success | warning | — | Button style. Prefer danger for the semantic role; destructive remains an alias. |
| size | undefined | sm | md | lg | icon | md | sm | md | lg | icon. Button size |
| loading | boolean | undefined | — | Shows a loading spinner and disables the button. Left unset on a `type="submit"` button inside a `<form>`, it follows the form's own pending state. Set it explicitly to override that either way. |
| loadingLabel | string | undefined | Loading | Accessible name of the loading spinner. Defaults to Loading. |
| asChild | boolean | undefined | false | Merges props onto the immediate child element instead of rendering a button |