This commit is contained in:
shadcn
2026-03-04 10:50:57 +04:00
parent 308ebdbd3b
commit 37ff1a3d12
5 changed files with 359 additions and 8 deletions

View File

@@ -195,6 +195,346 @@ On `npx shadcn add`, the following will:
}
```
## registry:ui
### UI component
A `registry:ui` item is a reusable UI component. It can have dependencies, registry dependencies, and CSS variables.
```json title="button.json" showLineNumbers
{
"$schema": "https://ui.shadcn.com/schema/registry-item.json",
"name": "button",
"type": "registry:ui",
"dependencies": ["radix-ui"],
"files": [
{
"path": "ui/button.tsx",
"content": "...",
"type": "registry:ui"
}
]
}
```
### UI component with CSS variables
```json title="sidebar.json" showLineNumbers
{
"$schema": "https://ui.shadcn.com/schema/registry-item.json",
"name": "sidebar",
"type": "registry:ui",
"dependencies": ["radix-ui"],
"registryDependencies": ["button", "separator", "sheet", "tooltip"],
"files": [
{
"path": "ui/sidebar.tsx",
"content": "...",
"type": "registry:ui"
}
],
"cssVars": {
"light": {
"sidebar-background": "oklch(0.985 0 0)",
"sidebar-foreground": "oklch(0.141 0.005 285.823)",
"sidebar-border": "oklch(0.92 0.004 286.32)"
},
"dark": {
"sidebar-background": "oklch(0.141 0.005 285.823)",
"sidebar-foreground": "oklch(0.985 0 0)",
"sidebar-border": "oklch(0.274 0.006 286.033)"
}
}
}
```
## registry:lib
### Utility library
A `registry:lib` item is a utility library. Use it to share helper functions, constants, or other non-component code.
```json title="utils.json" showLineNumbers
{
"$schema": "https://ui.shadcn.com/schema/registry-item.json",
"name": "utils",
"type": "registry:lib",
"dependencies": ["clsx", "tailwind-merge"],
"files": [
{
"path": "lib/utils.ts",
"content": "import { clsx, type ClassValue } from \"clsx\"\nimport { twMerge } from \"tailwind-merge\"\n\nexport function cn(...inputs: ClassValue[]) {\n return twMerge(clsx(inputs))\n}",
"type": "registry:lib"
}
]
}
```
## registry:hook
### Custom hook
A `registry:hook` item is a custom React hook.
```json title="use-mobile.json" showLineNumbers
{
"$schema": "https://ui.shadcn.com/schema/registry-item.json",
"name": "use-mobile",
"type": "registry:hook",
"files": [
{
"path": "hooks/use-mobile.ts",
"content": "...",
"type": "registry:hook"
}
]
}
```
### Hook with dependencies
```json title="use-debounce.json" showLineNumbers
{
"$schema": "https://ui.shadcn.com/schema/registry-item.json",
"name": "use-debounce",
"type": "registry:hook",
"dependencies": ["react"],
"files": [
{
"path": "hooks/use-debounce.ts",
"content": "...",
"type": "registry:hook"
}
]
}
```
## registry:font
### Custom font
A `registry:font` item installs a Google Font. The `font` field is required and configures the font family, provider, import name, and CSS variable.
```json title="font-inter.json" showLineNumbers
{
"$schema": "https://ui.shadcn.com/schema/registry-item.json",
"name": "font-inter",
"type": "registry:font",
"font": {
"family": "'Inter Variable', sans-serif",
"provider": "google",
"import": "Inter",
"variable": "--font-sans",
"subsets": ["latin"]
}
}
```
### Monospace font
```json title="font-jetbrains-mono.json" showLineNumbers
{
"$schema": "https://ui.shadcn.com/schema/registry-item.json",
"name": "font-jetbrains-mono",
"type": "registry:font",
"font": {
"family": "'JetBrains Mono Variable', monospace",
"provider": "google",
"import": "JetBrains_Mono",
"variable": "--font-mono",
"weight": ["400", "500", "600", "700"],
"subsets": ["latin"]
}
}
```
### Serif font
```json title="font-lora.json" showLineNumbers
{
"$schema": "https://ui.shadcn.com/schema/registry-item.json",
"name": "font-lora",
"type": "registry:font",
"font": {
"family": "'Lora Variable', serif",
"provider": "google",
"import": "Lora",
"variable": "--font-serif",
"subsets": ["latin"]
}
}
```
## registry:base
### Custom base
A `registry:base` item is a complete design system base. It defines the full set of dependencies, CSS variables, and configuration for a project. The `config` field is unique to `registry:base` items.
The `config` field accepts the following properties (all optional):
| Property | Type | Description |
| -------------------- | ---------------------------------- | --------------------------------------------------------------- |
| `style` | `string` | The style name for the base. |
| `iconLibrary` | `string` | The icon library to use (e.g. `lucide`). |
| `rsc` | `boolean` | Whether to enable React Server Components. Defaults to `false`. |
| `tsx` | `boolean` | Whether to use TypeScript. Defaults to `true`. |
| `rtl` | `boolean` | Whether to enable right-to-left support. Defaults to `false`. |
| `menuColor` | `"default" \| "inverted"` | The menu color scheme. Defaults to `"default"`. |
| `menuAccent` | `"subtle" \| "bold"` | The menu accent style. Defaults to `"subtle"`. |
| `tailwind.baseColor` | `string` | The base color name (e.g. `neutral`, `slate`, `zinc`). |
| `tailwind.css` | `string` | Path to the Tailwind CSS file. |
| `tailwind.prefix` | `string` | A prefix to add to all Tailwind classes. |
| `aliases.components` | `string` | Import alias for components. |
| `aliases.utils` | `string` | Import alias for utilities. |
| `aliases.ui` | `string` | Import alias for UI components. |
| `aliases.lib` | `string` | Import alias for lib. |
| `aliases.hooks` | `string` | Import alias for hooks. |
| `registries` | `Record<string, string \| object>` | Custom registry URLs. Keys must start with `@`. |
```json title="custom-base.json" showLineNumbers
{
"$schema": "https://ui.shadcn.com/schema/registry-item.json",
"name": "custom-base",
"type": "registry:base",
"config": {
"style": "custom-base",
"iconLibrary": "lucide",
"tailwind": {
"baseColor": "neutral"
}
},
"dependencies": [
"class-variance-authority",
"tw-animate-css",
"lucide-react"
],
"registryDependencies": ["utils", "font-inter"],
"cssVars": {
"light": {
"background": "oklch(1 0 0)",
"foreground": "oklch(0.141 0.005 285.823)",
"primary": "oklch(0.21 0.006 285.885)",
"primary-foreground": "oklch(0.985 0 0)"
},
"dark": {
"background": "oklch(0.141 0.005 285.823)",
"foreground": "oklch(0.985 0 0)",
"primary": "oklch(0.985 0 0)",
"primary-foreground": "oklch(0.21 0.006 285.885)"
}
},
"css": {
"@import \"tw-animate-css\"": {},
"@layer base": {
"*": {
"@apply border-border outline-ring/50": {}
},
"body": {
"@apply bg-background text-foreground": {}
}
}
}
}
```
### Base from scratch
Use `extends: none` to create a base that doesn't extend shadcn/ui defaults.
```json title="custom-base.json" showLineNumbers
{
"$schema": "https://ui.shadcn.com/schema/registry-item.json",
"name": "my-design-system",
"extends": "none",
"type": "registry:base",
"config": {
"style": "my-design-system",
"iconLibrary": "lucide",
"tailwind": {
"baseColor": "slate"
}
},
"dependencies": ["tailwind-merge", "clsx", "tw-animate-css", "lucide-react"],
"registryDependencies": ["utils", "font-geist"],
"cssVars": {
"light": {
"background": "oklch(1 0 0)",
"foreground": "oklch(0.141 0.005 285.823)"
},
"dark": {
"background": "oklch(0.141 0.005 285.823)",
"foreground": "oklch(0.985 0 0)"
}
}
}
```
## Common Fields
### Author
Use the `author` field to add attribution to your registry items.
```json title="example-item.json" showLineNumbers {5}
{
"$schema": "https://ui.shadcn.com/schema/registry-item.json",
"name": "custom-component",
"type": "registry:ui",
"author": "shadcn",
"files": [
{
"path": "ui/custom-component.tsx",
"content": "...",
"type": "registry:ui"
}
]
}
```
### Dev dependencies
Use the `devDependencies` field to install packages as dev dependencies.
```json title="example-item.json" showLineNumbers {5}
{
"$schema": "https://ui.shadcn.com/schema/registry-item.json",
"name": "custom-item",
"type": "registry:item",
"devDependencies": ["@types/mdx"],
"files": [
{
"path": "lib/mdx.ts",
"content": "...",
"type": "registry:lib"
}
]
}
```
### Metadata
Use the `meta` field to attach arbitrary metadata to your registry items. This can be used to store custom data that your tools or scripts can use.
```json title="example-item.json" showLineNumbers {5-8}
{
"$schema": "https://ui.shadcn.com/schema/registry-item.json",
"name": "custom-component",
"type": "registry:ui",
"meta": {
"category": "forms",
"version": "2.0.0"
},
"files": [
{
"path": "ui/custom-component.tsx",
"content": "...",
"type": "registry:ui"
}
]
}
```
## CSS Variables
### Custom Theme Variables

View File

@@ -67,7 +67,7 @@ These rules are **always enforced**. Each links to a file with Incorrect/Correct
The injected project context contains these key fields:
- **`aliases`** → use the actual alias prefix for imports (e.g. `@/`, `~/`), never hardcode.
- **`isRSC`** → when `true`, components using `useState`, `useEffect`, event handlers, or browser APIs need `"use client"`.
- **`isRSC`** → when `true`, components using `useState`, `useEffect`, event handlers, or browser APIs need `"use client"` at the top of the file. Always reference this field when advising on the directive.
- **`tailwindVersion`** → `"v4"` uses `@theme inline` blocks; `"v3"` uses `tailwind.config.js`.
- **`tailwindCssFile`** → the global CSS file where custom CSS variables are defined. Always edit this file, never create a new one.
- **`style`** → component visual treatment (e.g. `nova`, `vega`).

View File

@@ -95,15 +95,17 @@ Don't build custom empty state markup.
**Correct:**
```tsx
import { Empty, EmptyIcon, EmptyTitle, EmptyDescription, EmptyActions } from "@/components/ui/empty"
import { Empty, EmptyContent, EmptyDescription, EmptyHeader, EmptyMedia, EmptyTitle } from "@/components/ui/empty"
<Empty>
<EmptyIcon><FolderIcon /></EmptyIcon>
<EmptyTitle>No projects yet</EmptyTitle>
<EmptyDescription>Get started by creating a new project.</EmptyDescription>
<EmptyActions>
<EmptyHeader>
<EmptyMedia variant="icon"><FolderIcon /></EmptyMedia>
<EmptyTitle>No projects yet</EmptyTitle>
<EmptyDescription>Get started by creating a new project.</EmptyDescription>
</EmptyHeader>
<EmptyContent>
<Button>Create Project</Button>
</EmptyActions>
</EmptyContent>
</Empty>
```
@@ -141,7 +143,7 @@ toast("File deleted.", {
## Choosing between overlay components
Don't default to `Dialog` for everything.
Don't default to `Dialog` for everything. **When recommending an overlay, always show the full component structure with all required subcomponents.**
**Incorrect:**

View File

@@ -1,5 +1,7 @@
# Icons
**Always use the project's configured `iconLibrary` for imports.** Check the `iconLibrary` field from project context: `lucide``lucide-react`, `tabler``@tabler/icons-react`, etc. Never assume `lucide-react`.
---
## Icons in Button use data-icon attribute

View File

@@ -44,6 +44,8 @@ See [customization.md](../customization.md) for theming, CSS variables, and addi
## className for layout only
Use `className` for layout (e.g. `max-w-md`, `mx-auto`, `mt-4`), **not** for overriding component colors or typography. To change colors, use semantic tokens, built-in variants, or CSS variables.
**Incorrect:**
```tsx
@@ -59,3 +61,8 @@ See [customization.md](../customization.md) for theming, CSS variables, and addi
<CardContent>Dashboard</CardContent>
</Card>
```
To customize a component's appearance, prefer these approaches in order:
1. **Built-in variants**`variant="outline"`, `variant="destructive"`, etc.
2. **Semantic color tokens**`bg-primary`, `text-muted-foreground`.
3. **CSS variables** — define custom colors in the global CSS file (see [customization.md](../customization.md)).