]> git.smokeofanarchy.ru Git - space-station-14.git/commitdiff
Add support for true randomized characters (#14918)
authorNemanja <98561806+EmoGarbage404@users.noreply.github.com>
Wed, 29 Mar 2023 01:30:00 +0000 (21:30 -0400)
committerGitHub <noreply@github.com>
Wed, 29 Mar 2023 01:30:00 +0000 (18:30 -0700)
Content.Server/Station/Systems/StationSpawningSystem.cs
Content.Shared/CCVar/CCVars.cs
Resources/Prototypes/Species/species_weights.yml [new file with mode: 0644]

index 65577ab05a42cf845604380ab8b0d4fa74724b34..641c801d50736dff28c823b8ed2b57c3e0614fd5 100644 (file)
@@ -8,18 +8,21 @@ using Content.Server.PDA;
 using Content.Server.Roles;
 using Content.Server.Station.Components;
 using Content.Server.Mind.Commands;
-using Content.Server.Shuttles.Components;
 using Content.Shared.Access.Systems;
 using Content.Shared.CCVar;
+using Content.Shared.Humanoid;
 using Content.Shared.Humanoid.Prototypes;
 using Content.Shared.Inventory;
 using Content.Shared.PDA;
 using Content.Shared.Preferences;
+using Content.Shared.Random;
+using Content.Shared.Random.Helpers;
 using Content.Shared.Roles;
 using JetBrains.Annotations;
 using Robust.Shared.Configuration;
 using Robust.Shared.Map;
 using Robust.Shared.Prototypes;
+using Robust.Shared.Random;
 using Robust.Shared.Utility;
 
 
@@ -33,6 +36,7 @@ namespace Content.Server.Station.Systems;
 public sealed class StationSpawningSystem : EntitySystem
 {
     [Dependency] private readonly IPrototypeManager _prototypeManager = default!;
+    [Dependency] private readonly IRobustRandom _random = default!;
     [Dependency] private readonly IConfigurationManager _configurationManager = default!;
     [Dependency] private readonly HandsSystem _handsSystem = default!;
     [Dependency] private readonly HumanoidAppearanceSystem _humanoidSystem = default!;
@@ -42,10 +46,13 @@ public sealed class StationSpawningSystem : EntitySystem
     [Dependency] private readonly SharedAccessSystem _accessSystem = default!;
     [Dependency] private readonly IdentitySystem _identity = default!;
 
+    private bool _randomizeCharacters;
+
     /// <inheritdoc/>
     public override void Initialize()
     {
         SubscribeLocalEvent<StationInitializedEvent>(OnStationInitialized);
+        _configurationManager.OnValueChanged(CCVars.ICRandomCharacters, e => _randomizeCharacters = e, true);
     }
 
     private void OnStationInitialized(StationInitializedEvent ev)
@@ -106,12 +113,31 @@ public sealed class StationSpawningSystem : EntitySystem
             return jobEntity;
         }
 
-        if (!_prototypeManager.TryIndex(profile?.Species ?? HumanoidAppearanceSystem.DefaultSpecies, out SpeciesPrototype? species))
+        string speciesId;
+        if (_randomizeCharacters)
+        {
+            var weightId = _configurationManager.GetCVar(CCVars.ICRandomSpeciesWeights);
+            var weights = _prototypeManager.Index<WeightedRandomPrototype>(weightId);
+            speciesId = weights.Pick(_random);
+        }
+        else if (profile != null)
+        {
+            speciesId = profile.Species;
+        }
+        else
         {
-            species = _prototypeManager.Index<SpeciesPrototype>(HumanoidAppearanceSystem.DefaultSpecies);
+            speciesId = SharedHumanoidAppearanceSystem.DefaultSpecies;
         }
 
-        var entity = EntityManager.SpawnEntity(species.Prototype, coordinates);
+        if (!_prototypeManager.TryIndex<SpeciesPrototype>(speciesId, out var species))
+            throw new ArgumentException($"Invalid species prototype was used: {speciesId}");
+
+        var entity = Spawn(species.Prototype, coordinates);
+
+        if (_randomizeCharacters)
+        {
+            profile = HumanoidCharacterProfile.RandomWithSpecies(speciesId);
+        }
 
         if (job?.StartingGear != null)
         {
@@ -124,10 +150,10 @@ public sealed class StationSpawningSystem : EntitySystem
         if (profile != null)
         {
             _humanoidSystem.LoadProfile(entity, profile);
-            EntityManager.GetComponent<MetaDataComponent>(entity).EntityName = profile.Name;
+            MetaData(entity).EntityName = profile.Name;
             if (profile.FlavorText != "" && _configurationManager.GetCVar(CCVars.FlavorText))
             {
-                EntityManager.AddComponent<DetailExaminableComponent>(entity).Content = profile.FlavorText;
+                AddComp<DetailExaminableComponent>(entity).Content = profile.FlavorText;
             }
         }
 
index d50ad12461856bce13dd3b5d75063db81e29d839..8280d8d294bfaf8884149bf36de4fdc02c763ae3 100644 (file)
@@ -1300,6 +1300,18 @@ namespace Content.Shared.CCVar
         public static readonly CVarDef<bool> ICNameCase =
             CVarDef.Create("ic.name_case", true, CVar.SERVER | CVar.REPLICATED);
 
+        /// <summary>
+        /// Whether or not players' characters are randomly generated rather than using their selected characters in the creator.
+        /// </summary>
+        public static readonly CVarDef<bool> ICRandomCharacters =
+            CVarDef.Create("ic.random_characters", false, CVar.SERVER);
+
+        /// <summary>
+        /// A weighted random prototype used to determine the species selected for random characters.
+        /// </summary>
+        public static readonly CVarDef<string> ICRandomSpeciesWeights =
+            CVarDef.Create("ic.random_species_weights", "SpeciesWeights", CVar.SERVER);
+
         /*
          * Salvage
          */
diff --git a/Resources/Prototypes/Species/species_weights.yml b/Resources/Prototypes/Species/species_weights.yml
new file mode 100644 (file)
index 0000000..2e82a0b
--- /dev/null
@@ -0,0 +1,8 @@
+#default species weights used for randomly selected species
+- type: weightedRandom
+  id: SpeciesWeights
+  weights:
+    Human: 5
+    Reptilian: 4
+    SlimePerson: 4
+    Diona: 2