style: rediseno de layout profesional en las 7 apps
Headers sticky con marca y acciones, contenedores max-w-[1280px], grids de contenido con rails laterales sticky (cotizador, mi-dia, detalle de cobranza), stepper vertical en el wizard de alta, toolbar+ tabla unificadas en cobranza, tabs como segmented control en dashboards, chat con barra de entrada fija y preguntas sugeridas, landing con navbar + hero + grid de modulos + footer.
This commit is contained in:
@@ -1,6 +1,7 @@
|
||||
import { useState } from 'react'
|
||||
import MiTablero from '../components/MiTablero'
|
||||
import TableroGeneral from '../components/TableroGeneral'
|
||||
import type { AccionesTablero } from '../components/comunes'
|
||||
import { esRolConEquipo } from '../lib/mi-tablero'
|
||||
import { getSesion } from '../services/auth'
|
||||
|
||||
@@ -8,42 +9,70 @@ type Vista = 'mia' | 'general'
|
||||
|
||||
const VISTAS: { id: Vista; etiqueta: string }[] = [
|
||||
{ id: 'mia', etiqueta: 'Mi tablero' },
|
||||
{ id: 'general', etiqueta: 'General' },
|
||||
{ id: 'general', etiqueta: 'Tablero general' },
|
||||
]
|
||||
|
||||
/**
|
||||
* Tableros con vista por rol: el vendedor entra a "Mi tablero" (sus KPIs y el
|
||||
* funnel de sus leads); coordinador/corporativo/admin entran a "General" con
|
||||
* la sección Equipo. El toggle permite cambiar de vista en cualquier momento.
|
||||
* la sección Equipo. El header sticky concentra la marca, el segmented control
|
||||
* de vistas y el botón "Actualizar" de la vista activa.
|
||||
*/
|
||||
export default function DashboardPage() {
|
||||
const rol = getSesion()?.usuario.rol ?? 'vendedor'
|
||||
const conEquipo = esRolConEquipo(rol)
|
||||
const [vista, setVista] = useState<Vista>(conEquipo ? 'general' : 'mia')
|
||||
const [acciones, setAcciones] = useState<AccionesTablero | null>(null)
|
||||
|
||||
return (
|
||||
<div>
|
||||
<div className="border-b border-[#E5E7EB] bg-white">
|
||||
<div className="mx-auto flex max-w-6xl gap-2 px-4 py-3" role="tablist" aria-label="Vista del tablero">
|
||||
{VISTAS.map((v) => (
|
||||
<button
|
||||
key={v.id}
|
||||
type="button"
|
||||
role="tab"
|
||||
aria-selected={vista === v.id}
|
||||
onClick={() => setVista(v.id)}
|
||||
className={
|
||||
vista === v.id
|
||||
? 'rounded-lg bg-accent px-5 py-2 text-xs font-medium text-white shadow-sm transition-all duration-100 ease-out hover:bg-accent-hover'
|
||||
: 'rounded-lg border border-[#D1D5DB] bg-white px-5 py-2 text-xs font-medium text-[#374151] transition-all duration-100 ease-out hover:bg-[#F9FAFB]'
|
||||
}
|
||||
<header className="sticky top-0 z-10 border-b border-[#E5E7EB] bg-white/95 backdrop-blur">
|
||||
<div className="mx-auto flex min-h-14 max-w-[1280px] flex-wrap items-center justify-between gap-x-4 gap-y-2 px-4 py-2 sm:px-6">
|
||||
<div className="flex items-center gap-2.5">
|
||||
<span className="flex h-8 w-8 items-center justify-center rounded-lg bg-accent text-xs font-bold text-white">
|
||||
F
|
||||
</span>
|
||||
<span className="text-sm font-semibold text-[#111827]">FRASA Desarrollos</span>
|
||||
</div>
|
||||
<div className="flex items-center gap-3">
|
||||
<div
|
||||
className="inline-flex rounded-lg border border-[#E5E7EB] bg-[#F1F5F9] p-1"
|
||||
role="tablist"
|
||||
aria-label="Vista del tablero"
|
||||
>
|
||||
{v.etiqueta}
|
||||
{VISTAS.map((v) => (
|
||||
<button
|
||||
key={v.id}
|
||||
type="button"
|
||||
role="tab"
|
||||
aria-selected={vista === v.id}
|
||||
onClick={() => setVista(v.id)}
|
||||
className={
|
||||
vista === v.id
|
||||
? 'rounded-md bg-white px-3 py-1.5 text-xs font-medium text-[#111827] shadow-sm transition-all duration-100 ease-out'
|
||||
: 'rounded-md px-3 py-1.5 text-xs font-medium text-[#64748B] transition-all duration-100 ease-out hover:text-[#111827]'
|
||||
}
|
||||
>
|
||||
{v.etiqueta}
|
||||
</button>
|
||||
))}
|
||||
</div>
|
||||
<button
|
||||
type="button"
|
||||
onClick={() => acciones?.actualizar()}
|
||||
disabled={!acciones || acciones.cargando}
|
||||
className="rounded-lg border border-[#D1D5DB] bg-white px-4 py-1.5 text-xs font-medium text-accent shadow-sm transition-all duration-100 ease-out hover:bg-blue-50 disabled:opacity-50"
|
||||
>
|
||||
{acciones?.cargando ? 'Actualizando…' : 'Actualizar'}
|
||||
</button>
|
||||
))}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
{vista === 'mia' ? <MiTablero /> : <TableroGeneral mostrarEquipo={conEquipo} />}
|
||||
</header>
|
||||
{vista === 'mia' ? (
|
||||
<MiTablero alCambiarAcciones={setAcciones} />
|
||||
) : (
|
||||
<TableroGeneral mostrarEquipo={conEquipo} alCambiarAcciones={setAcciones} />
|
||||
)}
|
||||
</div>
|
||||
)
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user