Как избежать глобального государства - PullRequest
2 голосов
/ 07 марта 2009

В настоящее время я пишу приложение. Если я хочу избежать Singletons, я должен просто передать ссылки всего вокруг?

Например,

У меня есть "основной" класс.
Класс: Основной
+ ---- Экран
+ ---- камера
+ ---- Рельеф
+ ---- Автомобиль
+ ---- PhysicsWorld

Содержит классы «Моя камера», «Ландшафт», «Автомобиль» и т. Д. Теперь у меня есть проблемы при создании, скажем, объекта Terrain. Terrain хочет получить доступ к основным классам объекта Screen, чтобы он мог добавить свою графику Terrain на экран. Он также хочет знать об объекте Camera для того, когда он рисует, поэтому он знает, в каком масштабе его нарисовать. Он также хочет знать о моем объекте PhysicsWorld, чтобы он мог добавить себя в физический движок.

Должен ли я всегда тащить эти объекты назад и вперед между конструкторами? Я имею в виду, когда я создаю объект Terrain, мне просто нужно обойти мой экранный объект, мой физический мир, камеру и т. Д.?

Другой случайный сценарий, который у меня есть, теперь ... внутри моего класса Vehicle мне нужно вызвать метод Restart () в моем классе Main. Значит ли это, что я должен передать экземпляр main в Vehicle? На самом деле ??

Мне неудобно постоянно передавать 4-5 вещей моим классам, особенно в моем сценарии, когда почти каждому имеющемуся в игре объекту нужен экран, физика, информация о камере и т. Д.

Есть предложения?

Ответы [ 4 ]

2 голосов
/ 07 марта 2009

Чувствовать себя постоянно передать 4-5 вещей на мои занятия, особенно в моем сценарии сейчас, где почти каждый внутриигровой объект у меня есть нужен экран, физика, информация о камере, и т.п. Тогда правильный вопрос: «зачем мне все 5 объектов во всех моих классах?» Почему на Земле каждый объект в gmae нуждается в какой-либо из упомянутых вещей? Игровому объекту нужна позиция и все, что ему нужно для обработки своего поведения. Тогда отдельный рендерер может, вы знаете, визуализировать объект. Это означает, что только визуализатор нуждается в информации и экране камеры.

Физика может пойти в любую сторону. У вас может быть отдельный физический объект, который обновляет игровой объект, или вы можете передать этот физический объект каждому игровому объекту. Но даже если вы передадите это, мы дошли до одного из трех перечисленных объектов. :)

Вот почему глобалы и синглтоны часто лучше избегать. Они маскируют ваши зависимости, так что вы получите гораздо больше зависимостей между вашими объектами, чем вам действительно нужно. И тогда становится почти невозможно удалить глобалы.

Однако, если вы придерживаетесь глобалов, сделайте себе одолжение и, по крайней мере, избегайте одиночных игр. Вам не нужны дополнительные ограничения, навязанные синглтоном.

Местность хочет получить доступ к основным классам Экран объекта, чтобы он мог добавить свой Графика местности на экран. Это также хочет знать о камере объект, когда он рисует так знает, в каком масштабе его нарисовать. Это также хочет знать о моем PhysicsWorld объект, чтобы он мог добавить себя в физический движок.

Объект местности должен знать одну вещь: какова местность. Кто-то другой может взять на себя ответственность за это. Кто-то должен знать о камере, экране и графике местности, что говорит о том, что тот же объект может правдоподобно выполнять другие задачи, связанные с этими объектами (например, другие задачи рендеринга). Почему ландшафт должен заботиться о том, в каком масштабе он нарисован? Нужно знать масштаб игры, а не масштаб в пространстве камеры. И почему кто-то еще не может добавить местность к физическому движку? Основная функция может сделать это даже. Создайте ландшафт, создайте физический движок, зарегистрируйте ландшафт с помощью физического движка, запустите игру.

1 голос
/ 07 марта 2009

Я не знаю ActionScript, но при условии, что переменные передаются по ссылке, минимум, что вы можете сделать, это создать класс «Environment», содержащий Camera, Screen, Terrain, PhysicsWorld, который вы передаете экземплярам.

0 голосов
/ 29 мая 2009

Я предлагаю вам взглянуть на примеры проектов XNA (google it). Они хорошо продуманы и могут дать вам несколько советов.

Кроме того, поскольку вы используете AS3, вы можете использовать систему событий для отправки сообщений другим объектам. Например, вместо того, чтобы передавать свой Main в класс Vehicle, сделайте Main (или что-либо еще заинтересованное) слушателем вашего класса Vehicle. Затем, скажем, автокатастрофа, и вы хотите перезапустить игру, отправив событие, например, CAR_CRASHED. Слушатели вашего автомобиля должны сделать что-то на основе этого сообщения. Если вы хотите понять систему событий, введите EventDispatcher, выделите ее и нажмите F1 в вашей IDE Flash.

0 голосов
/ 07 марта 2009

У меня точно такая же проблема (также в ActionScript 3, по совпадению).

Я работал над RTS для flash и обнаружил, что мне нужно передать большое количество ссылок на каждый новый класс (например, gameGrid, currentSelection, visibleUnits и т. Д.).

В конце концов я понял, что на самом деле мне нужно, чтобы каждый класс поддерживал свои собственные свойства и вместо этого передавал ссылки на эти классы (хорошо объекты).

Но в любом случае, сейчас я делаю статические переменные, содержащие ссылки на часто используемые объекты, такие как основная сцена, интерфейс, движок и область отображения внутри класса RTSGlobals. Я также помещаю туда константы, такие как размер экрана.

Я знаю, что это на самом деле не отвечает на ваш вопрос, но я полагаю, что иногда стоит игнорировать немного хорошей практики ООП в пользу эффективного решения.

Если у кого-то есть подходящее решение, пожалуйста, скажите:)

...