Button triggers an action or opens a destination, with shared variants, keyboard behavior and disabled states.
01Preview
02Usage
Import Button from the shared package. Load @dg/ui/styles.css once in the application layout.
<script>
import { Button } from "@dg/ui";
let count = $state(0);
</script>
<Button label="Explore artworks" href="/artworks" />
<Button label="Add an item" variant="accent" onclick={() => count++} />
<p class="feedback" aria-live="polite">Items added: {count}</p>
<Button disabled icon={false}>Unavailable action</Button>
Use type="submit" or type="reset" inside a form for native form behavior. Without href, the default type is button, so an ordinary action does not submit its surrounding form.
03Examples
01Variants and states
02Links and custom content
03Native form
04Narrow container
04Notes
- Native HTML attributes (
id,class,style,aria-*,target,rel,name,value) and DOM callbacks such asonclick,onfocusandonkeydownare forwarded to the native button or anchor. - Forwarding uses native attribute types; unknown props are not supported. Pass class as a string and use attributes appropriate to the rendered button or link.
subtleis the default neutral variant: a prominent surface without a visible border, marked at its four corners by the shared.half-crossedaccent half-crosses, like focused fields. Hover replaces the marks with the shared inverted fill.soliduses the prominent text color as its resting background.accentuses the accent color for its background and border, with dark lettering in both themes and the shared inverted hover state.- The
childrensnippet replaceslabel. The default arrow can be removed withicon={false}, replaced with a string such asicon="+", or supplied as a decorative snippet. - Width follows the label, even inside a stack or
Sectionthat stretches its children; long labels wrap within the container. Set a width in the owning styles for a full-width button. Padding uses the shared control tokens, and both minimum dimensions follow--control-min-size.
05Parameters
| Name | Type | Default | Description |
|---|---|---|---|
label | string | "" | Button text when no children snippet is supplied. |
variant | 'subtle' | 'solid' | 'accent' | "subtle" | Neutral surface with accent corners, solid inverted surface, or filled accent surface. |
href | string | undefined | Supplying a destination renders a native link instead of a button. |
type | 'button' | 'submit' | 'reset' | "button" | Native form behavior for the button variant. |
disabled | boolean | false | Block activation and remove keyboard focus, including when href is supplied. |
icon | string | false | Snippet | "→" | Trailing decorative icon. False removes it; a string or snippet replaces the arrow. |
children | Snippet | undefined | Custom button content; replaces label. |
06Methods
| Name | Description |
|---|---|
focus() | Focus the element without scrolling. Access with bind:this. |
07Accessibility
Give textless actions an explicit accessible name with aria-label. Icons are decorative and do not supply the button's accessible name. Disabled actions, including links, cannot be activated and are excluded from keyboard navigation.
Use Tab to check visible focus, then Enter to activate a link or Enter and Space to activate a button. Hover over the variants and switch themes to inspect their states. Focus can also be restored explicitly through the component's focus() method.