Связь с событиями в игровом движке: да или нет?

Я читаю Кодирование игры , и автор рекомендует Событие Управляемая связь между игровыми объектами и модулями.

В принципе, все участники живых игр должны общаться с ключевыми модулями (физика, AI, игровая логика, игровой режим и т. д.) с помощью внутренней системы обмена сообщениями. Это означает необходимость разработки эффективного менеджера событий. Плохо спроектированная система использует циклы процессора, особенно влияя на мобильные платформы.

Это проверенный и рекомендуемый подход? Как мне решить, использовать ли его?

59 голосов | спросил Bunkai.Satori 25 Jpm1000000pmTue, 25 Jan 2011 21:47:45 +030011 2011, 21:47:45

8 ответов


45

Это расширение мой комментарий до полного ответа, как было предложено.

Да , простой и простой. Коммуникация должна произойти, и в то время как есть ситуации, когда «Мы еще там?» требуется опрос типа, проверяя, должны ли они делать что-то еще, обычно теряя время. Вместо этого вы можете реагировать на то, что им говорят. Кроме того, четко определенный путь связи между объектами /системами /модулями значительно увеличивает параллельные настройки.

Я дал обзор на высоком уровне системы сообщений о событиях over on Stack Overflow . Я использовал его из школы в профессиональные игровые титры и теперь не-игровые продукты, адаптированные к прецеденту каждый раз, конечно.

EDIT : Чтобы задать вопрос о комментариях на , как вы узнаете, какие объекты должны получить сообщение : сами объекты должны Request уведомлены о событиях. Для вашего EventMessagingSystem (EMS) потребуется Register (int iEventId, IEventMessagingSystem * pOjbect, (EMSCallback) fpMethodToUseForACallback) , а также соответствующий Unregister ( создавая уникальную запись для iEventId из указателя объекта и обратного вызова). Таким образом, когда объект хочет знать о сообщении, он может Register () с системой. Когда ему больше не нужно знать о событиях, он может Unregister () . Очевидно, что вам нужен пул этих объектов регистрации обратного вызова и эффективный способ добавления /удаления их из списков. (Я обычно использовал самонастраивающиеся массивы, причудливый способ сказать, что они отслеживают собственные распределения между пулом пулов неиспользуемых объектов и массивами, которые при необходимости меняют их размеры).

EDIT : для полностью работающей игры с циклом обновления и системой обмена сообщениями событий вы можете проверить старый школьный проект . Сообщение Stack Overflow, связанное выше, также ссылается на него.

ответил James 25 Jpm1000000pmTue, 25 Jan 2011 23:45:08 +030011 2011, 23:45:08
21

Мое мнение состоит в том, что вы должны просто начать делать свою игру и реализовать то, с чем вам удобно. По мере того как вы это сделаете, вы обнаружите, что используете несколько MVC, но не другие; события в некоторых местах, но не в других; компоненты в некоторых местах, но наследование других; чистые конструкции в некоторых местах, а крутые конструкции других.

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

ответил James 25 Jpm1000000pmTue, 25 Jan 2011 23:45:08 +030011 2011, 23:45:08
16

Лучше вопрос, какие альтернативы существуют? В такой сложной системе с правильно разделенными модулями для физики, AI и т. Д., Как еще вы можете организовать эти системы?

Передача сообщений кажется «лучшим» решением этой проблемы. Я не могу думать об альтернативах прямо сейчас. Но на практике существует множество примеров передачи сообщений. Фактически, операционные системы используют передачу сообщений для нескольких своих функций. Из Wikipedia :

  

Сообщения также обычно используются в том же смысле, что и средство межпроцессного общения; другой общий метод - это потоки или трубы, в которых данные отправляются как последовательность элементарных элементов данных (более высокая версия виртуальной схемы).

(Interprocess communication - это связь между процессами (например, запуском экземпляров программ) в среде операционной системы)

Итак, если он достаточно хорош для операционной системы, вероятно, он достаточно хорош для игры, верно? Есть и другие преимущества, но я позволю Wikipedia статья о передаче сообщений объясняет.

Я также задал вопрос о переполнении стека, «Структуры данных для сообщение, проходящее внутри программы? ", которое вы, возможно, захотите прочитать.

ответил Ricket 25 Jpm1000000pmTue, 25 Jan 2011 21:57:45 +030011 2011, 21:57:45
14

Сообщения обычно хорошо работают, когда:

  1. Вещь, отправляющая сообщение, не заботится о ее получении.
  2. Отправитель не должен получать немедленный ответ от получателя.
  3. Возможно, несколько приемников прослушивают одного отправителя.
  4. Сообщения будут отправляться нечасто или непредсказуемо. (Другими словами, если каждый объект должен получать сообщение «обновление» каждый отдельный кадр, сообщения на самом деле не покупают вас много.)

Чем больше ваши потребности совпадают с этим списком, тем лучше будут подходящие сообщения. На очень общем уровне они довольно хороши. Они делают хорошую работу, не тратя впустую циклы процессора, чтобы ничего не делать в отличие от опроса или других более глобальных решений. Они фантастичны в развязке частей кодовой базы, что всегда полезно.

ответил munificent 11 FebruaryEurope/MoscowbFri, 11 Feb 2011 01:09:29 +0300000000amFri, 11 Feb 2011 01:09:29 +030011 2011, 01:09:29
4

