# SPRINT PDF · MODO TRANSCRIPTOR · INTENTO 2

> **Para Ricci:** después de hacer el revert de los 4 commits del PDF anterior, pegá este prompt en sesión NUEVA de Claude Code. Es agresivo a propósito.

---

===PROMPT===

Hola Claude. Soy Ricci. Necesito que **transcribas** el PDF del sistema legacy de Infinia a Innovium. La iteración anterior falló porque tomaste decisiones de diseño en lugar de copiar el legacy. **Acabo de revertir esos 4 commits.** Empezamos de nuevo.

⚠️ **Cambio fundamental de mentalidad:** NO sos diseñador. NO sos arquitecto. NO sos creativo. **Sos un TRANSCRIPTOR.** Tu única tarea es copiar líneas del legacy al código nuevo cambiando solo de dónde vienen los datos.

═══════════════════════════════════════════════════════════════════
PROHIBICIONES ABSOLUTAS · violar cualquiera = ABORTAR el sprint
═══════════════════════════════════════════════════════════════════

1. ❌ **PROHIBIDO inventar nombres de secciones.**
   Las secciones se llaman EXACTAMENTE así:
   - "1. DATOS DEL CONTRATANTE"
   - "2. DATOS DEL FALLECIDO"
   - "3. DETALLES DEL SERVICIO FUNERARIO"
   - "4. COMPLEMENTO AL SERVICIO FUNERARIO"
   - "5. RESUMEN DE VALORES"
   
   NO se llaman "CONTRATANTE", NO "FALLECIDO", NO "FUNERAL Y LUGARES", 
   NO "RESUMEN ECONÓMICO", NO "SERVICIO FUNERARIO". 
   Si te tienta cambiar el nombre por uno "más limpio" o "más moderno": **NO**.

2. ❌ **PROHIBIDO inventar texto legal o párrafos propios.**
   Las notas legales son LITERALMENTE estas 5 (en este orden):
   ```
   1. La factura de los gastos se realiza a la caja de previsión correspondiente. Si procede.
   2. Para dejar o retirar documentos, el horario de atención es de 08:30 a 18:00 horas.
   3. Para licitaciones Municipales es deber del contratante gestionar el subsidio con la Municipalidad, de caso contrario el cliente deberá cancelar en forma particular.
   4. Si el cliente no hiciere uso del servicio contratado, podrá cambiarlo por otro, cederlo a un tercero, o cambiarlo por otro producto disponible pagando diferencia si existiere. No procede restitución de dinero.
   5. Todos los valores indicados NO incluyen IVA.
   ```
   NO redactes párrafo libre tipo "Por el presente instrumento, el contratante X contrata con Demo...". Eso NO está en el legacy.

3. ❌ **PROHIBIDO agregar info del tenant en el header del PDF.**
   El header NO dice "DEMO / Servicios funerarios / Sucursal: Casa Matriz".
   El header dice EXACTAMENTE:
   - Izquierda: caja redondeada con borde con "CONTRATO Nº 1149" + abajo "Fecha: ... Hora: ..."
   - Derecha: SOLO el logo del tenant (Image, sin texto)
   
   El nombre del tenant, "Servicios funerarios", "Sucursal" NO van en el header.

4. ❌ **PROHIBIDO usar texto como marca de agua.**
   La marca de agua es **`Image('img/logos/logo_full.png', 10, 50, 200, 230)`** del legacy.
   En Innovium: usar el logo del tenant cargado en /admin/configuracion (o el del tenant master si no hay).
   NO uses texto "1149" como marca de agua. NO uses líneas curvas. **Es una IMAGEN del logo.**
   Si el tenant no tiene logo cargado: omití la marca de agua (no inventes nada).

5. ❌ **PROHIBIDO dividir el contrato en 2 páginas.**
   El legacy cabe en 1 página (Carta 216×330mm). Si tu PDF está usando 2, algo posicionaste mal.
   Revisá que cada `Cell` use la altura `6` o `5` que usa el legacy, no más.

6. ❌ **PROHIBIDO agregar footer "Documento generado por Innovium · Contrato N° X · Emitido X".**
   El footer es ÚNICAMENTE: `Page X/{nb}` centrado, Arial Italic 9.
   Línea exacta del legacy: `$this->Cell(0, 6, 'Page ' . $this->PageNo() . '/{nb}', 0, 0, 'C');`

7. ❌ **PROHIBIDO usar Times serif para el body.**
   El body es Arial. Times solo para "EJECUTIVO:", "CONTRATANTE:", "NOTAS:" y los nombres de las firmas.
   Líneas exactas del legacy:
   - Body: `$pdf->SetFont('Arial', '', 9);` (regular) o `'B', 9` (bold)
   - Section title: `$pdf->SetFont('Arial', 'B', 10);`
   - Header número contrato: `$pdf->SetFont('Arial', 'B', 12);`
   - Firmas/notas: `$pdf->SetFont('Times', 'B', 9);` y `'Times', '', 9`
   - Footer: `$pdf->SetFont('Arial', 'I', 9);`

