Cesar Mendivil e43686e36d feat(modal-parts): add modular components for modal UI
- Introduced ModalDestinationButton for destination selection with customizable icons and labels.
- Added ModalInput for text input with optional character counter.
- Implemented ModalLink for reusable links styled as underlined text.
- Created ModalPlatformCard for platform selection with badges.
- Developed ModalRadioGroup for radio button groups with custom styling.
- Added ModalSection for grouping modal content with optional labels.
- Implemented ModalSelect for dropdown selections with custom styling.
- Created ModalShareButtons for sharing options via Gmail, Email, and Messenger.
- Developed ModalTextarea for multi-line text input with character counter.
- Introduced ModalToggle for toggle switches with optional help text and links.
- Updated README.md with component descriptions, usage examples, and design guidelines.
- Added index.ts for centralized exports of modal components.
2025-11-06 00:32:08 -07:00

5.5 KiB

Sistema de Componentes Modulares para Modales

Descripción

Sistema de componentes reutilizables basado en el diseño de StreamYard y Google Material Design que permite crear modales consistentes y atractivos con mínimo código.

Componentes Disponibles

1. Modal (Base)

Componente contenedor principal usando <dialog> nativo de HTML5.

Props:

  • open: boolean - Controla visibilidad
  • onClose: () => void - Callback al cerrar
  • title?: string - Título del modal
  • children: ReactNode - Contenido principal
  • footer?: ReactNode - Botones de acción
  • width?: 'sm' | 'md' | 'lg' | 'xl' - Ancho predefinido
  • closeOnOverlayClick?: boolean - Cerrar al hacer clic afuera

Enlaces azules subrayados para textos de ayuda.

Props:

  • href: string - URL del enlace
  • children: ReactNode - Texto del enlace

Ejemplo:

<ModalLink href="https://docs.example.com">
  nuestra documentación
</ModalLink>

3. ModalCopyInput

Input de solo lectura con botón de copiar integrado.

Props:

  • value: string - Texto a copiar
  • buttonText?: string - Texto del botón (default: "Copiar")
  • copiedText?: string - Texto al copiar (default: "✓ Copiado")
  • onCopy?: (value: string) => void - Callback al copiar

Ejemplo:

<ModalCopyInput 
  value="https://streamyard.com/abc123"
  buttonText="Copiar enlace"
/>

4. ModalShareButtons

Botones para compartir por diferentes medios (Gmail, Email, Messenger).

Props:

  • onGmail?: () => void - Acción para Gmail
  • onEmail?: () => void - Acción para Email
  • onMessenger?: () => void - Acción para Messenger
  • customButtons?: ShareButton[] - Botones personalizados

Ejemplo:

<ModalShareButtons
  onGmail={() => window.open('...')}
  onEmail={() => window.location.href = 'mailto:...'}
  onMessenger={() => console.log('Messenger')}
/>

5. ModalToggle

Toggle switch con estilo Material + icono de ayuda opcional.

Props:

  • checked: boolean - Estado del toggle
  • onChange: (checked: boolean) => void - Callback al cambiar
  • label: string - Texto descriptivo
  • helpText?: string - Texto de ayuda
  • helpLink?: string - URL de ayuda

Ejemplo:

<ModalToggle
  checked={enabled}
  onChange={setEnabled}
  label="Los invitados pueden transmitir a sus destinos"
  helpLink="https://support.example.com/article"
/>

Uso Completo

import React, { useState } from 'react'
import { Modal } from './Modal'
import { 
  ModalLink, 
  ModalCopyInput, 
  ModalShareButtons, 
  ModalToggle 
} from './modal-parts'

const MyModal: React.FC<Props> = ({ open, onClose, inviteLink }) => {
  const [allowGuests, setAllowGuests] = useState(true)

  return (
    <Modal
      open={open}
      onClose={onClose}
      title="Invitar colaboradores"
      width="md"
    >
      <div style={{ display: 'flex', flexDirection: 'column', gap: '16px' }}>
        <p style={{ color: '#5f6368', fontSize: '14px' }}>
          Comparte este enlace. Lee las{' '}
          <ModalLink href="/instructions">
            instrucciones para invitados
          </ModalLink>.
        </p>

        <ModalCopyInput value={inviteLink} />

        <ModalShareButtons
          onGmail={() => window.open(`https://mail.google.com/...`)}
          onEmail={() => window.location.href = `mailto:...`}
        />

        <ModalToggle
          checked={allowGuests}
          onChange={setAllowGuests}
          label="Permitir que invitados transmitan"
          helpLink="/help/guest-permissions"
        />
      </div>
    </Modal>
  )
}

Diseño y Estilo

Colores (Light Mode)

  • Primary Blue: #1a73e8 (botones principales, links, hover)
  • Text Primary: #202124
  • Text Secondary: #5f6368
  • Border: #dadce0
  • Background: #ffffff
  • Hover Background: #f1f3f4

Colores (Dark Mode)

  • Primary Blue: #8ab4f8
  • Text Primary: #e8eaed
  • Text Secondary: #9aa0a6
  • Border: #5f6368
  • Background: #2d2e30
  • Hover Background: #3c4043

Espaciado

  • Gap entre elementos: 16px
  • Padding body: 24px
  • Padding header/footer: 20-24px

Tipografía

  • Título: 16px normal (no bold)
  • Body text: 14px
  • Line height: 1.4-1.5

Ventajas del Sistema

Reutilizable: Cada componente es independiente
Consistente: Diseño uniforme basado en StreamYard
Mantenible: Cambios centralizados en un solo lugar
Flexible: Combina componentes según necesidad
Accesible: Soporte keyboard, ARIA labels, focus management
Responsive: Adaptable a mobile y desktop
Dark Mode: Soporte completo de theming

Archivos

src/components/
├── Modal.tsx                    # Componente base
├── Modal.module.css
├── modal-parts/
│   ├── index.ts                 # Exportaciones
│   ├── ModalLink.tsx
│   ├── ModalLink.module.css
│   ├── ModalCopyInput.tsx
│   ├── ModalCopyInput.module.css
│   ├── ModalShareButtons.tsx
│   ├── ModalShareButtons.module.css
│   ├── ModalToggle.tsx
│   └── ModalToggle.module.css
├── InviteGuestsModal.tsx        # Implementación real
├── ExampleModal.tsx             # Ejemplo de uso
└── ...

Próximos Pasos

  • Agregar más variantes de botones (outlined, text)
  • Componente ModalSelect para dropdowns
  • Componente ModalTextarea para texto largo
  • Animaciones de transición entre secciones
  • Tests unitarios para cada componente