Button
Neo-brutalist button component supporting 9 variants, 4 sizes + icon mode, loading state, and asChild composition support.
Demo
变体
尺寸
状态
提交按钮
装饰形态(flair)
Installation
pnpm dlx brutx-vue@latest add buttonUsage
<script setup>
import { Button } from 'brutx-ui-vue'
</script>
<template>
<Button variant="primary" size="default">
Click me
</Button>
</template>Loading State
<script setup>
import { ref } from 'vue'
import { Button } from 'brutx-ui-vue'
const isLoading = ref(false)
async function handleSubmit() {
isLoading.value = true
await new Promise(resolve => setTimeout(resolve, 2000))
isLoading.value = false
}
</script>
<template>
<Button variant="primary" :loading="isLoading" @click="handleSubmit">
Save Changes
</Button>
</template>Disabled State
<script setup>
import { Button } from 'brutx-ui-vue'
</script>
<template>
<Button variant="primary" disabled>
Disabled
</Button>
</template>Submit Button and Pending Text
Set type="submit" to render the button as a form submit button. Combined with loading and pendingText, the button displays a pending text (replacing the slot content) during submission. When pendingText is not provided, it falls back to the i18n default (submitButton.submitting):
<script setup>
import { ref } from 'vue'
import { Button } from 'brutx-ui-vue'
const isLoading = ref(false)
async function handleSubmit() {
isLoading.value = true
await new Promise(resolve => setTimeout(resolve, 2000))
isLoading.value = false
}
</script>
<template>
<form @submit.prevent="handleSubmit">
<Button type="submit" variant="primary" :loading="isLoading" pending-text="Saving...">
Save
</Button>
</form>
</template>The pending text is shown and the slot content is hidden only when type="submit" and loading=true. In all other cases, the slot content renders normally and the loading icon still appears.
asChild
Use asChild to render button styles onto a custom element (e.g., a router link):
<script setup>
import { Button } from 'brutx-ui-vue'
import { RouterLink } from 'vue-router'
</script>
<template>
<Button as-child>
<RouterLink to="/about">About</RouterLink>
</Button>
</template>Glitch Effect
Button includes effect="glitch" for the glitch tear animation.
<template>
<Button
effect="glitch"
variant="primary"
glitch-trigger="click"
glitch-speed="fast"
glitch-direction="both"
data-text="GLITCH"
>
GLITCH
</Button>
</template>Note: when building a glitch button directly with the exported
buttonVariants({ effect: 'glitch' }), passglitchSpeedandglitchDirectionexplicitly — themedium/horizontaldefaults are provided by the<Button>component, not by the raw utility function.
With the default effect="none", Button creates no effect media listeners, timers, or text synchronization. Both autoplay and the exposed play() method respect this switch. Glitch playback stops while disabled, loading, or reduced motion is enabled. KeepAlive deactivation and unmount release resources; activation reads the current motion preference before resuming.
Variants
| Variant | Description |
|---|---|
default | Background color with hard shadow |
primary | Primary (coral) background |
secondary | Secondary (mint) background |
accent | Accent (yellow) background |
danger | Destructive (red) background with white text |
success | Success (green) background |
outline | Transparent background with inversion on hover |
ghost | No border or shadow with subtle hover effect |
link | No border or shadow with underline on hover |
<template>
<Button variant="primary">Primary variant</Button>
</template>Decorative Flair
The flair dimension composes orthogonally with color variants, offering three mechanical texture modes:
| Flair | Description |
|---|---|
none | Default; outputs no extra decoration classes |
stacked | Multi-layer rainbow hard shadow with matched 1.5x press displacement |
hazard | Warning stripes surround a solid yellow label with black text, preserving text contrast on hover |
ticket | Ticket tear — semicircle notches at the left/right midpoints |
<template>
<Button variant="primary" flair="stacked">Stacked shadow</Button>
<Button variant="accent" flair="hazard">Hazard stripes</Button>
<Button variant="default" flair="ticket">Ticket notch</Button>
</template>Sizes
| Size | Height | Padding | Font Size |
|---|---|---|---|
sm | h-9 | px-3 py-1 | text-sm |
default | h-11 | px-5 py-2 | text-base |
lg | h-14 | px-8 py-3 | text-lg |
xl | h-16 | px-10 py-4 | text-xl |
icon | h-11 w-11 | p-0 | — |
API Reference
| Name | Type | Default | Description |
|---|---|---|---|
variant | "accent" | "danger" | "default" | "ghost" | "link" | "outline" | "primary" | "secondary" | "success" | undefined | "default" | Controls the button’s visual variant, including its color and interaction-state styles. |
DetailsDeclared typeNonNullable<"default" | "ghost" | "primary" | "secondary" | "success" | "danger" | "accent" | "outline" | "link" | null | undefined> | undefined Literal values
Default value details
Sourcepackages/ui/src/components/button/Button.vue | |||
size | "default" | "icon" | "lg" | "sm" | "xl" | undefined | "default" | Controls the button dimensions and padding. Use icon for a square icon button. |
DetailsDeclared typeNonNullable<"default" | "lg" | "sm" | "xl" | "icon" | null | undefined> | undefined Literal values
Default value details
Sourcepackages/ui/src/components/button/Button.vue | |||
flair | "none" | "stacked" | "hazard" | "ticket" | undefined | "none" | Adds a decorative treatment such as stacked shadows, hazard stripes, or a ticket notch. It composes independently with the color variant. |
DetailsDeclared type"none" | "stacked" | "hazard" | "ticket" | undefined Literal values
Default value details
Sourcepackages/ui/src/components/button/Button.vue | |||
asChild | boolean | undefined | false | Merges the button props, styles, and interaction behavior into its single child element. |
DetailsDeclared typeboolean | undefined Literal values
Default value details
Sourcepackages/ui/src/components/button/Button.vue | |||
type | "button" | "submit" | "reset" | undefined | undefined | Sets the native button type. When omitted, the rendered native button uses the browser’s default button behavior. |
DetailsDeclared type"button" | "submit" | "reset" | undefined Literal values
Default value details
Sourcepackages/ui/src/components/button/Button.vue | |||
loading | boolean | undefined | false | Shows a loading icon and places the button in its disabled state. |
DetailsDeclared typeboolean | undefined Literal values
Default value details
Sourcepackages/ui/src/components/button/Button.vue | |||
disabled | boolean | undefined | false | Disables the button’s normal user interaction. |
DetailsDeclared typeboolean | undefined Literal values
Default value details
Sourcepackages/ui/src/components/button/Button.vue | |||
pendingText | string | undefined | undefinedRuntime fallback: | Text used as the default slot fallback while a submit button is loading. Explicit slot content takes precedence. |
DetailsDeclared typestring | undefined Default value details
Sourcepackages/ui/src/components/button/Button.vue | |||
pressed | boolean | undefined | undefined | Sets the pressed state for a toggle button and is reflected through aria-pressed. |
DetailsDeclared typeboolean | undefined Literal values
Default value details
Sourcepackages/ui/src/components/button/Button.vue | |||
expanded | boolean | undefined | undefined | Sets whether the content controlled by the button is expanded and is reflected through aria-expanded. |
DetailsDeclared typeboolean | undefined Literal values
Default value details
Sourcepackages/ui/src/components/button/Button.vue | |||
effect | "none" | "glitch" | undefined | "none" | Enables or disables the glitch visual effect. The effect is disabled by default. |
DetailsDeclared type"none" | "glitch" | undefined Literal values
Default value details
Sourcepackages/ui/src/components/button/Button.vue | |||
glitchTrigger | GlitchTrigger | undefined | "hover" | Selects how the glitch effect starts: on hover, on click, on autoplay, or never. It applies only when effect="glitch". |
DetailsDeclared typeGlitchTrigger | undefined Literal values
Referenced types GlitchTrigger Type definition — GlitchTriggerexport type GlitchTrigger = 'hover' | 'click' | 'autoplay' | 'none' Default value details
Sourcepackages/ui/src/components/button/Button.vue | |||
glitchInterval | number | undefined | 3000 | Sets the autoplay interval for the glitch effect in milliseconds. It applies only when glitchTrigger="autoplay" and is clamped to the effect timing limits. |
DetailsDeclared typenumber | undefined Default value details
Sourcepackages/ui/src/components/button/Button.vue | |||
glitchSpeed | ButtonGlitchSpeed | undefined | "medium" | Controls the playback speed of the glitch animation. |
DetailsDeclared typeButtonGlitchSpeed | undefined Literal values
Referenced types ButtonGlitchSpeed Type definition — ButtonGlitchSpeedtype ButtonGlitchSpeed = NonNullable<ButtonVariantProps['glitchSpeed']> Default value details
Sourcepackages/ui/src/components/button/Button.vue | |||
glitchDirection | ButtonGlitchDirection | undefined | "horizontal" | Controls the direction of the glitch distortion. |
DetailsDeclared typeButtonGlitchDirection | undefined Literal values
Referenced types ButtonGlitchDirection Type definition — ButtonGlitchDirectiontype ButtonGlitchDirection = NonNullable<ButtonVariantProps['glitchDirection']> Default value details
Sourcepackages/ui/src/components/button/Button.vue | |||
class | string | undefined | undefined | Additional CSS classes merged into the button root element. |
DetailsDeclared typestring | undefined Default value details
Sourcepackages/ui/src/components/button/Button.vue | |||
| Name | Signature or type | Description |
|---|---|---|
@click | MouseEvent | The rendered root’s native click event is available to consumers through Vue attribute fallthrough; Button does not declare a custom event with this name.
|
DetailsDeclared typeMouseEvent Sourcepackages/ui/src/components/button/Button.vue | ||
| Name | Signature or type | Description |
|---|---|---|
#default | {} | The button content. If no slot content is provided, pending text is shown only when type="submit" and loading are both true. Explicit slot content takes precedence. |
DetailsDeclared type{}Sourcepackages/ui/src/components/button/Button.vue | ||
| Name | Signature or type | Description |
|---|---|---|
play | () => void | Manually activates the glitch animation. It takes effect only when effect="glitch"; it bypasses the trigger and disabled checks, while a reduced-motion preference still hides the animation. |
DetailsDeclared type() => void Sourcepackages/ui/src/components/button/Button.vue | ||
stop | () => void | Immediately clears the active glitch animation state. |
DetailsDeclared type() => void Sourcepackages/ui/src/components/button/Button.vue | ||
Accessibility
- Keyboard: Supports
Space/Enterto trigger click - ARIA Attributes: Automatically sets the
disabledattribute (non-asChildmode) oraria-disabled="true"(asChildmode) when disabled; automatically setsaria-busy="true"when loading - Focus Management: Supports keyboard navigation and focus styles (
focus:outline)