---
title: Cheat Sheet
description: Every Bamboo API on one page.
---

Everything below is a function call that returns a class string. There is no JSX factory and no template literal syntax
— one way to write a style, which is also what lets the [build-time compiler](/docs/guides/source-transformation)
resolve it completely.

## Styling

```jsx
import { css, cx } from '../styled-system/css'

css({ color: 'red.500', padding: '4' }) // tokens by name
css({ color: '#f00', padding: '13px' }) // raw values work too
css({ display: '[var(--btn-display)]' }) // escape hatch — skips token checking

css({ _hover: { color: 'red.700' } }) // condition as a block
css({ color: { base: 'red.500', _hover: 'red.700' } }) // …or per property
css({ fontSize: { base: 'sm', md: 'lg' } }) // responsive, mobile first
css({ color: { base: 'black', _dark: 'white' } }) // theming condition

cx('external', cond && 'another') // unknown external inputs remain a tiny runtime join
```

## Composing styles

The compiler semantically composes statically analyzable Bamboo classes passed to `cx`. With unknown external inputs,
`cx` is only a string join and makes no conflict guarantee. Merge the **objects** when the inputs are available as
styles, where the last write wins per property:

```jsx
css({ padding: '4' }, { padding: '8' }) // → padding 8
css(base, props.css) // the overridable-component idiom
css.raw({ padding: '4' }) // a style object to merge later
```

See [Merging styles](/docs/concepts/merging-styles).

## Recipes

```jsx
import { cva, sva } from '../styled-system/css'

const button = cva({
  className: 'button', // optional extraction metadata; ignored by Vite atom identity
  base: { borderRadius: 'md' },
  variants: { size: { sm: { padding: '2' }, lg: { padding: '4' } } },
  defaultVariants: { size: 'sm' },
  compoundVariants: [{ size: 'lg', tone: 'brand', css: { fontWeight: 'bold' } }],
})

button({ size: 'lg' }) // shared atoms for this complete selection
const [variantProps, rest] = button.splitVariantProps(props)
```

The Vite compiler resolves the selected recipe and any statically analyzable `cx()` composition before allocating
globally shared atoms in `utilities`. Declaring the same shape in `theme.recipes` generates only reachable finite
variant states — see [inline vs config recipes](/docs/concepts/recipes#should-i-use-an-inline-or-config-recipe).

`sva` is the same for multi-part components. Under Vite, each selected slot receives its complete atom string:

```jsx
const checkbox = sva({ slots: ['root', 'control'] /* … */ })
const classes = checkbox({ size: 'md' })
classes.root // shared atoms for the selected root styles
classes.control // shared atoms for the selected control styles
```

CLI/PostCSS extraction can instead use
[`scopeRoots`](/docs/concepts/slot-recipes#variant-scoping-in-extraction-only-output) to deliver variants through
`@scope`.

## Patterns

Layout helpers that are `css()` with a transform applied. `flex`, `grid`, `gridItem`, `center`, `container`, `spacer`,
`divider`, `float`, `aspectRatio`, `bleed`, `linkOverlay`.

```jsx
import { flex } from '../styled-system/patterns'
;<div className={flex({ direction: 'column', gap: '4', align: 'center' })} />
```

## Tokens and escape hatches

```jsx
import { token } from '../styled-system/tokens'
import { css, fallback, viewTransition } from '../styled-system/css'

token('colors.red.500') // var(--colors-red-500)
token.value('colors.red.500') // the resolved value, for canvas and the like
css({ height: fallback('100dvh', '100vh') }) // progressive enhancement
viewTransition({
  /* … */
}) // ::view-transition-* rules, one class
```

See [Writing styles](/docs/concepts/writing-styles) for the full surface.
