# Devlog del Proyecto: Masmorres (Physical-Web Crawler)

Este documento sirve para llevar un control diario del desarrollo, decisiones técnicas y nuevas funcionalidades implementadas en el proyecto.

## [2025-12-29] - Sistema Avanzado de Mapeo de Tiles

### Funcionalidades Implementadas
- **TileDefinitions.js:** Nuevo módulo centralizado con definiciones de todas las tiles (rooms, corridors, L-shapes, T-junctions).
  - Cada tile incluye: dimensiones, tipo, imagen, matriz de walkability, y exits.
  - Matriz de walkability: 0 = no pisable, 1-8 = pisable con capa/altura, 9 = escaleras.
  
- **Sistema de Deck Abstracto:**
  - El deck ahora contiene tipos abstractos (e.g., 'L', 'corridor') en lugar de tiles específicas.
  - Composición: 8 rooms 4x4, 4 rooms 4x6, 12 corridors, 10 L-shapes, 8 T-junctions.
  - Cuando se dibuja un tipo, el sistema selecciona aleatoriamente entre las variantes que encajan.

- **Validación de Conexiones:**
  - `canConnectTiles()`: Verifica compatibilidad de tipos, dirección de salidas, y alineación de walkability.
  - Reglas de conexión: Rooms ↔ Rooms/Corridors, Corridors ↔ Rooms/Corridors/L/T, L/T ↔ Corridors.
  - Validación de dirección: Si sales por N, la nueva tile debe tener salida S.

- **Alineación de Walkability:**
  - `validateWalkabilityAlignment()`: Maneja tiles de diferentes tamaños (corridor 2x6 vs room 4x4).
  - Prueba offset 0 primero, luego offset 2 (ancho del corridor) si es necesario.
  - Sistema de offset para desplazar L-shapes y T-junctions y alinear áreas pisables.

- **Filtrado de Orientación:**
  - Corridors se filtran por orientación: puertas E/W requieren corridors EW, puertas N/S requieren corridors NS.
  - Selección exhaustiva: Cuando se dibuja una L o T, se prueban todas las variantes antes de descartar.

### Cambios Técnicos
- Modificado `DungeonDecks.js` para usar sistema de deck abstracto.
- Actualizado `exploreRoom()` en `main.js` para trabajar con tipos abstractos y seleccionar variantes concretas.
- Nuevas funciones: `validateWalkabilityAlignment()`, `canConnectTiles()`, `getEdgeCells()`, `shouldPlaceDoor()`.
- Actualizado `renderRoom()` para usar `room.tileDef` en lugar de `ASSETS.tiles`.

### Problemas Conocidos
- **Offset de L/T:** La alineación de L-shapes y T-junctions todavía presenta desplazamientos incorrectos en algunos casos.
- **Frecuencia de L/T:** Aunque se aumentó la cantidad en el deck, las L y T solo aparecen cuando se conectan desde corridors, limitando su frecuencia.

### Próximos Pasos
- Depurar y corregir el cálculo del offset para L-shapes y T-junctions.
- Revisar la lógica de aplicación del offset según la dirección de conexión (N/S vs E/W).
- Considerar ajustar las reglas de conexión para permitir más variedad en la generación.

## [2025-12-28] - Fase 1: Arquitectura Híbrida y Servidor

### Infraestructura
- **Game Server (`game-server.js`):** Implementado servidor WebSocket (Socket.io) en puerto 3001 para gestionar la comunicación PC-Móvil.
- **Docker:** Actualizado `docker-compose.yml` para ejecutar el servidor juego como servicio independiente.
- **Networking:** Configuración dinámica de IP en el cliente para permitir conexión desde dispositivos en la red local.

### Datos
- **Esquemas JSON:** Definidos contratos de datos iniciales en `src/schemas/`:
  - `CampaignSchema.js`: Estructura para campañas multijugador.
  - `MissionSchema.js`: Configuración para generación procedural y scripting.

## [2025-12-28] - Corrección Completa del Sistema de Puertas

### Funcionalidades Implementadas
- **Refactorización de Posicionamiento de Puertas:**
  - Creada función unificada `getDoorWorldPosition()` que centraliza el cálculo de posiciones.
  - Eliminada duplicación de lógica entre generación de huecos en paredes y posicionamiento de meshes de puertas.
  - Reducción de ~45 líneas de código duplicado.

- **Corrección de Alineamiento E/W:**
  - Identificado problema: Las paredes Este y Oeste tienen `rotation = π/2`, lo que hace que su eje X local apunte hacia -Z.
  - Solución: Invertir el `wallOffset` para ambas paredes E/W: `wallOffset = -(doorWorldPos.z - centerZ)`.
  - **Resultado:** Puertas y huecos perfectamente alineados en todas las direcciones (N, S, E, W).

