Nexanexa
Paso 7

Estilos con @nexa/ui

Design tokens (con tema oscuro real) + componentes reales en CSS (Button, Input, Card, Dialog, Drawer) + un set chico de utilidades de layout, con tree-shaking real: el sitio solo envía el CSS de lo que de verdad usa. Deliberadamente chico, no un kit completo (más abajo, cómo completarlo rápido si necesitás más).

Usar una clase

<button class="nx-btn nx-btn-primary">Comprar</button>

Sin declarar nada — nexa build ya detecta las clases nx-* y genera el CSS correspondiente.

Declararlo en nexa.toml

nexa add ui
# Instalado @nexa/ui v0.1.0 (stable).
# Registrado en nexa.toml y nexa.lock.

nexa add ui registra el módulo — no descarga nada (ya está embebido en el binario), solo hace que nexa.toml refleje la realidad y nexa build deje de avisar.

Tree-shaking real

# dist/assets/nexa-ui.<hash>.css
# solo trae tokens + .nx-btn — nada de .nx-dialog si no se usó

nexa-ui.css lleva solo los tokens + los componentes que el sitio completo usa — una página 100% estática del mismo proyecto no lo enlaza en absoluto.

¿Cuántos componentes hay, y qué hacer si necesitás más?

<!-- Tailwind Play CDN: rápido para prototipar; para producción, compilar el CSS -->
<script src="https://cdn.tailwindcss.com"></script>

<!-- componentes ya armados sobre Tailwind -->
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/daisyui@4/dist/full.min.css">

<!-- o, clásico -->
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/bootstrap@5.3.3/dist/css/bootstrap.min.css">

Hoy son Button, Input, Card, Dialog y Drawer (más los tokens de color/espaciado/radio y un set chico de utilidades de layout, ver más abajo) — la lista completa, con cada modificador, está en docs/REFERENCIA.md del repo de Nexa. Para armar un diseño completo rápido tenés tres caminos, y los tres usan el mismo mecanismo (un <link>, visto en el paso anterior): (1) escribir tu propio CSS de cero — este mismo tutorial lo hace así, un site.css a mano enlazado en el layout; (2) usar Tailwind (por CDN para prototipar, o tu propio build para producción) + un kit de componentes ya armados sobre Tailwind como DaisyUI o Flowbite; o (3) usar Bootstrap, PrimeVue/PrimeReact, o el que prefieras. @nexa/ui y un framework de terceros no compiten — podés usar nx-btn para lo simple y Tailwind/Bootstrap para el resto del layout, en la misma página.

Toast/snackbar para dashboards: ui.notify()

function saveOk() {
    ui.notify({ message: "Guardado con éxito", variant: "success" });
}

function saveError() {
    ui.notify({ message: "No se pudo guardar", variant: "danger", duration: 0 });
}

No confundir con platform.notify() (una notificación real del sistema operativo, vista en el paso de empaquetado nativo) — ui.notify() es una notificación efímera dentro de la página, tipo $q.notify() de Quasar. Se apila con otras, se auto-cierra a los 4s (duration: 0 lo desactiva), es accesible (role="status") y no necesita declarar nada: ui ya es builtin, igual que para el Dialog.

Dialog apilable + ui.confirm()/ui.alert()

async function removeItem() {
    if (await ui.confirm("¿Seguro que querés borrar esto?")) {
        // ...
    }
}

<div class="nx-drawer" hidden>...</div>

Abrir un segundo Dialog mientras el primero está abierto se apila de verdad (z-index correcto por profundidad, aria-hidden en el que queda cubierto) — el foco ya estaba aislado por diálogo desde siempre. ui.confirm()/ui.alert() son el caso común de confirmar antes de borrar algo, o avisar que algo se guardó, sin escribir el <div class="nx-dialog"> a mano: devuelven una Promise real que resuelve con Aceptar/Cancelar/Escape. Drawer (para sidebars y menús) tiene el mismo foco atrapado que Dialog, con su propio CSS.

Tema oscuro y utilidades de layout

<button data-nexa-strategy="load" onClick={() => platform.theme.set("dark")}>Oscuro</button>

<nav class="nx-flex nx-gap-3">...</nav>
<ul class="nx-grid nx-grid-cols-3">...</ul>
<main class="nx-stack">...</main>

Sin llamar nunca a platform.theme.set(), el sitio ya respeta prefers-color-scheme del sistema operativo — el helper (platform.theme.set("dark"|"light"|"system")) es solo para que el usuario elija explícitamente y esa elección le gane al sistema; se persiste solo con platform.storage(), ya visto. nx-flex/nx-grid/nx-stack son un set chico y deliberado de utilidades de layout, tree-shakeadas igual que el resto — no un sistema de utilidades completo tipo Tailwind.