mirror of
https://github.com/DeltaV-Station/Delta-v.git
synced 2026-10-04 13:27:30 +00:00
99 lines
4.5 KiB
C#
99 lines
4.5 KiB
C#
using System.Runtime.CompilerServices;
|
|
using Content.Shared.Atmos.Prototypes;
|
|
using Content.Shared.CCVar;
|
|
using JetBrains.Annotations;
|
|
|
|
namespace Content.Shared.Atmos.EntitySystems;
|
|
|
|
public abstract partial class SharedAtmosphereSystem
|
|
{
|
|
/*
|
|
Partial class for operations involving GasMixtures.
|
|
|
|
Sometimes methods here are abstract because they need different client/server implementations
|
|
due to sandboxing.
|
|
*/
|
|
|
|
/// <summary>
|
|
/// Cached array of gas specific heats.
|
|
/// </summary>
|
|
public float[] GasSpecificHeats => _gasSpecificHeats;
|
|
private float[] _gasSpecificHeats = new float[Atmospherics.TotalNumberOfGases];
|
|
|
|
public string?[] GasReagents = new string[Atmospherics.TotalNumberOfGases];
|
|
protected readonly GasPrototype[] GasPrototypes = new GasPrototype[Atmospherics.TotalNumberOfGases];
|
|
|
|
public virtual void InitializeGases()
|
|
{
|
|
foreach (var gas in Enum.GetValues<Gas>())
|
|
{
|
|
var idx = (int)gas;
|
|
// Log an error if the corresponding prototype isn't found
|
|
if (!_prototypeManager.TryIndex<GasPrototype>(gas.ToString(), out var gasPrototype))
|
|
{
|
|
Log.Error($"Failed to find corresponding {nameof(GasPrototype)} for gas ID {(int)gas} ({gas}) with expected ID \"{gas.ToString()}\". Is your prototype named correctly?");
|
|
continue;
|
|
}
|
|
GasPrototypes[idx] = gasPrototype;
|
|
GasReagents[idx] = gasPrototype.Reagent;
|
|
}
|
|
|
|
Array.Resize(ref _gasSpecificHeats, MathHelper.NextMultipleOf(Atmospherics.TotalNumberOfGases, 4));
|
|
|
|
for (var i = 0; i < GasPrototypes.Length; i++)
|
|
{
|
|
/*
|
|
As an optimization routine we pre-divide the specific heat by the heat scale here,
|
|
so we don't have to do it every time we calculate heat capacity.
|
|
Most usages are going to want the scaled value anyway.
|
|
|
|
If you would like the unscaled specific heat, you'd need to multiply by HeatScale again.
|
|
TODO ATMOS: please just make this 2 separate arrays instead of invoking multiplication every time.
|
|
*/
|
|
_gasSpecificHeats[i] = GasPrototypes[i].SpecificHeat / HeatScale;
|
|
}
|
|
}
|
|
|
|
/// <summary>
|
|
/// Calculates the heat capacity for a <see cref="GasMixture"/>.
|
|
/// </summary>
|
|
/// <param name="mixture">The <see cref="GasMixture"/> to calculate the heat capacity for.</param>
|
|
/// <param name="applyScaling">Whether to apply the heat capacity scaling factor.
|
|
/// This is an extremely important boolean to consider or else you will get heat transfer wrong.
|
|
/// See <see cref="CCVars.AtmosHeatScale"/> for more info.</param>
|
|
/// <returns>The heat capacity of the <see cref="GasMixture"/>.</returns>
|
|
[PublicAPI]
|
|
public float GetHeatCapacity(GasMixture mixture, bool applyScaling)
|
|
{
|
|
var scale = GetHeatCapacityCalculation(mixture.Moles, mixture.Immutable);
|
|
|
|
// By default GetHeatCapacityCalculation() has the heat-scale divisor pre-applied.
|
|
// So if we want the un-scaled heat capacity, we have to multiply by the scale.
|
|
return applyScaling ? scale : scale * HeatScale;
|
|
}
|
|
|
|
/// <summary>
|
|
/// Gets the heat capacity for a <see cref="GasMixture"/>.
|
|
/// </summary>
|
|
/// <param name="mixture">The <see cref="GasMixture"/> to calculate the heat capacity for.</param>
|
|
/// <returns>The heat capacity of the <see cref="GasMixture"/>.</returns>
|
|
/// <remarks>Note that the heat capacity of the mixture may be slightly different from
|
|
/// "real life" as we intentionally fake a heat capacity for space in <see cref="Atmospherics.SpaceHeatCapacity"/>
|
|
/// in order to allow Atmospherics to cool down space.</remarks>
|
|
protected float GetHeatCapacity(GasMixture mixture)
|
|
{
|
|
return GetHeatCapacityCalculation(mixture.Moles, mixture.Immutable);
|
|
}
|
|
|
|
/// <summary>
|
|
/// Gets the heat capacity for a <see cref="GasMixture"/>.
|
|
/// </summary>
|
|
/// <param name="moles">The moles array of the <see cref="GasMixture"/></param>
|
|
/// <param name="space">Whether this <see cref="GasMixture"/> represents space,
|
|
/// and thus experiences space-specific mechanics (we cheat and make it a bit cooler).
|
|
/// See <see cref="Atmospherics.SpaceHeatCapacity"/>.</param>
|
|
/// <returns>The heat capacity of the <see cref="GasMixture"/>.</returns>
|
|
[MethodImpl(MethodImplOptions.AggressiveInlining)]
|
|
protected abstract float GetHeatCapacityCalculation(float[] moles, bool space);
|
|
}
|