Skip to Content
DocsEnterpriseBlogShowcase

Chakra Factory

Use the chakra factory to create supercharged components

Overview

Chakra factory serves as a way to create supercharged JSX component from any HTML element to enable them receive JSX style props.

import { chakra } from "@chakra-ui/react"

The chakra factory can be used in two ways: as a JSX element or as a factory function.

JSX Element

Style props are CSS properties that you can pass as props to your components. With the JSX factory, you can use chakra.<element> syntax to create JSX elements that support style props.

import { chakra } from "@chakra-ui/react"

const Button = ({ children }) => (
  <chakra.button bg="blue.500" color="white" py="2" px="4" rounded="md">
    {children}
  </chakra.button>
)

Factory function

Use the chakra function to convert native elements or custom components. The key requirement is that the component must accept className as props.

const Link = chakra("a")

function Example() {
  return <Link bg="red.200" href="https://chakra-ui.com" />
}

Another example with a custom component.

import * as RadixScrollArea from "@radix-ui/react-scroll-area"

const ScrollArea = chakra(RadixScrollArea.Root)

function Example() {
  return (
    <ScrollArea>
      <RadixScrollArea.Viewport>
        <div>Hello</div>
      </RadixScrollArea.Viewport>
    </ScrollArea>
  )
}

Attaching styles

Use the chakra function to attach styles or recipes to components.

const Link = chakra("a", {
  base: {
    bg: "papayawhip",
    color: "red.500",
  },
})

// usage: <Link href="https://chakra-ui.com" />

Attaching recipes

Here's an example of attaching a recipe to the component.

const Card = chakra("div", {
  base: {
    shadow: "lg",
    rounded: "lg",
    bg: "white",
  },
  variants: {
    variant: {
      outline: {
        border: "1px solid",
        borderColor: "red.500",
      },
      solid: {
        bg: "red.500",
        color: "white",
      },
    },
  },
})

// usage: <Card variant="outline" />

Forwarding props

By default, the chakra factory only filters chakra related style props from getting to the DOM. For more fine-grained control of how props are forwarded, pass the shouldForwardProp option.

Here's an example that forwards all props that doesn't start with $

const Component = chakra("div", {
  shouldForwardProp(prop) {
    return !prop.startsWith("$")
  },
})

To create custom forward props logic, combine the @emotion/is-prop-valid package and the isValidProperty from Chakra UI.

import { chakra, defaultSystem } from "@chakra-ui/react"
import shouldForwardProp from "@emotion/is-prop-valid"

const { isValidProperty } = defaultSystem

const Component = chakra("div", {
  shouldForwardProp(prop, variantKeys) {
    const chakraSfp = !variantKeys?.includes(prop) && !isValidProperty(prop)
    return shouldForwardProp(prop) && chakraSfp
  },
})

Default Props

Use the defaultProps option to pass default props to the component.

const Button = chakra(
  "button",
  {
    base: {
      bg: "blue.500",
      color: "white",
    },
  },
  { defaultProps: { type: "button" } },
)

Polymorphism

Every component created with the chakra factory can accept the as and asChild props to change the underlying DOM element.

<Button as="a" href="https://chakra-ui.com">
  Chakra UI
</Button>

or

<Button asChild>
  <a href="https://chakra-ui.com">Chakra UI</a>
</Button>

Learn more about composition in Chakra UI here