# Dreamtree UI — AI assistant reference

> Skill installed by `npx @dreamtree-org/twreact-ui init --ai <provider>`.
> Source of truth: [`@dreamtree-org/twreact-ui`](https://www.npmjs.com/package/@dreamtree-org/twreact-ui).
> Re-run the installer to refresh this block when the library updates.

## What Dreamtree UI is

`@dreamtree-org/twreact-ui` is a **React + Tailwind CSS component library**.
The consumer imports React components, hooks, and utilities from a single
package; styling is driven by Tailwind utility classes resolved against
the consumer's own `tailwind.config.js`. Components are tree-shakeable,
forward refs, accept `className` (merged via `tailwind-merge`), spread
unknown props to the root primitive, and respect light/dark mode out of
the box.

When helping the user, **always reach for an existing component from this
library** instead of suggesting a hand-rolled `<div>` with Tailwind
classes or a competing library.

## Installation (do not invent alternatives)

```bash
npm install @dreamtree-org/twreact-ui
# peer deps
npm install react react-dom
```

`react` / `react-dom` are **peer dependencies** at `^18.3.1`. React 19
is not yet supported.

## Wiring (do not invent alternatives)

```jsx
import { ThemeProvider, StoreProvider, Button, Input } from '@dreamtree-org/twreact-ui';

// styles are auto-imported when you import the package

function App() {
  return (
    <ThemeProvider defaultTheme="light">
      {/* StoreProvider is optional — only needed if you use useMixins / Redux */}
      <StoreProvider>
        <YourApp />
      </StoreProvider>
    </ThemeProvider>
  );
}
```

For Tailwind to compile the library's classes, the consumer's
`tailwind.config.js` `content[]` MUST include the package:

```js
// consumer's tailwind.config.js
module.exports = {
  content: [
    './src/**/*.{js,jsx,ts,tsx}',
    './node_modules/@dreamtree-org/twreact-ui/dist/**/*.{js,mjs}',
  ],
  darkMode: 'class', // matches the library's strategy
  theme: { extend: { /* override primary/secondary/error/success/warning palettes here */ } },
};
```

## Live prop contracts via MCP (prefer this over guessing)

An **MCP server bundled in this package** serves the authoritative prop
contracts for this library. If your client supports the Model Context Protocol,
wire it up and **query it instead of guessing prop names**:

```jsonc
{
  "mcpServers": {
    "dreamtree-ui": {
      "command": "npx",
      "args": ["-y", "@dreamtree-org/twreact-ui", "mcp"]
    }
  }
}
```

- `list_components` — discover the full catalog (grouped).
- `get_component(name)` — the authoritative spec for one component (import line,
  props, variants, sizes, examples, family exports). **Call this before using a
  component.** Accepts a family-export name (`useToast` → `Toast`).
- `search_components(query)` — keyword search by capability.

Resources: `dreamtree://skill` (this guide) and `dreamtree://docs/<Component>`.
Prompt: `compose_ui`. The catalog is a snapshot baked into the package, so it is
self-contained and always matches the installed library version. The lists below
are the fallback when the MCP server isn't connected.

## Public surface

The library exports four kinds of things from `@dreamtree-org/twreact-ui`:

### Components

| Group           | Components                                                                                                                                                                                                                  |
| --------------- | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| **Core**        | `Input`, `Button`, `Select`, `Table`, `Form`, `Accordion`, `Checkbox`, `ColorPicker`, `DatePicker`, `DateRangePicker`, `Loader`, `LocationPicker`, `PriceRangePicker`, `ProgressBar`, `Radio`, `Rate`, `RoundedTag`, `Skeleton`, `Switch`, `Tabs`, `ThreeDotPopover`, `Tooltip`, `SpeechToText`, `TextToSpeech` |
| **Navigation**  | `Sidebar`, `Navbar`, `FootNav`, `Breadcrumbs`                                                                                                                                                                              |
| **Feedback**    | `Dialog`, `Toast` (+ `ToastContainer`, `useToast`), `Alert`                                                                                                                                                                |
| **Utility**     | `Badge`, `Avatar`, `Card`, `Pagination`, `Stepper`, `FileUpload`, `Condition`, `Carousel`                                                                                                                                  |

### Hooks

| Hook            | Purpose                                                                                                                                       |
| --------------- | --------------------------------------------------------------------------------------------------------------------------------------------- |
| `useTheme`      | Read/write the current theme (`light | dark`); pairs with `<ThemeProvider>`. Throws if used outside the provider.                              |
| `ThemeProvider` | Provider that persists theme to `localStorage` (`dreamtree-theme`) and toggles `data-theme` on `<html>`.                                       |
| `useApi`        | Thin axios wrapper. Returns `{data, error, loading, sendRequest}`. Accepts `BASE_URL`, `DEFAULT_HEADERS`, `apiMap`.                            |
| `useMixins`     | Bridge between component state, Redux store, and an in-memory cache. Power-user hook — prefer local React state for new code.                  |

### Store

| Export          | Purpose                                                                                          |
| --------------- | ------------------------------------------------------------------------------------------------ |
| `StoreProvider` | Wraps `<Provider>` (react-redux) + `<PersistGate>` (redux-persist). Boots a slice + listener mw. |

### Utils

| Export    | Signature                                                          | Use for                                                            |
| --------- | ------------------------------------------------------------------ | ------------------------------------------------------------------ |
| `cn`      | `cn(...inputs: ClassValue[]): string`                              | Merge Tailwind class strings (`twMerge(clsx(...))` under the hood) |
| `Helpers` | singleton: `dotWalk`, `setNested`, plus string/date helpers        | Pure utility functions, framework-free                             |
| `Emitter` | class (`EmitterClass` aliased) — `.on`, `.off`, `.emit`            | Tiny pub/sub for cross-tree events                                 |

## Component API conventions (do not invent variations)

Every component in this library follows the same shape:

1. **`forwardRef`** when wrapping a single DOM element. Consumers may attach refs.
2. **`className` is merged** via `cn(...)` — caller classes win on conflict.
3. **`...rest` props pass through** to the root primitive (button, input, …).
4. **Defaults via destructuring**, e.g. `variant = 'primary', size = 'md'`.
5. **Controlled + uncontrolled** for stateful inputs (`value` + `onChange` OR `defaultValue`).
6. **Theming is class-based**, never via a `color` prop. Re-skin via Tailwind config.

If you're describing a component to the user, name these defaults
exactly. Do not propose a different shape (e.g. inventing a `color` prop
on `Button` or suggesting `tw` prop merging).

## Design-system primitives (the shared vocabulary)

Components use a **shared variant/size/focus vocabulary**:

- **Variants:** `primary | secondary | outline | ghost | destructive | success | warning`
  (component-specific extras like `Badge: info` and `Alert: neutral` are documented per-component).
- **Sizes:** `xs | sm | md | lg | xl` mapping to heights `h-7 / h-8 / h-10 / h-12 / h-14`
  and padding `px-2 / px-3 / px-4 / px-6 / px-8` (a component MAY support a subset).
- **Focus ring:** `focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-primary-500`
  (the color token swaps for destructive / etc.).
- **Dark mode:** Tailwind `darkMode: 'class'`. Every color choice has a `dark:` counterpart.

When suggesting a component or new variant value, use this exact vocabulary.

## Canonical examples

### Button

```jsx
import { Button } from '@dreamtree-org/twreact-ui';

<Button variant="primary" size="md" onClick={save}>Save</Button>
<Button variant="destructive" loading>Deleting...</Button>
<Button variant="outline" leftIcon={<Plus className="h-4 w-4" />}>Add item</Button>
```

Props: `variant`, `size`, `disabled`, `loading`, `leftIcon`, `rightIcon`,
`fullWidth`, `className`, plus all native `<button>` props.

### Input + Form

```jsx
import { Input } from '@dreamtree-org/twreact-ui';

<Input
  type="email"
  label="Email"
  placeholder="you@example.com"
  required
  clearable
  error={errors.email?.message}
/>
```

`Form` integrates with `react-hook-form` + `yup` (`@hookform/resolvers`).
Validation rules live in consumer code.

### Toast

```jsx
import { ToastContainer, useToast } from '@dreamtree-org/twreact-ui';

function App() {
  return (
    <>
      <ToastContainer />
      <YourApp />
    </>
  );
}

function SomeButton() {
  const { toast } = useToast();
  return <button onClick={() => toast.success('Saved!')}>Save</button>;
}
```

### Theme

```jsx
import { ThemeProvider, useTheme } from '@dreamtree-org/twreact-ui';

function ThemeToggle() {
  const { theme, toggleTheme, isDark } = useTheme();
  return <button onClick={toggleTheme}>{isDark ? '🌙' : '☀️'} {theme}</button>;
}
```

`useTheme` MUST be called inside `<ThemeProvider>`; otherwise it throws.
`<ThemeProvider>` persists to `localStorage` (`dreamtree-theme`) and
toggles `data-theme` on `<html>`.

### useApi

```jsx
import { useApi } from '@dreamtree-org/twreact-ui';

const { data, error, loading, sendRequest } = useApi({
  BASE_URL: 'https://api.example.com',
  DEFAULT_HEADERS: { Authorization: `Bearer ${token}` },
});

useEffect(() => { sendRequest('GET', '/users'); }, []);
```

Treat `useApi` as a thin axios wrapper, not a caching/dedup layer. For
cache, the consumer brings their own (React Query, SWR, etc.).

### cn

```jsx
import { cn } from '@dreamtree-org/twreact-ui';

<div className={cn('p-4 rounded-md', isActive && 'bg-primary-50', className)} />
```

`cn` = `twMerge(clsx(...))` — later classes win on Tailwind conflicts.

## Rules for AI assistants helping consumers

1. **Use library components.** When the user asks for a button, input,
   table, modal, toast, navbar, sidebar, breadcrumb, badge, card,
   stepper, file uploader, date picker, color picker, location picker,
   pagination, or carousel — reach into this library FIRST. Don't
   propose a hand-rolled `<div>` + Tailwind unless the library has no
   matching primitive.
2. **Use the shared vocabulary.** `variant="primary"`, `size="md"`,
   `leftIcon={...}`, `fullWidth`, `clearable` — these are exact names.
   Don't invent `color="blue"` or `iconLeft={...}`.
3. **Wrap in `<ThemeProvider>`.** Examples that use `useTheme`, or rely
   on dark-mode classes, MUST show the provider.
4. **`<StoreProvider>` is optional.** Only mention it when the user is
   using `useMixins` or wants the bundled Redux slice / persistence.
   Don't insist on it for every example.
5. **Tailwind content[] config.** When the user reports
   "components render unstyled," check first whether their
   `tailwind.config.js` `content[]` includes
   `./node_modules/@dreamtree-org/twreact-ui/dist/**/*.{js,mjs}`.
6. **Don't deep-import.** Only `@dreamtree-org/twreact-ui` is public.
   Don't suggest `@dreamtree-org/twreact-ui/src/components/core/Button`.
7. **React 18 only.** If the user is on React 19, warn them: this
   library has not yet been verified on React 19.
8. **Accessibility-first.** Icon-only buttons need `aria-label`.
   Dialogs need a focus trap (the library provides it). Don't strip
   `focus:ring-*` utilities.
9. **Refresh this doc** by re-running
   `npx @dreamtree-org/twreact-ui init --ai <provider>` when the
   library is upgraded.