8. ❌ **PROHIBIDO unir Cofre/Urna y Servicio Funerario en secciones separadas.**
   En el legacy va TODO en sección "3. DETALLES DEL SERVICIO FUNERARIO":
   - Urna + Valor
   - Capilla + Carroza + Auto + Van + Cruz + Tarjetero
   - Libro + Tarjeta + Arreglo + Cert. Médica
   - Tramit. + Cafetería
   - MEDIDAS DEL COFRE: Alto/Ancho/Largo
   - OTROS SERVICIOS (subtítulo dentro de la sección 3)
   
   NO hagas dos secciones separadas. NO omitas OTROS SERVICIOS.

9. ❌ **PROHIBIDO omitir campos.**
   Estos campos DEBEN aparecer en el PDF (en su sección correcta):
   - Sección 1: Nombre Completo, RUT, Teléfono 1, Teléfono 2, Correo, Dirección, Parentesco
   - Sección 2: Nombre Completo, RUT, Falleció en, Edo. Civil, Nacionalidad, Fecha Nacimiento, Fecha Defunción, **Entidad Previsional, Entidad Previsional 2, Entidad Previsional 3**
   - Sección 3: Urna, Valor, Capilla, Carroza, Auto, Van, Cruz, Tarjetero, Libro Condolencias, Tarjeta Condolencias, Arreglo, Certificación Médica, Tramitación Registro Civil, Cafetería, MEDIDAS DEL COFRE, OTROS SERVICIOS
   - Sección 4: Lugar de Velación, Lugar de Sepultación, Fecha Funeral, Hora Funeral
   - Sección 5: Valor lista, Total Servicio, Aporte Previsional, Abono Cliente, Pendiente de pago + box "APORTE PREVISIONAL" detallado por entidad

10. ❌ **PROHIBIDO usar layout "moderno" para Sección 5.**
    Sección 5 tiene 2 columnas EXACTAS:
    - Izquierda (97mm): los 5 valores listados con `Cell` de altura 6
    - Derecha (97mm): box redondeado con título "APORTE PREVISIONAL:" y lista entidad/monto
    
    NO hagas tabla moderna. NO uses solo una columna. NO renombres a "RESUMEN ECONÓMICO".

═══════════════════════════════════════════════════════════════════
TU PROCESO DE TRABAJO · paso a paso
═══════════════════════════════════════════════════════════════════

### Paso 1 · Leer el legacy completo (obligatorio antes de codear)

Leé `docs/sprint-1-5a-fixes-2/LEGACY_GENERARPDF.php` LÍNEA POR LÍNEA. Las 945 líneas. **Sin saltos.**

Tu objetivo: entender que cada línea de FPDF (`Cell`, `MultiCell`, `SetFont`, `SetXY`, `Image`, `Rect`, `Ln`) tiene un equivalente directo que vas a copiar.

### Paso 2 · Mapear queries del legacy a queries de Innovium

El legacy tiene queries SQL crudas. Vos NO las copiás. Pero sí mapeás QUÉ DATOS extrae cada query a QUÉ MODEL/MÉTODO usar en Innovium.

Por ejemplo:

```php
// Legacy:
$sql = "SELECT * FROM contrato, planes, detalle_plan WHERE CONTRATO = $contrato ..."
$row = $sql->fetch_assoc();
$row['CONTRATANTE']  // → $cliente['nombres'].' '.$cliente['apellido_paterno']
$row['RUT_CONTRATANTE']  // → $cliente['rut']
$row['TELEFONO1']  // → $cliente['telefono_1']
$row['CORREO']  // → $cliente['email']
// ...etc
```

**Hacé un mapping completo en un comentario al principio del archivo `PdfGeneratorNI.php`** antes de empezar a generar.

### Paso 3 · Transcribir Header (líneas 269-323 del legacy)

Copiá ESTE bloque del legacy a tu Header() de la clase PDF:

```php
function Header()
{
    // Banda superior (gris)
    $this->SetFillColor(245, 245, 245);
    $this->Rect(0, 0, 216, 24, 'F');
    
    // Logo a la derecha (si tenant tiene logo)
    $logoPath = $this->tenantLogoPath; // path local descargado de R2 si existe
    if ($logoPath && file_exists($logoPath)) {
        $this->Image($logoPath, 175, 4, 18, 18);
    }
    
    // Caja blanca con borde para "CONTRATO Nº"
    $this->SetFillColor(255, 255, 255);
    $this->SetDrawColor(210, 210, 210);
    $this->RoundedRect(10, 5, 160, 18, 2.5, 'DF');
    
    // Texto "CONTRATO Nº 1149"
    $this->SetXY(14, 7);
    $this->SetFont('Arial', 'B', 12);
    $this->Cell(120, 6, utf8_decode("CONTRATO Nº " . $this->numeroContrato), 0, 1);
    
    // "Fecha: X Hora: Y"
    $this->SetFont('Arial', '', 9);
    $this->Cell(120, 5, utf8_decode("Fecha: {$this->fecha}   Hora: {$this->hora}"), 0, 1);
    
    $this->Ln(10);
}
```

