Skip to main content
/
/
/
Button

Button

import Button from "@intility/bifrost-react/Button";

Basic Button

<Button onClick={() => alert("Hello, world!")}>Basic button</Button>
<Button onClick={() => alert("Hello, world!")}>Basic button</Button>

Submitting a form

Breaking change in 4.0

Bifrost <Button> is type="button" by default since 4.0.

This differs from a native <button> (and bifrost < 4.0) which defaults to "submit" when type is omitted.

If you want to submit a <form>, you need to explicitly use <Button type="submit">

// if form has an `action` or `onSubmit` handler <form> <Button type="submit">Submit the form</Button> </form>
// if form has an `action` or `onSubmit` handler <form> <Button type="submit">Submit the form</Button> </form>

If the button navigates to a new URL on click, you should probably use a html link element <a> instead of <Button>.

You can style links as buttons using the .bf-button css class. This should work fine for <Link> components from react-router or next/link as well.

<a class="bf-button" href="/css/button#links-styled-as-a-button"> Read more about links and buttons </a>
<a class="bf-button" href="/css/button#links-styled-as-a-button"> Read more about links and buttons </a>

Variants

Options for variant prop:

  • 'basic': Default button variant. Same as not passing a variant.
  • 'filled': A powerful call-to-action button. Preferably only used once per page.
  • 'flat': A tertiary button for actions that don't need as much focus.
'outline' variant was removed in Bifrost 4.7
<Button>Basic</Button> <Button variant='filled'>Filled</Button> <Button variant='flat'>Flat</Button>
<Button>Basic</Button> <Button variant='filled'>Filled</Button> <Button variant='flat'>Flat</Button>

States

Options for 'state' prop:

  • 'default': Default state. Same as not passing a state.
  • 'inactive': Dimmed button. Use instead of disabled button.
  • 'neutral': Neutral colors. Nice when you have multiple buttons and don't want to overload the UI.
  • 'alert': Red colored button. Use for destructive actions. E.g deletion.
  • 'inverted': Inverted colors for use on contrasting backgrounds.
Use inactive state instead of a disabled button
<Button>Default</Button> <Button state="inactive">Inactive</Button> <Button state="neutral">Neutral</Button> <Button state="alert">Alert</Button> <Box background="inverted"> <Button state="inverted">Inverted</Button> </Box>
<Button>Default</Button> <Button state="inactive">Inactive</Button> <Button state="neutral">Neutral</Button> <Button state="alert">Alert</Button> <Box background="inverted"> <Button state="inverted">Inverted</Button> </Box>

Combine state and variant

You can use any variant combined with any state.

statevariant
default
inactive
neutral
alert
inverted

Small size

Use the small prop for a smaller button size.

<Button small>Basic</Button> <Button small variant='filled'>Filled</Button> <Button small variant='flat'>Flat</Button>
<Button small>Basic</Button> <Button small variant='filled'>Filled</Button> <Button small variant='flat'>Flat</Button>

Icon

You can place practically any JSX content inside a button, including <Icon>

<Button> <Icon icon={faGlobe} marginRight /> Button with Icon </Button> <Button variant='filled'> Next <Icon icon={faArrowRight} marginLeft /> </Button> <Button variant='flat'> <Icon icon={faCalendarPlus} marginRight /> Add to calendar </Button>
<Button> <Icon icon={faGlobe} marginRight /> Button with Icon </Button> <Button variant='filled'> Next <Icon icon={faArrowRight} marginLeft /> </Button> <Button variant='flat'> <Icon icon={faCalendarPlus} marginRight /> Add to calendar </Button>

Icon-only button

If you have a button without text content, don't forget to add an aria-label to make it accessible for screen readers.

<Button aria-label="Go to front page"> <Icon icon={faHome} /> </Button>
<Button aria-label="Go to front page"> <Icon icon={faHome} /> </Button>

Pill (rounded)

The pill prop will round the corners.

If you want a circular button (for an icon-only button for instance) you can also apply noPadding.

