-
Notifications
You must be signed in to change notification settings - Fork 95
SML Mod, SML Session Settings, and Base Game Mod Configs Types #419
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: Dev
Are you sure you want to change the base?
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,51 @@ | ||
| = Mod Configuration Options | ||
|
|
||
| == Session Settings vs. Mod Config vs. Game User Settings | ||
|
|
||
| There are various ways for mod developers to add configuration options for their mods, and it can be confusing to know which one | ||
| to use. Listed below are the main types of configuration options, and the pros and cons of each type. In general, Session Settings | ||
| are best for options that affect gameplay and may vary between different saves, Mod Configs are best for options that are more visual | ||
| or client-specific, and Game User Settings are best for options that should be configurable on dedicated servers and designed for | ||
| per server or per client rather than per save. | ||
|
|
||
| xref:Development/ModLoader/ModConfigs/SessionSettings.adoc[Session Settings]: | ||
|
|
||
| .Pros: | ||
| ** Good for things that do not pertain to a particular player, or you want to be a choice per save file, such as | ||
| *** What recipes from a mod are enabled | ||
| *** How fast a machine operates | ||
| *** Options for a custom level | ||
| ** Per-save configuration | ||
| ** Automatically replicated in multiplayer | ||
| ** Can be made to sync between server and clients by mod developer if desired | ||
|
|
||
| .Cons: | ||
| ** Not per-installation, settings have to be re-configured for every new session. | ||
| ** Must be registered in the mod's GameInstanceModule to be registered. | ||
| ** Not visible in Dedicated Servers, as the User Interface is not loaded there. | ||
|
|
||
| xref:Development/ModLoader/ModConfigs/Configuration.adoc[Mod Configurations]: | ||
|
|
||
| .Pros: | ||
| ** Per-installation configuration | ||
| *** Carries over between saves | ||
| ** Can be made to sync between server and clients by mod developer if desired | ||
| ** Different users may want different settings on the same server, such as visual options or UI options that do not affect gameplay | ||
|
|
||
| .Cons: | ||
| ** Not replicated in multiplayer by default | ||
| ** Server settings must be configured through the Mod Config file | ||
|
|
||
| xref:Development/ModLoader/ModConfigs/UserSettings.adoc[Game User Settings], known as FGUserSetting: | ||
|
|
||
| .Pros: | ||
| ** Per-installation configuration | ||
| *** Carries over between saves | ||
| ** Can use the icon functionality offered by FGUserSettingCategory | ||
| ** Allows Dedicated Server and clients to have different settings for the same mod | ||
| ** Automatically replicated in multiplayer if `Is Session Setting Wide` is checked | ||
|
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. That is not the case. User Settings are never replicated unless you manually write the code for your specific setting to replicate (like base game does for some of its settings) |
||
| ** Contains an user interface for dedicated servers to configure settings that affect the server | ||
|
|
||
| .Cons: | ||
| ** Not per-save, changes affect all save files using the same installation | ||
| ** Mod must be a GameFeature to use Game User Settings, and settings must be registered in the mod's FGGameFeatureData to be registered. | ||
|
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Worth adding that they are added to the "Options" menu and not "Mod Options" or any other SML-related menu, so you need to be careful to group your settings reasonably well to avoid overwhelming the user. |
||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,234 @@ | ||
| = User Settings | ||
|
|
||
| Game User Settings are a feature that is used by the base game's Creative Mode and Game Mode Settings | ||
|
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I think you are confusing two separate systems here. The first system is User Settings (entry points in C++ are FGUserSetting, IFGOptionInterface and IFGOptionInterfaceImpl, as well FGOptionsLibrary) The second system is Game User Settings. Game User Settings are User Settings implementation that uses the ini file in saved data directory to persist the setting values, shows them in Options menu (and in Server Options), and is global to the install of the game/server. Creative Mode (aka Advanced Game Settings) are another implementation that stores the data on a per save game basis and does some additional handling to marshal it and pass it from session creation to the game logic on the loaded game map. Game Modes are another implementation similar to Creative Mode, but with its own gameplay differences. What your User Setting does and how it behaves heavily depends on what Manager class it actually belongs you (such as UFGGameUserSettings, UFGAdvancedGameSettings, or another implementation for game modes), because all of these behaviors are manager-specific. |
||
| that allows mods to store configuration information on a _per-game-install_ basis. | ||
| Game User Setting values are xref:Development/Satisfactory/Multiplayer.adoc[automatically replicated in multiplayer] | ||
| and can be edited by any connected player. | ||
|
|
||
| Game User Settings are currently stored in the Engine's GameUserSettings.ini file, | ||
| making them available exceedingly early in the loading process. | ||
| This may change in the future depending on what mod developers decide is more useful. | ||
|
|
||
| == Defining New Game User Settings | ||
|
|
||
| Game User Settings are defined by Data Assets. | ||
| To create a Game User Setting in Blueprint, in a content browser right click and select | ||
| `Create Advanced Asset` > `Miscellaneous` > `Data Asset` and search for `FGUserSetting`. | ||
|
|
||
| === Selecting a Str Id | ||
|
|
||
| Game User Settings are handled by `UFGGameUserSettings`, the class the game uses to define the configuration options in the settings menu. | ||
|
|
||
| The "Str Id" field is a unique identifier for the Game User Setting | ||
| and is used for retrieving the value of the Game User Setting later. | ||
| See the table below for some examples of Str Ids and things to keep in mind when selecting one. | ||
|
|
||
| .Example User Setting Str Ids | ||
| |=== | ||
| |✔️ Good Example |❌ Bad Practice | ||
|
|
||
| |✔️ `YourModReference.EnableFizzBuzz` | ||
|
|
||
| Prefix the id with your Mod Reference to ensure it is unique across mods. | ||
|
|
||
| | ❌ `EnableFizzBuzz` | ||
|
|
||
| Another mod could implement a User Setting by this name, | ||
| leading to a conflict. | ||
|
|
||
| |✔️ `YourModReference.WhizzbangStrengthMult` | ||
|
|
||
| Since User Settings are referenced by their string id, | ||
| giving them a verbose, unique name makes it easy to find all usages of the setting in code | ||
| via a find operation. | ||
|
|
||
| | ❌ `YourModReference.Multiplier` | ||
|
|
||
| Multiplier for what? It's easy to forget what this setting controls, | ||
| and if you ever decide to add other "multipliers" in the future, | ||
| they could easily be mentally confused with this one. | ||
|
|
||
| |✔️ `YourModReference.PowerCostMultFloat` | ||
|
|
||
| Since you must use a type-specific method to read/write a User Setting, | ||
| consider including the setting's type as part of its id as a reminder of what type it is. | ||
| Unfortunately using the wrong getter method is currently a silent error due to how the FG Options system is implemented, | ||
| making this problem particularly annoying to track down. | ||
|
|
||
| | | ||
| // intentionally blank | ||
|
|
||
| |✔️ `YourModRef.MinerMk1.PowerCostMultFloat` | ||
|
|
||
| Consider indicating which building/feature a setting applies to | ||
| if you offer multiple settings with similar names or functionality. | ||
|
|
||
| | | ||
| // intentionally blank | ||
|
|
||
|
|
||
| |=== | ||
|
|
||
| [id="Categories"] | ||
| === Display | ||
|
|
||
| The following fields control how User Settings appear to end users: | ||
|
|
||
| - Display Name: User-facing name of the option. Users can search for this text within the setting's category. | ||
| - Tool Tip: User-facing description of what the option does. | ||
| Appears at the bottom of the setting scroll list when the user hovers over the option. | ||
| Text will wrap as needed to fit the user's screen, but manual new lines are not supported. | ||
| - Widgets to Create: Defines where the setting appears. Elaborated on below. | ||
|
|
||
| [id="CategoryAsset"] | ||
| ==== Category Assets | ||
|
|
||
| User Settings appear in categories defined by FGUserSettingCategory assets. | ||
| You must create a minimum of 2 Category assets for your mod's User Settings, | ||
| one for the overarching Category used by your mod, and a second for a Sub Category within your category. | ||
| Category assets can be reused for multiple options within the same mod. | ||
|
|
||
| The following defaults are suggested: | ||
|
|
||
| [NOTE] | ||
| ==== | ||
| User Setting categories can use the icon functionality offered by FGUserSettingCategory. | ||
| ==== | ||
|
|
||
| [id="CategoryAsset_Main"] | ||
| ===== (Main) Category | ||
|
|
||
| Suggested asset name: `USC_YourModReference` | ||
|
|
||
| - mDisplayName: The Friendly Name of your mod, for example, `Example Mod`. The user can search all Categories for what you write here. | ||
| - mMenuPriority: Leave this at `0`, you can't infer what other mods the end user will have installed to pick a "good" value. | ||
| If you create multiple main categories, you can use this field to ensure they display next to each other. | ||
| In this case, pick a random large number to use as a base and then a small offset to group them together, for example, `864392` and `864392.1`. | ||
|
|
||
| Mods typically define a single main category for their User Settings. | ||
| If you end up creating multiple, make sure it's still clear which mod is offering the category. | ||
|
|
||
| [id="CategoryAsset_Sub"] | ||
| ===== Sub Category: | ||
|
|
||
| Suggested asset name: `USSubC_YourModReference_SubCategoryName` | ||
|
|
||
| - mDisplayName: Header text for this sub category. This field's text isn't currently searchable. | ||
| - mMenuPriority: Because you control all sub categories within your mod's category, this field is useful for ordering them. | ||
|
|
||
| [id="WidgetsToCreate"] | ||
| ==== "Widgets to Create" entry | ||
|
|
||
| User Settings inherit functionality from FGUserSettings that enable the same option to be displayed in multiple places, | ||
| so making one appear involves creating at least one entry in the Widgets to Create field. | ||
| Make sure to define these fields: | ||
|
|
||
| - Category Class: Self explanatory. | ||
| - Sub Category Class: Self explanatory. | ||
| - Menu Priority: Controls options' ordering within the sub category. | ||
|
|
||
| ==== Level Whitelist | ||
|
|
||
| When values are present in this array, the User Setting is restricted to only appear when playing in one of the specified game levels. | ||
|
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. This is not a vanilla functionality, I do not recall vanilla FGUserSetting assets having these feature. Are you sure you are not confusing them with SML Session Settings (which are a subclass of FGUserSettings)? |
||
| Combined with the fact that users can configure User Settings when setting up a new game save, | ||
| they are especially useful as options for custom maps. | ||
|
|
||
| === Behavior | ||
|
|
||
| Not all properties inherited from UFGGameUserSettings are relevant to User Settings. | ||
| You will have to experiment to see which ones have an effect. | ||
| Please update this documentation page via "Edit This Page" in the top right with your findings. | ||
|
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Again, behavior depends on a manager you are using, as I mentioned in the comment above. |
||
|
|
||
| Checking the "Use CVar" field is only required | ||
| if you wish to allow modifying the value of the User Setting via the game console. | ||
|
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Note that Use CVar is only supported for Game User Settings (not for game modes, AGS or anything else). Additionally, as a rule of thumb, you want to have all Game User Settings that are relevant for Dedicated Servers have a CVar (this is the convention that vanilla follows) |
||
|
|
||
| SML automatically forces the following property values on User Settings. | ||
| If you change any of these properties they will be automatically reset to these values | ||
| next time the asset is loaded. | ||
|
|
||
| * ShowInBuilds: `Public Builds` to ensure that User Settings are visible to the user | ||
| * ManagerAvailability: `USM MAX`, which is an invalid value, ensuring that the setting never displays in base-game options menus. | ||
|
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. This is deprecated, no need to explain this or even mention it |
||
| * IsSettingSessionWide: `true` to ensure that multiplayer clients are able to modify User Settings and have their changes stored with the save file. | ||
|
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. this only controls a little visual UI icon next to the setting, it has zero impact on the actual behavior of the setting. |
||
|
|
||
| In order to have a User Setting only editable at save creation, use the "Don't show in game" Visibility Disqualifier. | ||
|
|
||
| === Registration | ||
|
|
||
| A User Setting must be registered to be usable by the player. | ||
|
|
||
| To register a User Setting, list it in the relevant array of your mod's | ||
| xref:Development/Satisfactory/GameFeatureDataAsset.adoc[Game Feature Data Asset]. | ||
|
|
||
| Registering a User Setting makes it available to be configured in Satisfactory's Settings menu | ||
| which is available at both world creation and in the pause menu. | ||
|
|
||
| == Reading and Writing User Settings | ||
|
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. This is all good info, but specifically for Game User Settings, not for User Settings overall |
||
|
|
||
| Check ExampleMod for some example User Settings and how to read their values. | ||
| There is an example in the ExampleMod Level Blueprint and in the Game World Module. | ||
|
|
||
| === From Blueprints | ||
|
|
||
| To get a reference to the User Settings, use the "Get Option Interface" node. | ||
|
|
||
| You can read the value of a User Setting via the "Get <typename> Option Value" method of the User Settings Manager. | ||
| You can also subscribe to changes via "Subscribe to Dynamic Option Update". | ||
|
|
||
| If you want to programmatically modify the value of a User Setting, | ||
| use the "Set <typename> Option Value". | ||
|
|
||
| === From {cpp} | ||
|
|
||
| The UFGGameUserSettings is a UGameUserSettings UObject and as such can be accessed via the standard Unreal method of getting user settings. This does not require the game world context as shown below. | ||
|
|
||
| An example of reading a User Setting value from {cpp}: | ||
|
|
||
| ```cpp | ||
| UFGGameUserSettings* UserSettings = UFGGameUserSettings::GetFGGameUserSettings(); | ||
|
|
||
| // Boolean setting | ||
| const FVariant ConfigVariant = UserSettings->GetOptionValue(TEXT("ExampleMod.ExampleUserSetting")); | ||
| bool ConfigValue = ConfigVariant.GetValue<bool>(); | ||
| --or-- | ||
| bool ConfigValue = UserSettings->GetBoolOptionValue(TEXT("ExampleMod.ExampleUserSetting")); | ||
|
|
||
| // Integer setting | ||
| const FVariant ConfigVariant = UserSettings->GetOptionValue(TEXT("ExampleMod.ExampleUserSetting")); | ||
| int32 ConfigValue = ConfigVariant.GetValue<int32>(); | ||
| --or-- | ||
| int32 ConfigValue = UserSettings->GetIntOptionValue(TEXT("ExampleMod.ExampleUserSetting")); | ||
|
|
||
| // FString setting | ||
| const FVariant ConfigVariant = UserSettings->GetOptionValue(TEXT("ExampleMod.ExampleUserSetting")); | ||
| FString ConfigValue = ConfigVariant.GetValue<FString>(); | ||
| --or-- | ||
| FString ConfigValue = UserSettings->GetStringOptionValue(TEXT("ExampleMod.ExampleUserSetting")); | ||
|
|
||
| // Float setting | ||
| const FVariant ConfigVariant = UserSettings->GetOptionValue(TEXT("ExampleMod.ExampleUserSetting")); | ||
| float ConfigValue = ConfigVariant.GetValue<float>(); | ||
| --or-- | ||
| float ConfigValue = UserSettings->GetFloatOptionValue(TEXT("ExampleMod.ExampleUserSetting")); | ||
|
|
||
| // Linear Color setting | ||
| const FVariant ConfigVariant = UserSettings->GetOptionValue(TEXT("ExampleMod.ExampleUserSetting")); | ||
| FLinearColor ConfigValue = ConfigVariant.GetValue<FLinearColor>(); | ||
| --or-- | ||
| FLinearColor ConfigValue = UserSettings->GetLinearColorOptionValue(TEXT("ExampleMod.ExampleUserSetting")); | ||
| ``` | ||
|
|
||
| === Testing | ||
|
|
||
| Make sure to check in-game to ensure that your User Settings appear and display as you expect. | ||
| They are referred to in-game as Settings. This is the same as the game settings for Display, World, Gameplay, etc. | ||
|
|
||
| Check out ExampleMod for some example types and setups using User Settings. | ||
|
|
||
| == Advanced Game Settings | ||
|
|
||
| In order to create an Creative Mode setting (internally called an Advanced Game Setting) instead of a User Setting: | ||
|
|
||
| . Create a data asset of type `FGUserSetting`. | ||
| . Set the Manager Type Availability is set to `FGAdvancedGameSettings` in the asset properties. | ||
| . Ensure your mod's xref:Development/Satisfactory/GameFeatureDataAsset.adoc[Game Feature Data Asset] | ||
| is configured to scan for FGUserSetting assets at the path required to find your data asset. | ||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This is absolutely a bug and a missing feature, not really a "con"