FyroxEngine / Fyrox

3D and 2D game engine written in Rust
https://fyrox.rs
MIT License
7.61k stars 340 forks source link

Minimal support for headless mode #416

Closed martin-t closed 1 year ago

martin-t commented 1 year ago

Related to #222 - see latest comment.

I am not sure if the field should be named headless because it just disables sound, not graphics but i figured if adding this field is gonna be a breaking change, might as well call it that so that when somebody figures out a way to disable window creation, it's not another breaking change later.

Basically i thought i'd need to implement a full headless mode but for my usecase (running on CI) it turns disabling sound is all that's needed. I currently don't have any intention of looking into how to implemented a full headless mode because i suspect it would be a lot of effort. Nonetheless, i think this PR is very useful to be able to run fyrox games on CI, the only issue for me is whether i should keep calling that field headless or change the name to noaudio, no_sound or something similar.

martin-t commented 1 year ago

Oh and i added SoundEngine::new_headless() because i assume it's better than without_device. It looks like even the dummy device does mixing so i assume it has some side effects (plus the spawned thread). without_device says the user must periodically call render so i assume calling render is important even if we don't play any sound - maybe it consumes some buffer or something? I didn't look too deeply into it though, it's possible that without_device is sufficient for this usecase, let me know.

mrDIMAS commented 1 year ago

I think this approach with flags is quite hacky. Instead it should be done via conditional compilation, that will completely exclude renderer and sound backends from the engine. Actually, I want to experiment with this, because I'm so tired of animations and stuff. This should be fun to do.

martin-t commented 1 year ago

I don't think conditional compilation is a good option. That would mean having to compile the engine twice for client and server (increasing CI time) and always producing 2 separate final binaries (increasing incremental build time which is essential to keep down for gamedev). My game only has 1 binary that allows running as client or server or both in one process specifically because of this.

mrDIMAS commented 1 year ago

Good point. I poked conditional compilation a bit today and I see that it will add quite a lot of compilation conditions for the game code, making it quite annoying to write and maintain. I guess then the overall idea of the PR is fine, I just need to look at code again.

As for further changes, I think wrapping the renderer into Option<Renderer> would be good and simple solution to disable it too for the server mode. The winit's event loop can be used for the server logic without any problems, it is possible to run it without a window. So making EngineInitParams::window_builder and related fields (such as window and stuff in the Engine) optional is a way to go. I think it is not so hard to do, I'll take a look at it tomorrow.