**Mismo número, mismas coordenadas, mismos textos.** Solo cambiás de dónde vienen `numeroContrato`, `fecha`, `hora`.

### Paso 4 · Transcribir cada sección

**Para CADA `Cell()` del legacy:** escribí UN `Cell()` idéntico con los **mismos anchos numéricos**.

Ejemplo Sección 1 (línea 451+ del legacy):

```php
// LEGACY línea 452-454:
$pdf->SetFont('Arial', '', 9);
$pdf->Cell(36, 6, utf8_decode('Nombre Completo:'), 0, 0);
$pdf->SetFont('Arial', 'B', 9);
$pdf->Cell(110, 6, utf8_decode($row['CONTRATANTE']), 'B', 0);

// TU CÓDIGO debe ser literalmente:
$pdf->SetFont('Arial', '', 9);
$pdf->Cell(36, 6, utf8_decode('Nombre Completo:'), 0, 0);
$pdf->SetFont('Arial', 'B', 9);
$pdf->Cell(110, 6, utf8_decode($cliente['nombres'].' '.$cliente['apellido_paterno'].' '.($cliente['apellido_materno']??'')), 'B', 0);
```

**Mismos números: 36, 6, 0, 0, 110, 6, 'B', 0.** No los cambies.

### Paso 5 · Marca de agua (línea 419-421 del legacy)

```php
// Antes de cada AddPage, después de Header:
function watermark() {
    $logoFullPath = $this->tenantLogoFullPath; // mismo logo, tamaño grande
    if ($logoFullPath && file_exists($logoFullPath)) {
        $this->Image($logoFullPath, 10, 50, 200, 230);
    }
    // Si tenant no tiene logo: NO HAGAS NADA. NO uses texto fallback.
}
```

⚠️ **Crítico:** la imagen se inserta DESPUÉS del Header pero ANTES del contenido. Va de fondo. Para que se vea como marca de agua, FPDF tiene 2 opciones:
   a) Imagen pre-procesada con opacidad ya aplicada (PNG con alpha 12%)
   b) Usar `SetAlpha()` de fpdf-extension (si está disponible)

**Si no tenés extensión SetAlpha:** usar PNG pre-procesado. Documentar en CLAUDE.md que el logo del tenant debe subirse con opacidad ya aplicada o tener una variante "_watermark.png".

### Paso 6 · Notas legales (línea 400-417 del legacy)

```php
// Después de las firmas, ANTES del fin de página:
$this->SetFillColor(255, 255, 255);
$this->RoundedRect(10, $this->GetY(), 196, 40, 2.5, 'DF');

$this->SetXY(14, $this->GetY() + 2);
$this->SetFont('Times', 'B', 9);
$this->Cell(0, 6, utf8_decode('NOTAS:'), 0, 1);

$this->SetFont('Times', '', 9);
$notas = [
    '1. La factura de los gastos se realiza a la caja de previsión correspondiente. Si procede.',
    '2. Para dejar o retirar documentos, el horario de atención es de 08:30 a 18:00 horas.',
    '3. Para licitaciones Municipales es deber del contratante gestionar el subsidio con la Municipalidad, de caso contrario el cliente deberá cancelar en forma particular.',
    '4. Si el cliente no hiciere uso del servicio contratado, podrá cambiarlo por otro, cederlo a un tercero, o cambiarlo por otro producto disponible pagando diferencia si existiere. No procede restitución de dinero.',
    '5. Todos los valores indicados NO incluyen IVA.'
];
foreach ($notas as $n) {
    $this->SetX(14);
    $this->MultiCell(188, 4, utf8_decode($n), 0, 'L');
}
```

**Estos 5 textos son INVIOLABLES.** Copialos literal.

### Paso 7 · Firmas (línea 374-388 del legacy)

