Skip to content

Plan: creación de documentos por pasos en móvil (DocumentDrawer) ​

Objetivo ​

Que el flujo de crear/editar un documento desde DocumentDrawer en viewports móviles sea por etapas (wizard), con la misma filosofía que Configuración → Importaciones (ImportWizard: pasos numerados, avanzar/retroceder, contenido una pantalla a la vez), reduciendo scroll largo y sobrecarga cognitiva.

Referencia en el código actual ​

PiezaUbicaciónQué reutilizar como patrón
Wizard por pasos../../Frontend/components/ImportWizard.tsxsteps[], currentStep, handleNext / handleBack, canProceed(), AnimatePresence por paso, stepper visual
Entrada en settings../../Frontend/components/settings/sections/ImportSettings.tsxContenedor mínimo que monta el wizard
Documento../../Frontend/components/DocumentDrawer.tsxEstado unificado del documento; ya usa useMediaQuery / isNarrowViewport y estilos max-md: en acciones

ImportWizard hoy muestra los 5 pasos a la vez en el stepper (horizontal). En móvil suele convenir un stepper compacto (p. ej. “Paso 2 de 5” + barra de progreso, o dots) para no comprimir títulos; eso puede ser una variante responsive del mismo componente visual.

Alcance ​

  • Incluido: comportamiento solo cuando isNarrowViewport (o breakpoint acordado, p. ej. < md), manteniendo el layout actual en desktop/tablet anchos.
  • Incluido: documentos “estándar” (encabezado, líneas, totales, guardar) y extensiones que ya viven en el drawer (adjuntos, pagos, costos importación, campos personalizados), ordenadas en pasos lógicos.
  • Excluido (fase inicial): reescritura completa de DocumentDrawer; el plan favorece una capa de orquestación sobre el contenido existente.

Principios de UX ​

  1. Un foco por pantalla: cada paso muestra un subconjunto de UI; evitar duplicar formularios completos en dos pasos.
  2. Navegación clara: botones fijos Atrás / Siguiente (y Guardar solo en el último paso o siempre visible según decisión de producto).
  3. Validación por etapa: no permitir “Siguiente” si faltan datos obligatorios de esa etapa (equivalente a canProceed en ImportWizard).
  4. Sin pérdida de datos: el estado sigue siendo el de DocumentDrawer (mismos hooks/estado); solo cambia qué bloques se renderizan visibles.
  5. Coherencia con importaciones: reutilizar tokens, Card, animaciones (framer-motion) y textos de i18n donde aplique.

Propuesta de etapas (base) ​

Los nombres son orientativos; deben vivir en lib/i18n.

PasoContenido sugeridoValidación mínima para avanzar
1Tipo/contexto ya elegido al abrir + socio de negocio, fechas, moneda, punto de emisión, canalCliente/proveedor y fechas según reglas actuales del documento
2Líneas (DocumentItems / retenciones / bundles según tipo)Al menos una línea válida o reglas del tipo de documento
3Totales, descuentos globales, observaciones brevesOpcional o según tipo fiscal
4Extras: adjuntos, pagos anticipados, costos de importación, relaciones, campos personalizadosOpcional; puede dividirse en sub-pasos si el tipo de documento lo exige
5Revisión (resumen lectura) + acciones Guardar / Confirmar / enviarMisma validación final que hoy antes de submit

Nota: Para tipos especiales (p. ej. retención 05, programación de facturas), los pasos 2–4 pueden variar mediante una pequeña tabla getMobileStepsForDocumentType(type) para no forzar un único flujo.

Arquitectura técnica recomendada ​

Opción A — Recomendada: “Mobile step shell” ​

  • Nuevo componente, p. ej. DocumentDrawerMobileSteps, que:
    • Recibe currentStep, setCurrentStep, definición de pasos (id + render function o children por paso).
    • Envuelve el mismo contenido que hoy, pero con display / montaje condicional por paso (o visibility + inert para accesibilidad).
  • DocumentDrawerContent detecta isNarrowViewport y:
    • Si móvil: renderiza el shell de pasos + barra inferior (Atrás / Siguiente / Guardar).
    • Si no: renderiza el layout actual (una sola columna scrollable).

