Componentes de objetos Registrar juego en juego subsistemas? (Diseño de objetos de juego basado en componentes)
-
08-10-2019 - |
Pregunta
Estoy creando un sistema de objetos juego basado en componentes . Algunos consejos:
-
GameObject
es simplemente una lista deComponents
. - Hay
GameSubsystems
. Por ejemplo, la representación, la física, etc. CadaGameSubsystem
contiene punteros a algunos deComponents
.GameSubsystem
es una abstracción muy potente y flexible:. que representa cualquier rebanada (o aspecto) del mundo del juego
Hay una necesidad de un mecanismo de registro de Components
en GameSubsystems
(cuando se crea GameObject
y compuesto). Hay 4 se aproxima
- 1: patrón de cadena de responsabilidad . Cada
Component
se ofrece a todos losGameSubsystem
.GameSubsystem
toma una decisión, queComponents
registrar (y cómo organizarlos). Por ejemplo, GameSubsystemRender puede registrar renderizable Components.
Pro. Components
saber nada acerca de cómo se utilizan. Bajo acoplamiento. A. Podemos añadir nueva GameSubsystem
. Por ejemplo, vamos a añadir GameSubsystemTitles que registra todos ComponentTitle y garantiza que cada título es único y proporciona una interfaz a quering objetos por título. Por supuesto, ComponentTitle no debe ser reescrito o heredado en este caso. B. Podemos reorganizar GameSubsystems
existente. Por ejemplo, GameSubsystemAudio, GameSubsystemRender, GameSubsystemParticleEmmiter se pueden combinar en GameSubsystemSpatial (para colocar todo el audio, emmiter, render Components
en la misma jerarquía y el uso de las transformadas de padres y relativa).
Con. -Cada-a cada cheque. Muy innefficient.
Con. Subsystems
conocimientos sobre Components
.
- 2:. Cada búsquedas
Subsystem
paraComponents
de tipos específicos
Pro. rendimiento mejor que en Approach 1
.
Con. Subsystems
todavía saber sobre Components
.
- 3:
Component
sí registros enGameSubsystem(s)
. Sabemos que en tiempo de compilación que hay una GameSubsystemRenderer, por lo que dejó de ComponentImageRender llamará algo así como GameSubsystemRenderer :: registro (ComponentRenderBase *).
patrón Observer . suscribeComponent
hasta el evento de "actualización" (enviado porGameSubsystem(s)
).
Pro. Actuación. No hay controles innecesarios como en Approach 1
y Approach 2
.
Con. Components
están mal acoplado con GameSubsystems
.
- 4: Modelo Mediador .
GameState
(que contieneGameSubsystems
) puede implementar registerComponent (Componente *).
Pro. Components
y conocimientos GameSubystems
nada el uno del otro.
Con. En C ++ se vería como typeid-interruptor feo y lento.
Preguntas:
¿Qué enfoque es mejor y utiliza sobre todo en el diseño basado en componentes? La práctica lo dice? Cualquier sugerencia sobre (controlada por datos-) la implementación de Approach 4
?
Gracias.
Solución
Vote por el tercer enfoque.
Actualmente estoy trabajando en el sistema de juego de objetos basado en componentes y veo claramente algunas de las ventajas adicionales de este enfoque:
-
El Componente es cada vez más subentidad basta a sí mismo, ya que sólo depende de un conjunto de subsistemas disponibles (supongo este conjunto se fija en su proyecto).
-
El diseño controlada por datos es más aplicable. Lo ideal sería que, de esta manera es posible diseñar un sistema en el que los componentes están completamente definidas en los términos de datos, pero no en C ++.
EDIT: Una característica pensaba mientras se trabaja en CBGOS. A veces es conveniente tener la capacidad para diseñar y construir subsystemless componentes pasivos. Cuando esto está en su mente el cuarto enfoque es el único camino.
Otros consejos
Mi enfoque fue implementar el patrón de proxy dentro de cada subsistema. Como cada subsistema solamente está interesado en un subconjunto de los componentes totales de cada entidad puede contener, las tiendas de proxy punteros a sólo los componentes de los cuidados del sistema acerca de, por ejemplo, un sistema de movimiento sólo se preocupa por posición y la velocidad, por lo que necesita un proxy que almacena dos punteros, a esos componentes. Si la entidad no se encuentra uno o más de esos, entonces el subsistema de la ignorará. Si ambos componentes están presentes, a continuación, un nodo proxy se crea y se añade a una colección interna. También es útil para el proxy para almacenar el valor identificador único para la entidad, de modo que proxies pueden añadirse / eliminado en un tiempo constante de cada subsistema, de ser necesario.
En tal manera, debería ser necesaria una entidad a ser retirado del motor, un solo mensaje que contiene el ID de la entidad puede ser enviado a cada subsistema. El proxy entonces se puede retirar de cada colección subsistema independiente.