Skip to content
BigBang

Popular

    ↑↓Navigate↵OpenEscClose
    TR

    Components

    Button

    Lets people start an action and makes the most important action in an area easy to find.

    Storybook
    Storybook
    Source
    Source

    A native <button> is rendered; screen readers announce “Save, button”. The default type="button" means it never submits a form by accident. Rendered as an <a> with render, it is announced as a link. The label is the Button’s accessible name; icons are hidden from screen readers with aria-hidden. Icon-only Buttons are not supported in this version; every Button has a visible label.

    Key Behaviour
    Tab Moves focus to the Button. A disabled Button is skipped unless focusableWhenDisabled is set or the Button is loading.
    Enter Starts the action; inside a form with type="submit", submits the form.
    Space Starts the action.

    The focus ring is 2 px thick, drawn 2 px outside the Button, and shows only when the Button is reached with the keyboard, not on a mouse click. Its contrast against the page background is in the Contrast section below. A loading Button keeps focus.

    State Announced
    Default “Save, button”
    Disabled (disabled) Leaves the tab order; when browsing with a virtual cursor, “Save, button, unavailable”.
    Disabled but focusable (focusableWhenDisabled) Carries aria-disabled="true"; announced as “Save, button, unavailable” and can be focused.
    Loading (loading) The Button’s name stays its label. When loading starts, the polite status region next to the Button (role="status") has screen readers read loadingLabel once, or “Loading” in the Provider’s language without it. aria-busy is not used. When it is loading and disabled, the Button has aria-disabled="true" instead of the disabled attribute and stays in the tab order, so focus is not lost.

    Exact wording varies a little between screen readers and browsers; the above is the expected form.

    On an enabled Button, label and background reach at least 4.5:1 for every variant and tone, including hover and pressed, in every brand and mode. The values below were computed from the token sources (packages/tokens/src) with the WCAG relative luminance formula; the lowest value across the two brands (bigbang, fixture) is shown. A test in the token package checks the default pairs of every variant and tone, the primary hover pair and the danger hover and press fills on every build; the other hover and press pairs are computed here. Disabled Buttons are exempt.

    Variant and tone Pair Light mode Dark mode
    primary neutral Label / default, hover, pressed background 6.17:1 8.09:1
    secondary neutral Label / default, hover, pressed background 14.40:1 11.57:1
    tertiary neutral Label / page, hover, pressed background 13.24:1 11.57:1
    primary danger Label / default, hover, pressed background 5.63:1 8.83:1
    secondary danger Label / default, hover, pressed background 5.76:1 4.81:1
    tertiary danger Label / page, hover, pressed background 5.76:1 4.81:1
    Focus ring color-focus-ring / color-surface-default 5.97:1 8.09:1
    secondary danger border color-border-danger / page 5.45:1 6.15:1
    secondary neutral border color-border-default / page 1.38:1 1.49:1

    The border of a neutral secondary Button is below 3:1. The label and its verified contrast identify the Button; the border is only visual support. Product teams should not rely on the border alone to set a secondary Button apart from the page surface.

    Criterion How Button meets it What the product team must do
    1.4.1 Use of colour Meaning is not carried by colour alone; the danger tone also relies on the label text. Make sure the label says what the action does (“Delete”); do not depend on red alone.
    1.4.3 Contrast (minimum) Label contrast is at least 4.81:1 in all enabled states (table above). Do not change colour classes through className.
    1.4.11 Non-text contrast The focus ring is at least 5.97:1; the danger border at least 5.45:1. The neutral secondary border is below 3:1, but the label identifies the Button. Do not place a secondary Button where only its border sets it apart from the background.
    2.1.1 Keyboard A native <button>; Enter and Space start the action. Use Button instead of a clickable <div>.
    2.4.7 Focus visible A 2 px ring is drawn with :focus-visible. Do not remove the focus ring through className.
    2.4.11 Focus appearance (minimum) The ring is drawn outside the Button at a 2 px offset; nothing else covers it. Do not put a Button at the edge of an overflow: hidden container that clips the ring.
    2.5.3 Label in name The accessible name equals the visible label; while loading, the label stays the name. Do not give a name different from the visible label with aria-label.
    2.5.8 Target size (minimum) The smallest size is 32 px tall. Leave space between adjacent Buttons; do not shrink the size in narrow toolbars.
    4.1.2 Name, role, value A native <button>; disabled or aria-disabled when unavailable. When rendering a link with render, set nativeButton={false}.
    4.1.3 Status messages The polite status region announces once when loading starts. Announce the outcome (success, error) separately; Button only reports that loading started.