Proper UI

Installation

This guide walks through installing Proper UI and getting a new or existing project set up quickly.

Frameworks

The CLI detects your project and scaffolds the right files. Pick the framework you're using and run its init command from your project root.

Next.js

npx @properui/cli@latest init --nextjs

Vite

npx @properui/cli@latest init --vite

Bolt, v0, Lovable, Claude

AI builders that can run shell commands can use the same CLI. Run the framework flag that matches the generated project (--nextjs or --vite), or leave it off and let init auto-detect from the project files:

npx @properui/cli@latest init --nextjs

Manual

No CLI, no problem — see Manual installation below for the exact files to create by hand.

Installation via CLI

The CLI creates theme.css, updates globals.css with the required imports and custom variants, and adds the cx utility. For Vite it also wires the @ import alias for you — a paths entry in tsconfig.app.json/tsconfig.json and the matching resolve.alias in vite.config, since Vite needs both to resolve @/... imports and has no built-in tsconfig-paths support. For every other framework it reads your existing tsconfig.json path alias rather than writing one — if none is declared, it warns you and tells you what to add. Once your project is initialized, add components one at a time:

npx @properui/cli@latest add badges

Add as many components as you need — each command copies that component's source (and its dependencies) straight into your project:

npx @properui/cli@latest add button-group avatar table

Manual installation

If you'd rather not run the CLI, set the project up by hand.

1. Install the dependencies

npm install react-aria-components tailwind-merge tailwindcss-react-aria-components tailwindcss-animate @tailwindcss/typography

2. Create theme.css

Add a theme.css file with your design tokens inside a Tailwind v4 @theme block — brand palette, semantic colors, typography scale, shadows, and breakpoints. This is the single file to edit when re-branding.

/* theme.css */
@theme {
    --color-brand-50: #f5f8ff;
    --color-brand-500: #2563eb;
    --color-brand-600: #1d4ed8;
    /* …the rest of the brand scale, plus semantic bg-*/text-*/fg-*/border-* tokens */
}

.dark-mode {
    /* re-map the semantic tokens above for dark mode */
}

3. Update globals.css

Import Tailwind, your theme, and the typography stylesheet, register the plugins, and declare the dark custom variant:

/* globals.css */
@import "tailwindcss";
@import "./theme.css";
@import "./typography.css";

@plugin "@tailwindcss/typography";
@plugin "tailwindcss-react-aria-components";
@plugin "tailwindcss-animate";

@custom-variant dark (&:where(.dark-mode, .dark-mode *));

4. Add the cx utility

Every component merges its style object with cx, a thin wrapper around tailwind-merge that also understands the display-* text sizes:

// utils/cx.ts
import { extendTailwindMerge } from "tailwind-merge";

export const cx = extendTailwindMerge({
    extend: { theme: { text: ["display-xs", "display-sm", "display-md", "display-lg", "display-xl", "display-2xl"] } },
});

5. Copy in a component

With the setup files in place, copy any component's source directly from its page into your project, adjusting import paths to match your aliases.

FAQs