Usage
How to install, configure, and start building with the FRAYT Design System.
Prerequisites
- Node.js 18.17 or later
- pnpm (recommended) or npm
- Basic familiarity with React, Tailwind CSS, and Next.js
Installation
Clone the repository and install dependencies:
git clone <repository-url>
cd design-system
pnpm installStart the development server:
pnpm devThe app runs at http://localhost:3000.
Adding Components
This design system is built on shadcn/ui. Components are not installed as a package — they live directly in your codebase at components/ui/.
To add a new component:
npx shadcn@latest add <component-name>For example:
npx shadcn@latest add button
npx shadcn@latest add dialog
npx shadcn@latest add tableThe component source will be added to components/ui/ where you can customize it freely.
Project Structure
design-system/
├── app/ # Next.js App Router
│ ├── globals.css # Theme tokens + Tailwind config
│ ├── layout.tsx # Root layout with providers
│ └── docs/ # Documentation pages
├── components/
│ ├── ui/ # shadcn/ui components (70+)
│ ├── docs/ # Documentation-specific components
│ └── theme-provider.tsx # Dark/light mode provider
├── content/docs/ # MDX documentation content
├── lib/
│ ├── utils.ts # cn() class merging utility
│ └── source.ts # Fumadocs content loader
├── hooks/ # Reusable React hooks
└── public/ # Static assetsTheme File
To use the FRAYT theme in an existing shadcn/ui project, download the theme file and replace your globals.css token blocks:
The theme file includes:
- Light and dark mode color tokens using oklch
- Semantic colors — success, warning, danger (in addition to standard shadcn tokens)
- Chart colors — 5 coordinated data visualization colors
- Sidebar tokens — dedicated sidebar theming
- Radius scale — consistent border-radius progression
- Tailwind v4 registration —
@theme inlineblock for utility class support
For Tailwind CSS v3 projects, copy only the :root and .dark blocks — the @theme inline block is v4-only.
Using Design Tokens
All design tokens are defined as CSS custom properties in app/globals.css and exposed as Tailwind utility classes.
In Tailwind classes
// Background and text colors
<div className="bg-primary text-primary-foreground">
Primary surface
</div>
// Borders and rings
<div className="border-border ring-ring">
Bordered element
</div>
// Semantic colors
<div className="bg-destructive text-destructive-foreground">
Error state
</div>As CSS variables
.custom-element {
background-color: var(--primary);
color: var(--primary-foreground);
border-radius: var(--radius);
}Theme Switching
The design system supports light and dark mode via next-themes. The theme is applied using the class strategy on the <html> element.
// Theme is already configured in the root layout.
// To toggle programmatically:
import { useTheme } from 'next-themes';
function ThemeToggle() {
const { theme, setTheme } = useTheme();
return (
<button onClick={() => setTheme(theme === 'dark' ? 'light' : 'dark')}>
Toggle theme
</button>
);
}The cn() Utility
Use the cn() helper from lib/utils.ts to safely merge Tailwind classes without conflicts:
import { cn } from '@/lib/utils';
function MyComponent({ className }: { className?: string }) {
return (
<div className={cn('rounded-lg border p-4', className)}>
Content
</div>
);
}This uses clsx + tailwind-merge under the hood to resolve conflicting utility classes.