- **Corrección de Interacción con Puertas Abiertas:**
  - Problema detectado: Las puertas abiertas (invisibles) seguían bloqueando clics del ratón.
  - Solución: Filtrar puertas invisibles del raycast: `allDoors.push(...roomData.doors.filter(door => door.visible))`.
  - **Resultado:** Los jugadores ahora pueden hacer clic "a través" de puertas abiertas para seleccionar baldosas.

### Cambios Técnicos
- Nueva función `getDoorWorldPosition(room, door, centerX, centerZ, halfSizeX, halfSizeZ)`:
  - Devuelve: `{ worldPos, meshPos, rotation, wallOffset }`
  - Garantiza coherencia entre geometría de huecos y meshes visuales.
- Modificado raycast de puertas para excluir meshes invisibles (línea 1388).
- Commits: `8025d66`, `5852a97`, `57f6312`.

### Lecciones Aprendidas
- **Geometría Rotada:** Cuando un `PlaneGeometry` se rota (e.g., π/2), su sistema de coordenadas local cambia. Es crucial calcular offsets considerando la dirección del eje X local tras la rotación.
- **Raycast e Invisibilidad:** `mesh.visible = false` solo oculta visualmente un objeto, pero Three.js sigue detectándolo en raycasts. Siempre filtrar objetos invisibles antes de `intersectObjects()`.

## [2025-12-23] - Interacción con Puertas y Navegación

### Funcionalidades Implementadas
- **Sistema de Puertas Interactivas:**
  - Se eliminó la transición automática entre salas al pisar una puerta.
  - Ahora las puertas actúan como bloqueos físicos hasta que son "abiertas" explícitamente.
  - Lógica de selección: Click en una puerta cerrada para seleccionarla (feedback visual amarillo).
  - **Modal de Interacción:** 
    - Al mover una unidad adyacente a una puerta seleccionada, se dispara un modal UI: "¿Quieres abrir la puerta?".
    - **Confirmar:** La puerta visual se oculta, la sala destino se renderiza (si no lo estaba) y se permite el paso.
    - **Cancelar:** Se deselecciona la puerta y se mantiene cerrada.

### Cambios Técnicos
- Modificado `main.js` para incluir `checkDoorInteraction` al finalizar el movimiento.
- Nuevo estado en `SESSION`: `selectedDoorId`.
- Actualización de `isWalkable` para considerar el estado `isOpen` de las puertas.

## [2025-12-20] - Sistema Visual Dinámico (Dynamic Wall Opacity)

### Funcionalidades Implementadas
- **Opacidad de Muros Contextual:**
  - Los muros ahora ajustan su opacidad dinámicamente basándose en la rotación de la cámara (N, S, E, W) para evitar obstruir la visión del jugador.
  - **Regla General:** Los muros "frontales" a la cámara se vuelven semitransparentes (50%), mientras que los "traseros" permanecen opacos.

### Cambios Técnicos
- Implementada función `getWallOpacity(wallSide, viewDirection)`.
- Integración en `setCameraView` para refrescar opacidades al girar la vista.
- Los muros ahora tienen la propiedad `userData.wallSide` asignada durante la generación.

## [2025-12-19] - Feedback de Selección y UI

### Funcionalidades Implementadas
- **Resaltado de Selección (Highlighting):**
  - Unidades y objetos interactivos ahora muestran un aura/color amarillo al ser seleccionados.
  - Opacidad reducida al 50% para indicar estado de selección activo.
- **Mejoras de Animación:**
  - Refinamiento del "salto" de los standees al moverse entre casillas.

## [Inicio del Proyecto] - Manifiesto y Core Loop

### Visión General
- Definido el **Manifiesto Técnico (v2.0)**: Visión de un "Puente Híbrido" entre juego de mesa físico y motor narrativo digital (LLM).
- **Generación Procedural:** Algoritmo de mazmorras basado en tiles de 4x4 con expansión orgánica.
- **Motor Gráfico:** Three.js con cámara isométrica ortográfica y controles restringidos (N, S, E, W).

## [2025-12-29] Dungeon Generation Fixes
- **Alignment Fix:** Implemented explicit `doorCoordinates` for all asymmetric tiles (L, T) and corridors. This replaces the generic center-based logic and ensures precise "bit-to-bit" alignment of connections, solving visual drift and 1-cell gaps.
- **Deck Randomness Fix:** Removed a legacy debug fixed deck that was limiting the game to 7 cards.
- **Infinite Generation:** Improved `drawCompatibleCard` to automatically reshuffle the discard pile back into the deck if the current draw pile is exhausted during a search. This prevents "Could not find compatible tile" errors.
- **Balance Update:** Rebalanced the deck composition to increase room frequency (~50% rooms, ~50% paths).
