Files
OldThink/Content.Shared/Salvage/SharedSalvageSystem.cs

116 lines
4.0 KiB
C#
Raw Permalink Normal View History

2023-04-20 10:43:13 +10:00
using System.Linq;
2023-09-19 22:52:01 +10:00
using Content.Shared.CCVar;
2023-03-10 16:41:22 +11:00
using Content.Shared.Dataset;
2023-09-19 22:52:01 +10:00
using Content.Shared.Procedural;
using Content.Shared.Procedural.Loot;
2023-03-10 16:41:22 +11:00
using Content.Shared.Random;
using Content.Shared.Random.Helpers;
2023-04-20 10:43:13 +10:00
using Content.Shared.Salvage.Expeditions;
using Content.Shared.Salvage.Expeditions.Modifiers;
2023-09-19 22:52:01 +10:00
using Robust.Shared.Configuration;
2023-03-10 16:41:22 +11:00
using Robust.Shared.Prototypes;
2023-04-20 10:43:13 +10:00
using Robust.Shared.Random;
using Robust.Shared.Serialization;
using Robust.Shared.Utility;
2023-03-10 16:41:22 +11:00
namespace Content.Shared.Salvage;
public abstract partial class SharedSalvageSystem : EntitySystem
2023-03-10 16:41:22 +11:00
{
2023-09-19 22:52:01 +10:00
[Dependency] protected readonly IConfigurationManager CfgManager = default!;
2023-04-20 10:43:13 +10:00
[Dependency] private readonly IPrototypeManager _proto = default!;
/// <summary>
2023-09-19 22:52:01 +10:00
/// Main loot table for salvage expeditions.
2023-04-20 10:43:13 +10:00
/// </summary>
2023-09-19 22:52:01 +10:00
[ValidatePrototypeId<SalvageLootPrototype>]
public const string ExpeditionsLootProto = "SalvageLoot";
2023-04-20 10:43:13 +10:00
2023-03-10 16:41:22 +11:00
public static string GetFTLName(DatasetPrototype dataset, int seed)
{
var random = new System.Random(seed);
return $"{dataset.Values[random.Next(dataset.Values.Count)]}-{random.Next(10, 100)}-{(char) (65 + random.Next(26))}";
}
2023-09-19 22:52:01 +10:00
public SalvageMission GetMission(SalvageDifficultyPrototype difficulty, int seed)
2023-03-10 16:41:22 +11:00
{
2023-04-20 10:43:13 +10:00
// This is on shared to ensure the client display for missions and what the server generates are consistent
2023-09-19 22:52:01 +10:00
var modifierBudget = difficulty.ModifierBudget;
2023-04-20 10:43:13 +10:00
var rand = new System.Random(seed);
2023-09-19 22:52:01 +10:00
// Run budget in order of priority
// - Biome
// - Lighting
// - Atmos
var biome = GetMod<SalvageBiomeModPrototype>(rand, ref modifierBudget);
var light = GetBiomeMod<SalvageLightMod>(biome.ID, rand, ref modifierBudget);
var temp = GetBiomeMod<SalvageTemperatureMod>(biome.ID, rand, ref modifierBudget);
var air = GetBiomeMod<SalvageAirMod>(biome.ID, rand, ref modifierBudget);
var dungeon = GetBiomeMod<SalvageDungeonModPrototype>(biome.ID, rand, ref modifierBudget);
var factionProtos = _proto.EnumeratePrototypes<SalvageFactionPrototype>().ToList();
factionProtos.Sort((x, y) => string.Compare(x.ID, y.ID, StringComparison.Ordinal));
2023-09-19 22:52:01 +10:00
var faction = factionProtos[rand.Next(factionProtos.Count)];
2023-04-20 10:43:13 +10:00
var mods = new List<string>();
if (air.Description != string.Empty)
{
mods.Add(air.Description);
}
2023-04-20 10:43:13 +10:00
// only show the description if there is an atmosphere since wont matter otherwise
if (temp.Description != string.Empty && !air.Space)
{
mods.Add(temp.Description);
}
if (light.Description != string.Empty)
2023-04-20 10:43:13 +10:00
{
mods.Add(light.Description);
}
2023-09-19 22:52:01 +10:00
var duration = TimeSpan.FromSeconds(CfgManager.GetCVar(CCVars.SalvageExpeditionDuration));
2023-04-20 10:43:13 +10:00
2023-09-19 22:52:01 +10:00
return new SalvageMission(seed, dungeon.ID, faction.ID, biome.ID, air.ID, temp.Temperature, light.Color, duration, mods);
2023-03-10 16:41:22 +11:00
}
public T GetBiomeMod<T>(string biome, System.Random rand, ref float rating) where T : class, IPrototype, IBiomeSpecificMod
2023-03-10 16:41:22 +11:00
{
var mods = _proto.EnumeratePrototypes<T>().ToList();
2023-04-20 10:43:13 +10:00
mods.Sort((x, y) => string.Compare(x.ID, y.ID, StringComparison.Ordinal));
rand.Shuffle(mods);
foreach (var mod in mods)
{
if (mod.Cost > rating || (mod.Biomes != null && !mod.Biomes.Contains(biome)))
2023-04-20 10:43:13 +10:00
continue;
rating -= mod.Cost;
return mod;
}
throw new InvalidOperationException();
2023-03-10 16:41:22 +11:00
}
2023-04-20 10:43:13 +10:00
public T GetMod<T>(System.Random rand, ref float rating) where T : class, IPrototype, ISalvageMod
{
var mods = _proto.EnumeratePrototypes<T>().ToList();
mods.Sort((x, y) => string.Compare(x.ID, y.ID, StringComparison.Ordinal));
rand.Shuffle(mods);
foreach (var mod in mods)
{
if (mod.Cost > rating)
continue;
rating -= mod.Cost;
return mod;
}
throw new InvalidOperationException();
}
}
2023-03-10 16:41:22 +11:00