# Contrato del proyecto — léelo completo antes de escribir código Sitio + micro CRM para **FSPM (Fire Service Plus México)**, protección contra incendios. Es una **demo comercial** de Consultoría E3: tiene que verse y funcionar como producción. Raíz: `H:\MegaSync\Proyectos\fspm\fspm-web` ## Stack ya instalado — no cambies versiones, no agregues dependencias Next.js 15.5.4 (App Router) · React 19 · TypeScript estricto · Tailwind CSS **v4** (sin `tailwind.config`, los tokens viven en `@theme` dentro de `src/app/globals.css`) · Prisma 6.16 + SQLite · zod 4 · jose · bcryptjs. Si crees que necesitas una dependencia nueva, **no la instales**: resuélvelo con lo que hay o dilo en tu reporte final. ## Regla de propiedad de archivos — la más importante Trabajas en paralelo con otros agentes sobre el mismo árbol. **Solo puedes crear y editar los archivos de tu lote.** Si necesitas cambiar un archivo ajeno, no lo toques: descríbelo en tu reporte final y el orquestador lo integra. Archivos del orquestador, **de solo lectura para ti**: ``` src/app/globals.css src/app/layout.tsx src/data/*.ts src/lib/db.ts src/lib/utm.ts src/lib/crm/constantes.ts src/lib/leads/esquema.ts src/components/marca/RielClases.tsx src/components/site/Encabezado.tsx src/components/site/Pie.tsx prisma/schema.prisma package.json next.config.ts .env ``` ## Sistema de diseño — deriva todo de aquí, no improvises color ni tipografía Los tokens están en `src/app/globals.css` bajo `@theme`. Úsalos como clases de Tailwind (`bg-ink`, `text-muted`, `border-rule`, `text-signal`) o como `var(--color-…)`. **Dos mundos, y el contraste entre ellos es la idea:** - **Oscuro = el riesgo y la operación.** `bg-ink` (#0C1116, acero-humo azulado), paneles `bg-ink-2` / `bg-ink-3`, filetes `border-rule`. - **Claro = la evidencia y el documento.** `bg-paper` (#EEF1F3, blanco de plano de ingeniería — **no** es crema), texto `text-deep`. Alterna secciones entre los dos mundos. Es la traducción visual del diagnóstico del estudio: convertir autoridad técnica en confianza comprable. **Señal:** `text-signal` / `bg-signal` = #DB042B, el rojo real de FSPM extraído de su CSS. Es señal, no relleno: úsalo en el CTA, en el riel de clases y en acentos puntuales. `text-ember` (#F2B705) es el amarillo del traje de bombero de su propia fotografía: **solo para estados de riesgo, advertencia y atención**, nunca decorativo. **Tipografía**, ya cargada en el layout raíz: - `font-display` — Archivo 800/900. Encabezados. Versalitas y tracking cerrado. Es rotulación de equipo industrial. - `font-sans` — IBM Plex Sans. Cuerpo. - `font-mono` — IBM Plex Mono. **La capa de datos**: etiquetas, especificaciones, folios, cifras, códigos, UTMs. Todo dato numérico lleva `font-variant-numeric: tabular-nums` (ya aplicado a `.font-mono` y a `table`). Radios casi rectos: `rounded-[3px]` / `rounded-[2px]`. Es una herramienta, no una app de consumo. **Utilidades ya escritas — reúsalas en vez de reinventar:** `.shell` `.shell-wide` `.eyebrow` `.btn .btn-signal .btn-ghost .btn-deep .btn-sm` `.field .field-lite .field-label .field-error` `.panel .panel-lite` `.spec .spec-cell .spec-key .spec-val` `.hair .hair-lite` `.grid-bg .grid-bg-lite` `.hazard` `.badge .badge-signal .badge-ember .badge-ok` `.link` `.skip` `.anim-rise` `.anim-ignite` `.reveal`. ### Elemento firma: el riel de clases de fuego `src/components/marca/RielClases.tsx` — cinco celdas fijas `A B C D K`, se encienden solo las que ese producto/solución/lead cubre. Aparece en el sitio **y** en el panel. Úsalo siempre que haya clases de fuego; no dibujes otra variante. ### Movimiento Contenido. Una secuencia orquestada en el héroe y revelados discretos al hacer scroll con `.reveal` + IntersectionObserver. Nada de efectos dispersos: delatan trabajo automático. `prefers-reduced-motion` ya está respetado globalmente. ## Piso de calidad, no negociable - **Responsive real** desde 320px. Prueba mentalmente 320 / 768 / 1280 / 1920. - **Compatibilidad WebKit (Safari e iOS).** Es requisito explícito del cliente: usa `-webkit-backdrop-filter` junto a `backdrop-filter`, `-webkit-appearance: none` en controles, `-webkit-overflow-scrolling: touch` en scroll horizontal, `-webkit-tap-highlight-color` en elementos táctiles, y evita `gap` en `inline-flex` sin fallback. Nada de `100vh` a secas en móvil: usa `100dvh` con `100vh` de respaldo. - **Accesibilidad:** un solo `