Как стать автором
Обновить

Комментарии 15

Рассказал бы это всё кто-то ElectronicArts, а то их последней нетленке не хватает Ryzen 3950Х для 60 fps.

Я знаю только движок Bevy, который строится строго и безальтернативно вокруг ECS-подхода. Еще был Amethyst, но он пару лет назад схлопнулся и посоветовал всем уходить на Bevy.

Есть Fyrox как пример движка на Rust без ECS. Выглядит поинтереснее и пофичастее Bevy.

Спасибо за статью, не то чтобы узнал нечто новое, но обзорно она очень неплоха.

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

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

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

При этом рендер кустов, анимации и частицы отбирают то же процессорное время, столкновения пулек считает физика - это уже оптимизированные компоненты движка, распаралелленные и т.д.

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

Конечно есть и исключения, скажем игры типа факторио. Тут может помочь ecd. Последний кстати написан без ecs на плюсах и просто имеет хорошую структуру и оптимизацию для объектов

А можно подробнее про ecd? Не могу нагуглить ничего по этой аббревиатуре

Простите, опечатка
Речь о ECS.
То есть вот этот сценарий факторио с кучей перекладываемых ресурсов, конвейеров и прочие клеточные автоматы - это как раз подходящая для распараллеливания и строгой организации задача.

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

Godot так вообще открестился от ECS

Мне кажется они лукавят. То, как они скрепляют иерархии даёт намеки на то, что под капотом оно также крутится в ECS, просто не настолько явном.

В этом и дело, что кажется.

Godot целенаправленно выбрал классический ООПшный путь архитектуры, когда всё, слой за слоем, наследуется от более базового объекта. И они делают ставку на композицию при создании игровой логики, пусть у тебя будет объект состоять из кучки уникальных нодов, которые олицетворяют что-то одно. Для примера, у тебя будет в минимальном виде будет родительская Node3D для позиционирования, и в наследниках MeshRenderer и Rigidbody для обычного кубика в 3D. И эта часть вполне соотносится к замыслу компонент из ECS. И если уж и говорить, Godot частично на EC тянет. Главное отличие в том, что системы в них вполне себе размазаны по соответствующим компонентам, а на роль entity можно отнести базовый родительский объект, и обращаться с ним как с максимально топорным node/object, не обращая внимания на то, чем он является.

Ну и так же, движок вполне себе в линейном виде вызывает в каждом соответствующем объекте update() и physics_update(), а так же их иные уникальные методы по нотификации, но это задача скорее "серверов" на стороне движка, вроде PhysicsServer и GraphicsServer

то есть у каждого объекта мне явным образом надо звать update в котором явным образом позвать апдейты своих компонентов? Что-то типа

void MyCube::update() {
    rigid_body::update();
    mesh_renderer::update();
    my_cube_logic_update();
}

Или каждая из систем таки прописываются в систему, которые где-то централизовано обновляются?

MeshRender::MeshRender() {
  get_global()->get_mesh_renderer_system()->add(this);
}
// где-то в иэйнлупе
void Global::update(dt) {
  update_mesh_render_system();
  update_rigid_body_system();
}

Нужно помнить, что почти каждый самописный компонент в Godot будет наследоваться от Node, и просто каждый тик кор движка проходит по стэку всех объектов на сцене, и отправляет им нотификацию NOTIFICATION_PROCESS. Затем мост к GDScript вызывает _process(delta) -> void, мост к C# вызывает Process(double delta){};

Сложнее ситуация, если идёт наследование напрямую от Object. Такие объекты тоже могут принимать нотификации, но обычно они как раз и обрабатываются внешними серверами. И каждый сам определяет необходимый ему функционал на уровне контрактов.

Так что ближе ко второму, но не так явно. Всё же мы люди ленивые =Ъ

Ну вот собственно второй подход с подписками/регистрациями это вполне себе ECS, в первом случае там каскадный вызов update. Так делает например Cocos2d-x, поэтому что-то достаточно большое писать на нём нельзя без переписывания - огребаешь тормозов как на индирекциях, так и на кэшмисах и в рендеринге. Для мобильных казуалок хватает, а на штуки а ля геншин такого точно не хватит - 30 фпс картинка сожрёт батарею раньше чем загрузка ассетов кончится.

Вот еще годное интервью от разраба Тундры про ядра и многопоточность

https://youtu.be/Z-ssa55wRVo

моя. это было мимолётное сотрудничество. но селектел статью знатно зацензурил и обезличил, надо сказать

Зарегистрируйтесь на Хабре, чтобы оставить комментарий

Публикации

Истории