Barotrauma

Barotrauma

Barotrauma Workshop
You can build your own submarines and monsters with in-game editors and share your creations with other players. Imagine and experiment.
Impatient 2 23 Dec, 2023 @ 9:25pm
How Barotraumas game engine updates the component network
While trying to design some efficient component item assemblies, the question of how the game engine calculates the state of the component network arose to me.

I am a seasoned user of Factorio and have knowledge of how their game engine calculates the state of their equivalent to Barotraumas component network, the "circuit network". In the case of Factorio that behavior is actually well documented on their wiki ( see https://wiki.factorio.com/Tutorial:Combinator_tutorial#Introduction ).

With that knowledge and some testing, I made the assumption, that Barotraumas game engine works in a very similar if not the same way. But I did not study the source code and therefor can not be sure. And I would like to read what others, who have source code knowledge in this regard or did tests in this regard or at least pondered the same question, think about this topic. A blessing and heartly welcome would be of course a comment by the developers themselves, that sheds light on this topic.

The base line of my assumption on how Barotraumas game engine updates the component network is this: The game engine "updates" the ouputs of all the components once every "calculation cycle" "in parallel".

Explanation:

By "updating" I mean this:
  1. For each input pin of a component, get the input value from the output pin of the connected component.
  2. Do the calculation specific to this componts component type, with this components input values and internal settings.
  3. Write the result(s) to the output pins of this component.

By "in parallel" I mean this:
  • The game engine keeps an unordered (not regarding how the components are wired together) list of all the components and their current output value(s).
  • Each calculation cycle the game engine just iterates the unordered list of components and updates them (as described above).
  • It explicitely does not bother about what logic the wiring between multiple components tries to achive.
  • It explicitely does not try to calculate the final output of multiple sequentially wired components in one go.

By "calculation cycle" I mean this:
  • One iteration of calculating the component networks state.

Also, independently of my assumption, there are some interesting questions regarding the calculation cycles:
  • How are they connected to the rest of the game state?
  • Do they run in their own thread?
  • How many are there per second?
  • Where are they performed? (server, client or both)

If my assumption was true, the most important impact imo, which would allow for interesting designs, would be signal delay. Signal delay in sequentially wired components. For example picture 3 sigcheck components wired in sequence. Each testing for some abitrary value and based on that outputting some arbitrary value. Now when the input value to sigcheck1 changes, the final result of this sequence of 3 sigchecks (the new output value of sigcheck3) will only be available after 3 calculation cycles. In cycle one the new input causes a new ouptut in sigcheck1, which only becomes the new input for sigcheck2 in cycle 2 and NOT in cycle 1. And the new output of sigcheck2 only becomes the new input for sigcheck3 in cycle 3.
This example by itself may not make signal delay seem that important, because the game engine comes up with the result of this sequence of components at some point by whatever way it works anyways. BUT picture a second example: Now there are 2 sequences of components. SequenceA with 3 components A1, A2 and A3 and sequence B with 2 components B1 and B2. And these two sequences are wired in parallel. Meaning, the input pin(s) of component A1 and B1 are wired to the same ouput pin(s). This would cause the final result of sequence B to be available one calculation cycle earlier than the final result of sequence A. Does this seem more important now? I thought as in Factorio, this can at least be used for one thing: A signal converter. To solve the problem of converting a continuous signal to a signal pulse. What would be a cool pulse? A signal that is only emmited for one calculation cycle, right? If all the assumptions are true, this would be the shortest pulse, the game engine would allow for. So I designed a signal converter based on the assumption of signal delay. And it works - reliably. Relay components and delay components begone. I shared it in the workshop:

https://steamhost.cn/steamcommunity_com/sharedfiles/filedetails/?id=3100049173

Of course that does not mean that the underlying assumption is correct. The design could work for whatever other reasons unknown. But it supports the assumption.

In any case, clear and detailed knowledge on this topic would be very interesting. To know in detail how the game engine updates the component network would allow for tailored to the literal core designs.
Last edited by Impatient; 23 Dec, 2023 @ 9:35pm