<Button pill> Continue <Icon icon={faArrowRight} marginLeft /> </Button> <Button pill variant="filled"> <Icon icon={faCheck} marginRight /> Submit </Button> <Button pill variant="filled" state="alert"> <Icon icon={faTrashAlt} marginRight /> Delete </Button> <Button pill variant="flat"> <Icon icon={faTimes} marginRight /> Close </Button> <Button pill noPadding aria-label="Continue"> <Icon icon={faArrowRight} /> </Button> <Button pill variant="filled" noPadding aria-label="Submit"> <Icon icon={faCheck} /> </Button> <Button pill variant="filled" state="alert" noPadding aria-label="Delete"> <Icon icon={faTrashAlt} /> </Button> <Button pill variant="flat" noPadding aria-label="Close"> <Icon icon={faTimes} /> </Button>
<Button pill> Continue <Icon icon={faArrowRight} marginLeft /> </Button> <Button pill variant="filled"> <Icon icon={faCheck} marginRight /> Submit </Button> <Button pill variant="filled" state="alert"> <Icon icon={faTrashAlt} marginRight /> Delete </Button> <Button pill variant="flat"> <Icon icon={faTimes} marginRight /> Close </Button> <Button pill noPadding aria-label="Continue"> <Icon icon={faArrowRight} /> </Button> <Button pill variant="filled" noPadding aria-label="Submit"> <Icon icon={faCheck} /> </Button> <Button pill variant="filled" state="alert" noPadding aria-label="Delete"> <Icon icon={faTrashAlt} /> </Button> <Button pill variant="flat" noPadding aria-label="Close"> <Icon icon={faTimes} /> </Button>

Button.Group

Buttons can be used within a group, marked as selected with the active boolean prop.

Prop support

Do not use props such as state (except 'inactive'), small, and variant when <Button> is used as children of <Button.Group>

<Button.Group> <Button active> <Icon icon={faHandRock} marginRight /> Rock </Button> <Button> <Icon icon={faHandPaper} marginRight /> Paper </Button> <Button> <Icon icon={faHandScissors} marginRight /> Scissors </Button> </Button.Group>
<Button.Group> <Button active> <Icon icon={faHandRock} marginRight /> Rock </Button> <Button> <Icon icon={faHandPaper} marginRight /> Paper </Button> <Button> <Icon icon={faHandScissors} marginRight /> Scissors </Button> </Button.Group>

Button.Expand

Control <Button.Expand> state with the open prop, and use onClick just like any other button.

Useful for toggling expandable content.

<Button.Expand open={openState} onClick={setOpenState(!openState)}> Toggle </Button.Expand>
<Button.Expand open={openState} onClick={setOpenState(!openState)}> Toggle </Button.Expand>
Provides a container with a height transition.

Sandbox

import { useState } from "react";
import {
  faHandPaper,
  faHandRock,
  faHandScissors,
} from "@fortawesome/free-solid-svg-icons";
import Button from "@intility/bifrost-react/Button";
import Grid from "@intility/bifrost-react/Grid";
import Icon from "@intility/bifrost-react/Icon";

export default function () {
  const [expanded, setExpanded] = useState(false);
  const [active, setActive] = useState("rock");
  return (
    <div className="bf-padding">
      <Grid>
        <div className="bfl-inline">
          <Button>Basic</Button>
          <Button variant="filled">Filled</Button>
          <Button variant="flat">Flat</Button>
        </div>
        <div>
          <Button.Group>
            <Button
              active={active === "rock"}
              onClick={() => setActive("rock")}
            >
              <Icon icon={faHandRock} marginRight />
              Rock
            </Button>
            <Button
              active={active === "paper"}
              onClick={() => setActive("paper")}
            >
              <Icon icon={faHandPaper} marginRight />
              Paper
            </Button>
            <Button
              active={active === "scissors"}
              onClick={() => setActive("scissors")}
            >
              <Icon icon={faHandScissors} marginRight />
              Scissors
            </Button>
          </Button.Group>
        </div>
        <div>
          <Button.Expand onClick={() => setExpanded(!expanded)} open={expanded}>
            Toggle me
          </Button.Expand>
          {expanded && <p>My content</p>}
        </div>
      </Grid>
    </div>
  );
}