Что такое «игровой логический код»?

50

Я использую C # / XNA, и мне несколько раз говорили не смешивать код обновления с кодом отрисовки - и я уверен, что нет! Но может ли кто-нибудь описать, что такое «логический код»?

Как видно здесь: http://blogs.msdn.com/b/shawnhar/archive/2007/07/25/understanding-gametime.aspx

[...] убедитесь, что вы поместили всю свою игровую логику в метод Update (не в Draw!), и все будет работать с хорошей постоянной скоростью.

Я спрашиваю об этом, так как скорость моей игры колеблется относительно FPS. Медленный FPS равняется медленным объектам и наоборот. И да, я включаю ожидаемый position += speed * (float)gt.ElapsedGameTime.TotalSeconds;код.

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

Застенчивый парень
источник
Я думаю, что вы имели в виду position = speed * ...TotalSeconds. Обратите внимание, это =не так +=. Если бы это было +=так, как вы печатали, то ваша позиция почти мгновенно исчезла бы с экрана.
DrZ214
У меня есть код, который выглядит как «позиция + = направление * скорость * ... TotalSeconds», и это работает очень хорошо. Я мог что-то напечатать, но position = speed назначал бы это при каждом обновлении. Ваш путь может работать, но мой код работает следующим образом. (Обратите внимание, что направление нормализовано)
Shyy Guy
Я думал, gt.ElapsedGameTime.TotalSecondsсколько секунд прошло с момента запуска программы (игры). Если вы умножаете свою скорость на это, то после 5 секунд игры ваша скорость будет в 5 раз выше (кроме особого случая, когда скорость установлена ​​на 0). Не уверен, что еще ты мог бы сделать это неправдой, но я заинтригован.
DrZ214
1
Ага, это с момента последнего обновления. gamedev.stackexchange.com/questions/67968/…
Shyy Guy
2
Увлекательно, я бы никогда не догадался об этом. Никогда не было нужды в таких вещах в считанные секунды, потому что я лично использую свою собственную переменную, iiiкоторую я вручную увеличиваю каждое обновление, потому что я не хочу ее в считанные секунды, я хочу шаги или кадры. Я вижу, что ваш путь - это правильный способ софт-кодирования.
DrZ214

Ответы:

102

Меняет ли это состояние вашего игрового мира? Это логический код.

Отображает ли он состояние игрового мира? Это код рендеринга.

Нильс Оле Тимм
источник
Я посмотрю свой код, чтобы быть на 100% уверенным. Хорошее объяснение, спасибо.
Застенчивый парень
38
Он обрабатывает ввод? Код его контроллера. Отделите управление от логики, чтобы вы могли использовать одну и ту же логику с различными типами элементов управления. Например, FPSInputController + CharacterMotor против AIInputController + CharacterMotor против NetworkInputController (например, другие игроки в многопользовательском режиме) + CharacterMotor. Мотор (логический код) не заботится о том, как он получает инструкции, которые он делает, только о том, что они поставляются (этот вид развязки позволяет легко переходить от игрока к искусственному боту (например, Left 4 Dead и бездействующим игрокам) и обратно, между прочим).
Draco18s
10
Драко поднимает хороший вопрос. Есть много разных разделов, которые вы можете вставить в код. Разделение Нильса - это то, что я бы назвал архетипическим разделением между логикой и рендерингом, но есть много других слоев, которые вы увидите. Реальная причина разделения их на слои заключается в том, что каждый уровень состоит из одинаковых действий, для которых требуется одинаковый стиль кода с аналогичными требованиями. Например, во многих играх вы можете избавиться от логики игры, требующей 2 или 3 кадра для завершения, но если вы не выполняете рендеринг каждого кадра, глаз пользователя быстро заметит.
Cort Ammon
Если вы будете различать их, это поможет вам справиться с вашими требованиями, когда они станут источником напряжения.
Cort Ammon
6
И помните, что если вы добавите слишком много MVC, он может замедлиться до скорости сканирования, поэтому всегда стремитесь к балансу между ремонтопригодностью и оптимизацией. Но не оптимизируйте слишком рано, если вы не абсолютно уверены, что делаете. И помните, что вы всегда можете сделать рефакторинг. И ... Делай много игр и учись на своих ошибках.
Maurycy
24

