Overview
In this lesson, you'll learn how to define, extend, and customize slot recipes to create coordinated, multi-part designs that are both flexible and scalable.
Key Takeaways
A slot recipe is a style blueprint for components made up of multiple parts.
Each part (slot) such as root, list, trigger, indicator, or content, has its own styles, which work together to form the full component design.
While classic recipes handle single-part components, slot recipes manage complex ones that use dot notation (e.g., Tabs.Trigger or Menu.Item).
Extending or customizing them involves styling each slot individually while maintaining visual harmony across all parts.
The anatomy of a slot recipe (Tabs Component)
The first step is to determine if the component uses a slot recipe by analyzing it's anatomy
<Tabs.Root defaultValue="tab-1">
<Tabs.List>
<Tabs.Trigger value="tab-1">Tab 1</Tabs.Trigger>
<Tabs.Trigger value="tab-2">Tab 2</Tabs.Trigger>
<Tabs.Indicator />
</Tabs.List>
<Tabs.Content value="tab-1">Content 1</Tabs.Content>
<Tabs.Content value="tab-2">Content 2</Tabs.Content>
</Tabs.Root>
Define a custom slot recipe
Next, use defineSlotRecipe to create and control each slot's styles.
For example, this is how to define a slot recipe for a tabs component:
import { defineSlotRecipe } from "@chakra-ui/react"
export const customTabsRecipe = defineSlotRecipe({
className: "custom-tabs",
description: "Advanced tabs with coordinated slot styling",
slots: ["root", "list", "trigger", "indicator", "content"],
base: {
root: //root styles here,
list: //list styles here,
trigger: //trigger styles here,
indicator: //indicator styles here,
content: //content styles here,
},
})
Register your slot recipe in the theme
import { createSystem, defaultConfig, defineConfig } from '@chakra-ui/react'
import { customTabsRecipe } from './recipes'
const customConfig = defineConfig({
theme: {
recipes: {
tabs: customTabsRecipe,
},
},
})
export const system = createSystem(defaultConfig, customConfig)
Use your new slot recipe in components
<Tabs.Root defaultValue="tab-1" variant="solid" size="2xl">
<Tabs.List>
<Tabs.Trigger value="tab-1">Tab 1</Tabs.Trigger>
<Tabs.Trigger value="tab-2">Tab 2</Tabs.Trigger>
<Tabs.Indicator />
</Tabs.List>
<Tabs.Content value="tab-1">This is tab one</Tabs.Content>
<Tabs.Content value="tab-2">This is tab two</Tabs.Content>
</Tabs.Root>