Хорошо, я знаю, что этот пост довольно старый, но я не мог устоять.

Недавно я создал игровой движок. Он использует 3d сторонние библиотеки для рендеринга и физики, но я написал основную часть, которая определяет и обрабатывает сущности и логику игры.

Двигатель, безусловно, следует традиционному подходу. Существует основной цикл обновления, который вызывает функцию обновления для всех объектов. Коллизии напрямую сообщаются обратным вызовом для объектов. Связь между объектами осуществляется с помощью интеллектуальных указателей, обмениваемых между объектами.

Существует примитивная система сообщений, которая обрабатывает только небольшую группу сущности для сообщений двигателя. Эти сообщения предпочтительнее обрабатывать в конце игрового взаимодействия (пример - создание или уничтожение сущности), поскольку они могут взаимодействовать с списком обновлений. Таким образом, в конце каждого игрового цикла потребляется небольшой список сообщений.

Несмотря на примитивную систему сообщений, я бы сказал, что система в основном «основана на петле обновления».

Ну. После использования этой системы я считаю, что это очень просто, быстро и хорошо организовано. Логика игры видна и самосохраняется внутри объектов, а не динамична, как сообщение quewe. Я бы не стал делать это событием, потому что, на мой взгляд, системы событий вводят излишнюю сложность в логику игры и делают код игры очень трудным для понимания и отладки.

Но я также считаю, что чистая система, основанная на циклах обновления, такая же, как моя, тоже имеет некоторые проблемы.

Например, в некоторые моменты одна сущность может находиться в состоянии «ничего не делать», может ожидать приближения игрока или чего-то еще. В большинстве случаев объект сжигает процессорное время ни за что, и лучше отключить объект и включить его, когда произойдет определенное событие.

Итак, в моем следующем игровом движке я собираюсь принять другой подход. Сущности будут регистрироваться для операций двигателя, таких как обновление, рисование, обнаружение столкновения и т. Д. Каждое из этих событий будет иметь отдельные списки интерфейсов сущностей для реальных объектов.

ответил Artur Correa 3 MarpmSat, 03 Mar 2012 22:16:12 +04002012-03-03T22:16:12+04:0010 2012, 22:16:12
3

Отличные ответы до сих пор от Джеймса и Рикета, я только отвечаю, чтобы добавить примечание о предостережении. Передача сообщений /событийная связь, безусловно, является важным инструментом в арсенале разработчика, но ее легко можно использовать. Когда у вас есть молот, все выглядит как гвоздь и т. Д.

Вы абсолютно, 100%, должны думать о потоке данных вокруг своего названия и быть в полной мере осведомлены о том, как информация переходит от одной подсистемы к другой. В некоторых случаях передача сообщений явно лучше всего; в других, может быть более целесообразным, чтобы одна подсистема работала над списком общих объектов, позволяя другим подсистемам также работать в одном и том же общем списке; и еще много методов.

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

Говоря, почти каждая игра, в которой я когда-либо работал, была надежной системой асинхронного оповещения о событиях /событиях. Это позволяет вам писать сжатый, эффективный поддерживаемый код даже в условиях сложных и быстро меняющихся потребностей в дизайне.

ответил MrCranky 11 FebruaryEurope/MoscowbFri, 11 Feb 2011 01:14:43 +0300000000amFri, 11 Feb 2011 01:14:43 +030011 2011, 01:14:43
2

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

  • Игровые движки имеют дело с большими объемами данных.
  • Игры должны быть быстрыми (20-30 FPS должны быть минимальными).
  • Часто нужно знать, было ли что-то сделано или когда это будет сделано.

При использовании общего подхода разработчика игр «он должен быть максимально эффективным» такая система обмена сообщениями, таким образом, не является общей.

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

ответил mrbinary 26 Jam1000000amWed, 26 Jan 2011 01:28:21 +030011 2011, 01:28:21
2

Да. Это очень эффективный способ взаимодействия игровых систем друг с другом. События помогают развязать многие системы и позволяют даже компилировать вещи отдельно, не зная о существовании друг друга. Это означает, что ваши классы могут быть легче прототипированы, а время компиляции выполняется быстрее. Что еще более важно, вы получаете плоский дизайн кода вместо беспорядка зависимости.

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

Другое преимущество: у вас может быть несколько подсистем, которые прослушивают одно и то же событие. Например, все ваши удаленные представления (игроки) могут автоматически подписываться на событие создания сущности и создавать объекты на каждом клиенте с небольшой работой с вашей стороны. Представьте, сколько еще было бы работы, если бы вы не использовали события: вам нужно было бы разместить вызовы Update () где-нибудь или, возможно, вызвать view-> CreateEntity из игры логика (где знание о представлении и какая информация, которая ему требуется, не принадлежит). Трудно решить эту проблему без событий.

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

Более подробная информация и реализация здесь .

ответил user2826084 28 MaramFri, 28 Mar 2014 06:54:44 +04002014-03-28T06:54:44+04:0006 2014, 06:54:44

Похожие вопросы

Популярные теги

security × 330linux × 316macos × 2827 × 268performance × 244command-line × 241sql-server × 235joomla-3.x × 222java × 189c++ × 186windows × 180cisco × 168bash × 158c# × 142gmail × 139arduino-uno × 139javascript × 134ssh × 133seo × 132mysql × 132