```php
// Antes de las notas:
$firma = $this->firmaPath; // path del PNG de la firma
if ($firma && file_exists($firma)) {
    $this->Image($firma, 135, $this->GetY() - 2, 60, 0, 'PNG');
}

$this->Ln(10); // espacio para que línea de firma esté debajo

$this->SetFont('Times', 'B', 9);
$this->Cell(97, 5, utf8_decode('EJECUTIVO:'), 0, 0, 'C');
$this->Cell(97, 5, utf8_decode('CONTRATANTE:'), 0, 1, 'C');

$this->SetFont('Times', '', 9);
$this->Cell(97, 5, utf8_decode($vendedor['nombre']), 0, 0, 'C');
$this->Cell(97, 5, utf8_decode($cliente['nombres'].' '.$cliente['apellido_paterno']), 0, 1, 'C');

if (!empty($vendedor['telefono'])) {
    $this->Cell(97, 5, utf8_decode($vendedor['telefono']), 0, 1, 'C');
}
```

NO agregues "Firma capturada el X desde IP X". NO está en el legacy.

### Paso 8 · Footer (línea 392-393)

```php
function Footer() {
    $this->SetY(-15);
    $this->SetFont('Arial', 'I', 9);
    $this->Cell(0, 6, 'Page ' . $this->PageNo() . '/{nb}', 0, 0, 'C');
}
```

NADA más. Sin "Documento generado por...". Sin "Emitido el...".

### Paso 9 · Validación

Después de generar, abrí el PDF generado mentalmente comparando estructura con `docs/sprint-1-5a-fixes-2/PDF_INFINIA_REFERENCIA.pdf`:

- [ ] ¿1 sola página?
- [ ] ¿Header con caja "CONTRATO Nº" izq + logo der?
- [ ] ¿5 secciones numeradas con esos nombres exactos?
- [ ] ¿Marca de agua con logo (no texto "1149")?
- [ ] ¿Sección 3 tiene Urna + toggles + medidas + OTROS SERVICIOS?
- [ ] ¿Sección 5 tiene 2 columnas con APORTE PREVISIONAL detallado?
- [ ] ¿5 notas legales literales?
- [ ] ¿EJECUTIVO + CONTRATANTE en 2 columnas con líneas de firma?
- [ ] ¿"Page 1/1" centrado al pie?

Si CUALQUIERA de los checks dice NO → revisá la sección correspondiente antes de pedir validación.

═══════════════════════════════════════════════════════════════════
ANTES DE TOCAR CÓDIGO · 10 confirmaciones obligatorias
═══════════════════════════════════════════════════════════════════

Respondé uno por uno:

1. ¿Confirmás que sos TRANSCRIPTOR y no diseñador?
2. ¿Confirmás que las 5 secciones se llaman EXACTAMENTE "1. DATOS DEL CONTRATANTE", "2. DATOS DEL FALLECIDO", "3. DETALLES DEL SERVICIO FUNERARIO", "4. COMPLEMENTO AL SERVICIO FUNERARIO", "5. RESUMEN DE VALORES"?
3. ¿Confirmás que las notas son las 5 literales del legacy y NO inventás párrafos legales propios?
4. ¿Confirmás que el header NO incluye "DEMO/Servicios funerarios/Casa Matriz"?
5. ¿Confirmás que la marca de agua es `Image()` del logo, no texto?
6. ¿Confirmás que TODO cabe en 1 página y NO usás 2?
7. ¿Confirmás que el footer es ÚNICAMENTE "Page X/{nb}" centrado?
8. ¿Confirmás que vas a copiar las coordenadas EXACTAS del legacy (Cell con anchos 36, 110, 12, 30, 18, 33, 14, 70, 16, 170, 168, etc.)?
9. ¿Confirmás que la sección 5 tiene 2 columnas con APORTE PREVISIONAL detallado en columna derecha?
10. ¿Confirmás que después de generar el PDF, vas a recorrer el checklist de 9 ítems del Paso 9 antes de pedir validación?

═══════════════════════════════════════════════════════════════════
COMMITS · solo 4 esta vez (no 7 como antes)
═══════════════════════════════════════════════════════════════════

1. `chore(deps): install fpdf` (si lo desinstalaron en el revert)
2. `feat(pdf): PdfGeneratorNI con FPDF transcribiendo legacy 1:1`
   (UN solo commit con TODO: helpers, header, footer, secciones, notas, firmas, marca agua)
3. `test: PDF tiene secciones y notas legales correctas`
4. `chore: sprint pdf-replica cerrado`

═══════════════════════════════════════════════════════════════════
DEFINITION OF DONE
═══════════════════════════════════════════════════════════════════

NO consideres este sprint cerrado hasta que VOS MISMO recorrás el checklist de 9 ítems del Paso 9 y CONFIRMÉS los 9 con ✓. Si alguno está con ✗ → seguí trabajando, no me pidas validación visual con el PDF a medias.

Cuando los 9 estén ✓, mostrame:
- El PDF generado (path)
- El checklist con los 9 ✓
- `git log --oneline | head -8`

Recién ahí Ricci hace la validación visual final lado a lado con `PDF_INFINIA_REFERENCIA.pdf`.

¡Empezá leyendo el legacy completo!

===FIN DEL PROMPT===
