Recientemente he decidido renovar la arquitectura de mi juego para deshacerme de las jerarquías de clase profundas y reemplazarlas con componentes configurables. La primera jerarquía que estoy reemplazando es la jerarquía de elementos y me gustaría saber si estoy en el camino correcto.
Anteriormente, tenía una jerarquía que se parecía a esto:
Item -> Equipment -> Weapon
-> Armor
-> Accessory
-> SyntehsisItem
-> BattleUseItem -> HealingItem
-> ThrowingItem -> ThrowsAsAttackItem
No hace falta decir que estaba empezando a complicarse y no era una solución fácil para los artículos que necesitaban ser de varios tipos (es decir, algunos equipos se usan en la síntesis de artículos, algunos equipos son arrojables, etc.)
Luego intenté refactorizar y colocar la funcionalidad en la clase de elemento base. Pero luego me di cuenta de que el artículo tenía muchos datos no utilizados / superfluos. Ahora estoy tratando de hacer un componente como arquitectura, al menos para mis artículos antes de intentar hacerlo con mis otras clases de juego.
Esto es lo que estoy pensando actualmente para la configuración del componente:
Tengo una clase de elemento base que tiene ranuras para varios componentes (es decir, una ranura de componente de equipo, una ranura de componente de curación, etc., así como un mapa para componentes arbitrarios) así que algo como esto:
class Item
{
//Basic item properties (name, ID, etc.) excluded
EquipmentComponent* equipmentComponent;
HealingComponent* healingComponent;
SynthesisComponent* synthesisComponent;
ThrowComponent* throwComponent;
boost::unordered_map<std::string, std::pair<bool, ItemComponent*> > AdditionalComponents;
}
Todos los componentes del elemento heredarían de una clase ItemComponent base, y cada tipo de Componente es responsable de decirle al motor cómo implementar esa funcionalidad. es decir, el componente de curación le dice a los mecánicos de batalla cómo consumir el elemento como elemento de curación, mientras que el componente de lanzamiento le dice al motor de batalla cómo tratar el elemento como un elemento arrojable.
El mapa se utiliza para almacenar componentes arbitrarios que no son componentes de elementos centrales. Lo estoy emparejando con un bool para indicar si el Item Container debe administrar el ItemComponent o si está siendo administrado por una fuente externa.
Mi idea aquí era que definiera los componentes principales utilizados por mi motor de juego desde el principio, y mi fábrica de elementos asignaría los componentes que el elemento realmente tiene, de lo contrario son nulos. El mapa contendría componentes arbitrarios que generalmente serían agregados / consumidos por archivos de secuencias de comandos.
Mi pregunta es, ¿es este un buen diseño? Si no, ¿cómo se puede mejorar? Pensé en agrupar todos los componentes en el mapa, pero el uso de la indexación de cadenas parecía innecesario para los componentes principales del elemento