так вот, поговорим про команды. а именно - про LogicCommand.
так как игра реализована на движке от supercell - titan (и там уже на уровне движка логика команд реализована), то мы можем ожидать идентичную реализацию и в играх от хайпхайп. ведь так?
ведь так...?нее, нихуя.
как это реализовано в играх от supercell? разберём для начала
клиент -> серверигра собирает нужный LogicCommand (далее - команда), проставляет данные команды и отправляет её в HomeMode::addCommand, который заворачивает туда нужные данные, выполняет саму команду и отправляет её на временное хранение в commandstorage.
когда игре понадобится отправить команду (или же, команды), она создаёт сообщение EndClientTurnMessage, переносит оттуда команды из commandstorage, кодирует через LogicCommandManager.encodeCommand и отправляет.
причём кодирует в виде
всё максимально понятно и не сложно.
с
сервер -> клиент тоже всё максимально просто.
сервер присылает сообщение AvailableServerCommandMessage с закодированной командой.
игра вызывает LogicCommandManager.decodeCommand который сначала декодирует commandType, затем создаёт сопутствующий команде инстанс класса и декодирует команду дальше.
затем, игра также вызывает HomeMode::addCommand, ну и дальше всё по аналогии с клиентом. только сервер кодирует команду слегка по другому
казалось бы, хорошая реализация. ничего не добавить и не убавить.
но хайпхайп так не считают...клиент -> серверигра аллоцирует 36 байт памяти (типа LogicCommandRaw), проставляет филлерные значения и вызывает Hyperion::GameMode::addCommand, который по аналогии с HomeMode::addCommand из игр supercell проставляет некоторые данные и кидает команду в CommandStorage.
но затем))) игра создаёт уже сопутствующий LogicCommand, проставляет туда нужные данные, кодирует и...
внимание... берёт поинтер на буфер из ByteStream, и ставит его на 24 оффсет в аллоцированной памяти))) (ну и длину буфера на 28)
затем, когда игре нужно отправить команду, игра всё также создаёт сообщение EndClientTurnMessage в которое выставляет нужные данные с массивом raw команд, кодирует их через LogicCommandManager::encodeCommandRaw и отправляет.
и так и получается, что игра кодирует их в виде
а сам buffer выглядит как-то так...
сервер -> клиентпримерно всё также как и с supercell.
НО!!!когда игра получает AvailableServerCommandMessage, она вызывает LogicCommandManager::decodeCommandRaw который декодирует LogicCommandRaw и сохраняет всё добро... снова в аллоцированной памяти.
игра вызывает Hyperion::CommandStorage::executeCommand, который вызывает Hyperion::System::Commands::handleCommand, в КОТОРОМ ИГРА ИЗ LogicCommandRaw СОБИРАЕТ СОПУТСТВУЮЩУЮ КОМАНДУ. И ВЫПОЛНЯЕТ ЕЁ!!!!
сервер кодирует команду как-то так btw
а сам buffer выглядит как-то так...
и знаете что самое смешное? у них есть класс для raw-команд, который называется, не поверите, LogicCommandRaw. но они его даже не используют))) тупо память аллоцируют)))
(или мб компилятор продристался)удобнее ли такая реализация системы команд? сомневаюсь.