Регистрация игровых объектов Компоненты в игровых подсистемах? (Дизайн объекта на основе компонентов)
-
08-10-2019 - |
Вопрос
Я создаю А. Система игровой системы на основе компонентов. Отказ Некоторые советы:
GameObject
просто списокComponents
.- Есть
GameSubsystems
. Отказ Например, рендеринг, физика и т. Д. КаждыйGameSubsystem
содержит указатели на некоторые изComponents
.GameSubsystem
Очень мощная и гибкая абстракция: он представляет собой любой ломтик (или аспект) игрового мира.
Есть необходимость в механизме регистрации Components
в GameSubsystems
(когда GameObject
создается и составлен). Есть 4 подхода:
- 1: Цепочка ответственности шаблон. Каждый
Component
предлагается каждомуGameSubsystem
.GameSubsystem
принимает решение, котороеComponents
зарегистрироваться (и как их организовать). Например, GameSubsystemrender может зарегистрировать рендерируемые компоненты.
пропитывать Components
Ничего не знаю о том, как они используются. Низкое сцепление. А. Мы можем добавить новые GameSubsystem
. Отказ Например, давайте добавим gamesubsystemttles, которые регистрируются все компоненты и гарантируют, что каждый заголовок уникален и обеспечивает интерфейс для взыскания объектов по названию. Конечно, ComponentTitle не следует переписать или унаследовать в этом случае. Преступность Мы можем реорганизовать существующие GameSubsystems
. Отказ Например, GameSubsystemaudio, GameSubsystemrender, GameSubsystemparticlemmmiticle может быть объединен в GamesBsystemsPatial (чтобы разместить все аудио, Emmiter, Render Components
в той же иерархии и используйте родительские преобразования).
против. Каждый на каждый чек. Очень innefficed.
против. Subsystems
знать о Components
.
- 2: каждый
Subsystem
searches forComponents
конкретных типов.
пропитывать Лучшая производительность, чем в Approach 1
.
против. Subsystems
все еще знаешь о Components
.
- 3:
Component
регистрирует себя вGameSubsystem(s)
. Отказ Мы знаем во время компиляции, что есть GamebssystemRenderer, поэтому давайте pletommagerAgerender позвонит что-то вроде GamebsubsystemRenderer :: Регистр (ComponentRenderBase *).
Наблюдатель шаблон.Component
Подписки на мероприятие «Обновить» (отправленоGameSubsystem(s)
).
пропитывать Представление. Нет ненужных чеков, как в Approach 1
а также Approach 2
.
против. Components
сильно связаны с GameSubsystems
.
- 4: Посредник шаблон.
GameState
(который содержитGameSubsystems
) Может реализовать registercomponent (компонент *).
пропитывать Components
а также GameSubystems
ничего не знаю друг о друге.
против. В C ++ он будет выглядеть как уродливый и медленный выключатель типа.
Вопросы:Какой подход лучше и в основном используется в компонентском дизайне? Какая практика говорит? Любые предложения о внедрении (Data-Data) Approach 4
?
Спасибо.
Решение
Голосуйте за третий подход.
В настоящее время я работаю над компонентной игрой объектной системой, и я ясно вижу некоторые дополнительные преимущества этого подхода:
Компонент является все более и более самообеспеченным подсерением, поскольку это зависит только от набора доступных подсистем (я предполагаю, что этот набор фиксируется в вашем проекте).
Дизайн, ориентированная на данных, более применимо. В идеале, таким образом, вы можете разработать систему, где компоненты полностью определены в условиях данных, но не C ++.
Редактировать: Одной из функций, о котором я думал, работая над CBGOS. Иногда удобно иметь способность к дизайну и конструировать подсистемный пассивные компоненты. Когда это у вас на уме, четвертый подход является единственным способом.
Другие советы
Мой подход должен был реализовать узор прокси в каждой подсистеме. Поскольку каждая подсистема заинтересована только подмножеством общего количества компонентов, каждая сущность может содержать, прокси хранит указатели только к компонентам, которые система заботится о том, например, система движения заботится о положении и скорости, поэтому требуется прокси, который хранится два указателя, к этим компонентам. Если объект отсутствует один или несколько из них, то подсистема будет игнорировать ее. Если оба компонента присутствуют, то прокси-узел создается и добавляется к внутренней коллекции. Это также полезно для прокси хранить уникальное значение идентификатора для объекта, так что прокси могут быть добавлены / удалены в постоянное время из каждой подсистемы, если это необходимо.
Таким образом, необходимо будет удалить сущность от двигателя, одно сообщение, содержащее идентификатор объекта, может быть отправлено в каждую подсистему. Затем прокси можно удалить из каждой коллекции подсистемы самостоятельно.