# Proyecto UI U-Tad **[Read in English](README.md)** | **Español** --- ## Implementación del Sistema de Árbol de Habilidades ### Resumen Un sistema completo de árbol de habilidades con progresión basada en nodos, validación de prerrequisitos, líneas de conexión visuales y configuración orientada a datos. ![Overview 1](Docs/Images/Overview_1.png) --- ## Arquitectura: Decisión de Blueprint ### Implementación en Blueprint **Componentes:** `WBP_SkillTree`, `WBP_SkillNode`, `WBP_SkillNodeTooltip` **Justificación:** - **Velocidad de iteración**: El diseño y estilización de UI requiere iteración visual rápida - **Amigable para diseñadores**: Artistas/diseñadores pueden modificar la UI sin conocimientos de C++ ![Decision Blueprint 1](Docs/Images/DecisionBlueprint_1.png) --- ## Sistemas Principales ### 1. Capa de Datos (`SkillTreeTypes.h`) **Estructuras:** - `FSkillNodeData`: Fila de definición de habilidad para la tabla de datos (nombre, coste, prerrequisitos, efectos, bandera de inicio) - `FSkillNodeRuntime`: Envoltorio de estado en tiempo de ejecución - `ESkillNodeState`: Enum de estado (Bloqueado, Disponible, Seleccionado, Comprado) **Decisión**: El diseño basado en Data Table permite a no programadores configurar habilidades sin recompilar. ![Data Layer 1](Docs/Images/DataLayer_1.png) ### 2. Capa de Lógica (`SkillTreeComponent`) **Responsabilidades:** - Inicialización del árbol de habilidades desde DataTable - Gestión de estado (prerrequisitos, comprobaciones de asequibilidad) - Validación de selección y confirmación de compra - Auto-compra de habilidades iniciales - Gestión de puntos de habilidad - Ganchos de aplicación de efectos **Características Clave:** - **Ordenación por orden de compra**: Asegura que los prerrequisitos se compren antes que los dependientes - **Deselección en cascada**: Eliminar un prerrequisito deselecciona las habilidades dependientes - **Habilidades iniciales**: Marcadas en DataTable, auto-compradas en init, preservadas en reset - **Agregación de estadísticas**: Proporciona funciones `GetTotal[Stat]Bonus()` para sumar bonificaciones de todas las habilidades compradas ### 3. Capa de Integración de Estadísticas (`CharacterStatsComponent`) **Responsabilidades:** - Cálculo automático de estadísticas desde habilidades compradas - Gestión de estadísticas del personaje (Salud, Daño, Velocidad) - Actualizaciones en tiempo real cuando se compran habilidades - Integración con velocidad de movimiento **Cómo funciona:** - Encuentra SkillTreeComponent en el mismo actor en BeginPlay - Escucha el evento `OnSkillPurchased` - Itera todas las habilidades compradas, suma bonificaciones planas + porcentuales - Aplica fórmula: `StatFinal = Base + BonusPlano + (Base * BonusPorcentual / 100)` - Auto-actualiza la velocidad de CharacterMovementComponent - Emite eventos de cambio de estadísticas para actualizaciones de UI **Decisión**: Un componente de estadísticas separado mantiene las responsabilidades separadas - SkillTreeComponent maneja la progresión, CharacterStatsComponent maneja la aplicación de estadísticas. Hace ambos reutilizables independientemente. ### 4. Capa de Visualización (`SkillTreeConnectionsWidget`) **Responsabilidades:** - Dibujado automático de líneas entre nodos prerrequisito (¡Solo necesitas colocar los nodos en la UI!) - Coloreado dinámico de líneas basado en estados de habilidades - Refresco basado en eventos cuando cambian los estados **Enfoque Técnico:** - **Búsqueda genérica**: Funciona con cualquier jerarquía de widgets para que diseñadores/artistas no estén limitados al crear el widget del árbol de habilidades (Canvas, Overlay, Grid) - **Override de NativePaint**: Renderizado directo con Slate para rendimiento - **Binding de delegados**: Se refresca automáticamente cuando cambian los estados de las habilidades **Decisión**: Un único widget auto-contenido elimina la gestión manual de líneas y complejidad de Blueprint.

Lines 1 Lines 1

### 5. Capa de UI (Blueprints) **WBP_SkillNode & WBP_SkillNodeTooltip:** - Muestra icono de habilidad, estado, coste - Maneja eventos de clic (seleccionar/deseleccionar) - Almacena SkillID para búsqueda en tiempo de ejecución - Soporte de tooltip personalizado para mostrar detalles de habilidad - Actualizaciones de estado en tiempo real mediante binding de eventos permiten feedback visual instantáneo **WBP_SkillTree:** - Contiene nodos de habilidad colocados manualmente - Referencia a SkillTreeComponent - Aloja SkillTreeConnectionsWidget que dibuja líneas entre nodos automáticamente - Se vincula a eventos del componente para actualizaciones de UI **Decisión**: La colocación manual de nodos permite diseños personalizados (lineal, radial, ramificado) según preferencia del diseñador. --- ## Decisiones Clave de Diseño ### 1. Prerrequisitos de habilidades en DataTable **Alternativa**: Hard-coded en C++ o referencias a DataAssets **Elegido**: Array en DataTable **Razón**: Los diseñadores pueden modificar dependencias de habilidades sin intervención del programador y sin recompilar ### 2. Componente vs Subsistema **Alternativa**: Game Instance Subsystem **Elegido**: Actor Component **Razón**: Soporta múltiples árboles de habilidades por jugador (ej., árbol de combate, árbol de crafteo) y más fácil integración con guardar/cargar ### 3. Widget de Conexiones Único **Alternativa**: Widgets de línea individuales por conexión con gestión manual **Elegido**: Un widget dibuja todas las líneas automáticamente **Razón**: Elimina gestión de arrays, mejor rendimiento, manejo automático de coordenadas ### 4. Componente de Estadísticas Separado **Alternativa**: Aplicar estadísticas directamente en SkillTreeComponent **Elegido**: CharacterStatsComponent separado **Razón**: Separación de responsabilidades - SkillTreeComponent es reutilizable para cualquier sistema de progresión, CharacterStatsComponent específicamente maneja estadísticas de personaje. Permite árboles de habilidades sin bonificaciones de stats, o stats sin árboles de habilidades. --- ## Aspectos Técnicos Destacados - **Arquitectura basada en eventos**: El componente emite cambios de estado, la UI responde automáticamente - **Validación de máquina de estados**: Previene transiciones inválidas (ej., no se pueden seleccionar habilidades bloqueadas) - **Aplicación automática de estadísticas**: CharacterStatsComponent escucha compras de habilidades, recalcula estadísticas, las aplica al personaje - **Renderizado consciente de geometría**: Las líneas se adaptan a cualquier sistema de posicionamiento de widgets - **Configuración orientada a datos**: Cero cambios de código y no necesita compilar para nuevas habilidades o diseños de árbol - **Funcionalidad de reinicio**: Reembolsa habilidades no iniciales, mantiene puntos de inicio - **Diseño modular**: Progresión de habilidades, estadísticas y visualización son independientes