Save & Sync ways - THDigi/SE-ModScript-Examples GitHub Wiki

This is merely a summary of the ways one can store data persistently per block and synchronize it in multiplayer.

First off, it's kind of complicated, which is why there's no example scripts for these yet, if you don't count the published mod I link at the end.

The terminal controls/actions are only GUI so modders have to implement their own ways to save&sync the values (if applicable, most of the time it is).

Ways to do it:

  • Both: CustomData but is player-editable.
    You should use MyIni to parse/generate the data there, to be compatible with programmable-block scripts and other mods.

  • Sync: MySync<T> which can only be used with blittable types which means you can't use string with it for example.
    To check if a type is blittable you can use BlittableHelper<T>.IsBlittable by replacing T with the type, can be called outside of the game too.
    Another downside is that the game has a limit of 32 (should be 64 but it's bugged) and some blocks already have a high amount of them, Rotor for example has 30 from what I remember.
    I've also heard that regular components have their own sync property list, more digging required in that area.
    As for a guide in using it: Gwindalmir's guide on Keen discord.

  • Sync: Sending packets manually, this must be used if you need arrays/strings or any kind of complex packet.
    Example in this repo.

  • Storage: MyModStorageComponent is effectively a Dictionary<Guid, string> per entity.
    Acts identically to CustomData except for the fact that it's not synchronized in realtime and players can't edit it in game (they can still edit it in blueprints).
    It gets stored in copies, blueprints and gets streamed with the entity.
    Guide on Keen forum (archive.org)
    Mind that it requires a .sbc file to claim a Guid to indicate the mod is still present, otherwise the unclaimed Guid's values will be removed.
    The example .sbc from the link doesn't have all the wrapping tags, here's one from a working mod: EntityComponents.sbc.
    Just be sure to modify the <SubtypeId> and <guid> values to not collide with my mod.

  • Storage: There is also a way to use custom object builders to serialize data, I've not researched this way (was just added in v202) and if anyone does do this you should test what happens to the world when you remove the mod, if it breaks the world then it's not worth it.

Mod example

I use the manual packet + ModStorageComp way in my Gravity Collector mod amongst others but this one has the least function code besides the terminal, save and sync.

The gist is:

  • A single protobuf class to act as both the saved version and the packet for synchronizing. Serialized to binary then for storage to Base64 string too, which is faster and more compact than XML, and makes it more difficult for players to edit in blueprints as well.
  • Using IsSerialized override as an event for when the game wants the block to be serialized for me to convert the settings to string.
  • Every time a relevant property changes I schedule a sync event to avoid spamming from sliders and such.
  • The SyncSettings() below that is being called continuously (update100 would be more enough but I needed update10 for other purposes) which if scheduled will send the settings to server, which then relays them to everyone else if desired (behavior offered by my networking class, same one as in the example).
⚠️ **GitHub.com Fallback** ⚠️