Ventaja: el estado y la lógica de guardado permanecen en un solo sitio.

Opción B — Extraccer secciones ​

  • Partir DocumentDrawer en secciones ya nombradas (DocumentHeader, DocumentItems, …) y solo ordenarlas en pasos en móvil. Es más trabajo de refactor previo; puede ser fase 2.

Componente compartido de stepper ​

  • Extraer de ImportWizard un WizardStepper (props: steps, currentStep, variant: 'full' | 'compact') para usar en importaciones y en documentos, evitando duplicar markup.

Estado y comportamiento ​

  • Un solo árbol de estado: no crear un segundo “documento en progreso”; currentStep es solo UI.
  • Al abrir el drawer: resetear currentStep a 1 (o al paso adecuado si es edición y se quiere ir directo a líneas — decisión de producto).
  • Al cerrar: resetear paso para la próxima apertura.
  • Edición de documento existente: mismos pasos; el paso 5 puede enfatizar “Cambios” vs creación.

Validación ​

  • Centralizar por paso una función canGoNext(step): boolean que reutilice validaciones ya existentes (Zod, checks previos a handleSave, etc.) para no duplicar reglas.
  • Mostrar mensajes cortos bajo el step o con toast al bloquear “Siguiente”.

Accesibilidad y teclado ​

  • Foco al cambiar de paso (contenedor del paso con tabIndex={-1} y focus() opcional).
  • Evitar trampas de foco en drawers anidados (ya hubo trabajo con Sheet/portal en otras pantallas).

Internacionalización ​

  • Claves nuevas bajo un prefijo común, p. ej. documentWizard.step1Title, documentWizard.next, documentWizard.back, documentWizard.review.

Fases de implementación sugeridas ​

FaseEntregaRiesgo
1Stepper compacto + 3 pasos (Encabezado → Líneas → Revisión + guardar) solo para un subconjunto de tipos (p. ej. factura venta)Bajo
2Incorporar totales/observaciones como paso propio; barra de acciones alineada con diseñoMedio
3Adjuntos, pagos, importación, custom fields como pasos o sub-sección del paso 4Alto (muchos modales anidados)
4Matriz por documentType (compras, NC, retenciones, programadas) + pruebas E2E móvilAlto

Pruebas ​

  • Manual: iPhone/Android + Chrome devtools responsive.
  • Comprobar: rotación, teclado virtual cubriendo botones, scroll solo dentro del paso activo.
  • Regresión: desktop sin cambios visuales relevantes.

Riesgos y mitigación ​

RiesgoMitigación
DocumentDrawer muy grandeShell en archivo nuevo; tocar el mínimo de líneas en el drawer principal
Doble scroll (drawer + paso)min-h-0 + overflow-y-auto solo en el cuerpo del paso
Drawers secundarios (crear cliente, etc.)Mantener como hoy; no meterlos “dentro” de un paso sin revisar z-index

Criterios de éxito ​

  • En ancho móvil, el usuario completa un documento típico sin scroll interminable en una sola vista.
  • Tiempo y errores percibidos menores al flujo actual en móvil (validación opcional con usuarios).

Documento de planificación; la implementación puede ajustar nombres de componentes y número de pasos según prioridad de producto.


Implementación (resumen técnico) ​

  • Activo cuando: viewport estrecho (max-width: 767px), documento editable (!readOnly) y mode === 'document' (no afecta solo lectura ni otros modos del drawer).
  • Componentes: Frontend/components/document/DocumentDrawerMobileWizard.tsx (DocumentDrawerMobileWizardProgress, DocumentDrawerMobileWizardNav, constante MOBILE_DOC_WIZARD_STEPS = 5).
  • Pasos: 1 Datos (DocumentHeader) → 2 Líneas → 3 Totales y observaciones (DocumentFooter) → 4 Pagos, DTE, costos importación, campos personalizados, adjuntos → 5 Resumen + barra Guardar.
  • i18n: claves doc.mobileWizard.* en Frontend/lib/i18n.tsx.
  • Validación al pulsar “Siguiente”: paso 1 (cliente, condición de pago si aplica, fechas, punto de emisión, retención 05 si aplica); paso 2 (validateItems()).

Documentación API abaco · Changelog