Ваше разделение верно, если:

  • Вызов Draw () несколько раз подряд без чередующихся вызовов Update () никогда не приведет к каким-либо видимым изменениям между вызовами.
  • Вызов Update () несколько раз подряд без перемежающегося вызова Draw () был бы похож на игру в игру с выключенным экраном: все движется идеально и последовательно, вы просто не можете его видеть.
Томас
источник
5
Правильно написанные Draw()могут рисовать разные картинки с течением времени. Например, кадры анимированных спрайтов могут продолжать меняться. Кроме того, объекты могут продолжать визуально двигаться вперед, если код рендеринга использует общий трюк и увеличивает velocity * time since last update / period of updateвидимое положение объектов (в то время как их реальное положение остается неизменным).
HolyBlackCat
2
iffто есть если-и-только-если?
BalinKingOfMoria
3
@HolyBlackCat: это спорно. Что делать, если я хочу приостановить графику? Что если кадры анимации влияют на игру (анимация атаки, соответствующая хитбоксам и т. Д.)? Визуальная интерполяция по-прежнему подразумевает, что «время» (как в дельта-времени игры) проходит, но если время проходит, а вы нет, Updateто что еще не синхронизировано? Входы проигрывателя пропущены, сетевые события не обрабатываются и т. Д.? Игра должна быть запущена из одних часов, с фиксированными «галочками» для игровой логики или физики, полученными из этих часов, и производное графическое состояние, также управляемое теми же часами.
Шон Миддлдич
@SeanMiddleditch Я согласен, почти всегда вы можете писать Draw()таким образом, чтобы он всегда рисовал одну и ту же картинку при вызове несколько раз подряд. Нужно сделать это, если это возможно. Но бывают случаи, когда вы не знаете, с какой частотой Draw()будут звонить. Например, если вам нужна полная поддержка (фактическая 120 FPS) для новых мониторов с частотой 120 Гц, и вы включаете vsync. What if I want to pause graphics?Затем вы передаете 0 вместо фактического времени дельты в Draw().
HolyBlackCat
2
@HolyBlackCat: Ничто из того, что я получал, не исключало бы использование рендеринга 120 Гц. Я абсолютно не рекомендовал фиксированную ставку; это просто любительское. Должны быть одни глобальные игровые часы, дельта которых измеряется в терминах кадров рендеринга, которые подаются в значение накопления для игрового тика с фиксированной скоростью. Эти глобальные часы управляют графикой, включая интерполяцию. Вы можете приостановить графику, установив шкалу часов на 0. Вы можете иметь иерархические часы, так что, например, пользовательский интерфейс все еще работает и анимирует, а интерполяция символов тоже очень и очень легко останавливается.
Шон Мидлдитч
7

Дело здесь в разделении вещей модели, которые не являются моделью.

Логика игры - это модель, о которой говорится в

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

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

Подобное относится и к игровой логике.

Представьте, что в какой-то момент ваша игра была перенесена на другую консоль. Это может помочь представить что-то действительно отличное от вашей текущей цели. Например, если вы нацелены на что-то с помощью геймпада / контроллера, представьте, что ваша игра перенесена на планшет с сенсорным экраном. Логика игры - это часть кода, которая не меняется при портировании.

Если ваша игра была чем-то вроде военной стратегии, представьте, что она превращается в самую сложную настольную игру в мире. Логика игры - это фрагменты кода, которые напрямую соответствуют строкам в книге правил. (Не все строки в книге правил, не о движущихся фигурах, а о некоторых.)

Логика игры - это то, что никогда не меняется, независимо от формы.

Линдон Уайт
источник