Unstable 0.17.10.0
This commit is contained in:
@@ -360,7 +360,7 @@ namespace Barotrauma
|
||||
public List<Order> CurrentOrders => Info?.CurrentOrders;
|
||||
public bool IsDismissed => GetCurrentOrderWithTopPriority() == null;
|
||||
|
||||
private readonly List<StatusEffect> statusEffects = new List<StatusEffect>();
|
||||
private readonly Dictionary<ActionType, List<StatusEffect>> statusEffects = new Dictionary<ActionType, List<StatusEffect>>();
|
||||
|
||||
public Entity ViewTarget
|
||||
{
|
||||
@@ -1033,34 +1033,6 @@ namespace Barotrauma
|
||||
newCharacter = new Character(prefab, position, seed, characterInfo, id, isRemotePlayer, ragdoll);
|
||||
}
|
||||
|
||||
float healthRegen = newCharacter.Params.Health.ConstantHealthRegeneration;
|
||||
if (healthRegen > 0)
|
||||
{
|
||||
AddDamageReduction("damage", healthRegen);
|
||||
}
|
||||
float eatingRegen = newCharacter.Params.Health.HealthRegenerationWhenEating;
|
||||
if (eatingRegen > 0)
|
||||
{
|
||||
AddDamageReduction("damage", eatingRegen, ActionType.OnEating);
|
||||
}
|
||||
float burnReduction = newCharacter.Params.Health.BurnReduction;
|
||||
if (burnReduction > 0)
|
||||
{
|
||||
AddDamageReduction("burn", burnReduction);
|
||||
}
|
||||
float bleedReduction = newCharacter.Params.Health.BleedingReduction;
|
||||
if (bleedReduction > 0)
|
||||
{
|
||||
AddDamageReduction("bleeding", bleedReduction);
|
||||
}
|
||||
|
||||
void AddDamageReduction(string affliction, float amount, ActionType actionType = ActionType.Always)
|
||||
{
|
||||
newCharacter.statusEffects.Add(StatusEffect.Load(
|
||||
new XElement("StatusEffect", new XAttribute("type", actionType), new XAttribute("target", "Character"),
|
||||
new XElement("ReduceAffliction", new XAttribute("identifier", affliction), new XAttribute("amount", amount))).FromPackage(null), $"automatic damage reduction ({affliction})"));
|
||||
}
|
||||
|
||||
#if SERVER
|
||||
if (GameMain.Server != null && Spawner != null && createNetworkEvent)
|
||||
{
|
||||
@@ -1138,7 +1110,15 @@ namespace Barotrauma
|
||||
healthCommonness.Add(subElement.GetAttributeFloat("commonness", 1.0f));
|
||||
break;
|
||||
case "statuseffect":
|
||||
statusEffects.Add(StatusEffect.Load(subElement, Name));
|
||||
var statusEffect = StatusEffect.Load(subElement, Name);
|
||||
if (statusEffect != null)
|
||||
{
|
||||
if (!statusEffects.ContainsKey(statusEffect.type))
|
||||
{
|
||||
statusEffects.Add(statusEffect.type, new List<StatusEffect>());
|
||||
}
|
||||
statusEffects[statusEffect.type].Add(statusEffect);
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
@@ -3681,13 +3661,19 @@ namespace Barotrauma
|
||||
otherLimb.body.ApplyLinearImpulse(targetLimb.LinearVelocity * targetLimb.Mass, maxVelocity: NetConfig.MaxPhysicsBodyVelocity * 0.5f);
|
||||
if (attacker != null)
|
||||
{
|
||||
foreach (var statusEffect in statusEffects)
|
||||
if (statusEffects.TryGetValue(ActionType.OnSevered, out var statusEffectList))
|
||||
{
|
||||
if (statusEffect.type == ActionType.OnSevered) { statusEffect.SetUser(attacker); }
|
||||
foreach (var statusEffect in statusEffectList)
|
||||
{
|
||||
statusEffect.SetUser(attacker);
|
||||
}
|
||||
}
|
||||
foreach (var statusEffect in targetLimb.StatusEffects)
|
||||
if (targetLimb.StatusEffects.TryGetValue(ActionType.OnSevered, out var limbStatusEffectList))
|
||||
{
|
||||
if (statusEffect.type == ActionType.OnSevered) { statusEffect.SetUser(attacker); }
|
||||
foreach (var statusEffect in limbStatusEffectList)
|
||||
{
|
||||
statusEffect.SetUser(attacker);
|
||||
}
|
||||
}
|
||||
}
|
||||
ApplyStatusEffects(ActionType.OnSevered, 1.0f);
|
||||
@@ -3889,9 +3875,17 @@ namespace Barotrauma
|
||||
private readonly List<ISerializableEntity> targets = new List<ISerializableEntity>();
|
||||
public void ApplyStatusEffects(ActionType actionType, float deltaTime)
|
||||
{
|
||||
foreach (StatusEffect statusEffect in statusEffects)
|
||||
if (actionType == ActionType.OnEating)
|
||||
{
|
||||
float eatingRegen = Params.Health.HealthRegenerationWhenEating;
|
||||
if (eatingRegen > 0)
|
||||
{
|
||||
CharacterHealth.ReduceAfflictionOnAllLimbs("damage".ToIdentifier(), eatingRegen * deltaTime);
|
||||
}
|
||||
}
|
||||
if (!statusEffects.TryGetValue(actionType, out var statusEffectList)) { return; }
|
||||
foreach (StatusEffect statusEffect in statusEffectList)
|
||||
{
|
||||
if (statusEffect.type != actionType) { continue; }
|
||||
if (statusEffect.type == ActionType.OnDamaged)
|
||||
{
|
||||
if (!statusEffect.HasRequiredAfflictions(LastDamage)) { continue; }
|
||||
|
||||
@@ -327,16 +327,13 @@ namespace Barotrauma
|
||||
|
||||
public Limb GetAfflictionLimb(Affliction affliction)
|
||||
{
|
||||
foreach (KeyValuePair<Affliction, LimbHealth> kvp in afflictions)
|
||||
if (afflictions.TryGetValue(affliction, out LimbHealth limbHealth))
|
||||
{
|
||||
if (kvp.Key == affliction)
|
||||
if (limbHealth == null) { return null; }
|
||||
int limbHealthIndex = limbHealths.IndexOf(limbHealth);
|
||||
foreach (Limb limb in Character.AnimController.Limbs)
|
||||
{
|
||||
int limbHealthIndex = limbHealths.IndexOf(kvp.Value);
|
||||
foreach (Limb limb in Character.AnimController.Limbs)
|
||||
{
|
||||
if (limb.HealthIndex == limbHealthIndex) { return limb; }
|
||||
}
|
||||
return null;
|
||||
if (limb.HealthIndex == limbHealthIndex) { return limb; }
|
||||
}
|
||||
}
|
||||
return null;
|
||||
@@ -508,8 +505,8 @@ namespace Barotrauma
|
||||
amount -= matchingAffliction.Strength;
|
||||
matchingAffliction.Strength = 0.0f;
|
||||
matchingAfflictions.RemoveAt(i);
|
||||
if (i == 0) i = matchingAfflictions.Count;
|
||||
if (i > 0) reduceAmount += surplus / i;
|
||||
if (i == 0) { i = matchingAfflictions.Count; }
|
||||
if (i > 0) { reduceAmount += surplus / i; }
|
||||
SteamAchievementManager.OnAfflictionRemoved(matchingAffliction, Character);
|
||||
}
|
||||
else
|
||||
@@ -786,6 +783,8 @@ namespace Barotrauma
|
||||
Character.StackSpeedMultiplier(1f + Character.GetStatValue(StatTypes.WalkingSpeed));
|
||||
}
|
||||
|
||||
UpdateDamageReductions(deltaTime);
|
||||
|
||||
if (!Character.GodMode)
|
||||
{
|
||||
UpdateLimbAfflictionOverlays();
|
||||
@@ -816,6 +815,25 @@ namespace Barotrauma
|
||||
}
|
||||
}
|
||||
|
||||
private void UpdateDamageReductions(float deltaTime)
|
||||
{
|
||||
float healthRegen = Character.Params.Health.ConstantHealthRegeneration;
|
||||
if (healthRegen > 0)
|
||||
{
|
||||
ReduceAfflictionOnAllLimbs("damage".ToIdentifier(), healthRegen * deltaTime);
|
||||
}
|
||||
float burnReduction = Character.Params.Health.BurnReduction;
|
||||
if (burnReduction > 0)
|
||||
{
|
||||
ReduceAfflictionOnAllLimbs("burn".ToIdentifier(), burnReduction * deltaTime);
|
||||
}
|
||||
float bleedingReduction = Character.Params.Health.BleedingReduction;
|
||||
if (bleedingReduction > 0)
|
||||
{
|
||||
ReduceAfflictionOnAllLimbs("bleeding".ToIdentifier(), bleedingReduction * deltaTime);
|
||||
}
|
||||
}
|
||||
|
||||
private void UpdateOxygen(float deltaTime)
|
||||
{
|
||||
if (!Character.NeedsOxygen) { return; }
|
||||
@@ -897,28 +915,14 @@ namespace Barotrauma
|
||||
|
||||
// We need to use another list of the afflictions when we call the status effects triggered by afflictions,
|
||||
// because those status effects may add or remove other afflictions while iterating the collection.
|
||||
private readonly List<(Affliction affliction, Limb limb)> afflictionsCopy = new List<(Affliction affliction, Limb limb)>();
|
||||
private readonly List<Affliction> afflictionsCopy = new List<Affliction>();
|
||||
public void ApplyAfflictionStatusEffects(ActionType type)
|
||||
{
|
||||
afflictionsCopy.Clear();
|
||||
foreach (KeyValuePair<Affliction, LimbHealth> kvp in afflictions)
|
||||
afflictionsCopy.AddRange(afflictions.Keys);
|
||||
foreach (Affliction affliction in afflictionsCopy)
|
||||
{
|
||||
var affliction = kvp.Key;
|
||||
var limbHealth = kvp.Value;
|
||||
Limb targetLimb = null;
|
||||
if (limbHealth != null)
|
||||
{
|
||||
int healthIndex = limbHealths.IndexOf(limbHealth);
|
||||
targetLimb =
|
||||
Character.AnimController.Limbs.LastOrDefault(l => !l.IsSevered && !l.Hidden && l.HealthIndex == healthIndex) ??
|
||||
Character.AnimController.MainLimb;
|
||||
}
|
||||
afflictionsCopy.Add((affliction, GetAfflictionLimb(affliction)));
|
||||
}
|
||||
|
||||
foreach ((Affliction affliction, Limb limb) in afflictionsCopy)
|
||||
{
|
||||
affliction.ApplyStatusEffects(type, 1.0f, this, targetLimb: limb);
|
||||
affliction.ApplyStatusEffects(type, 1.0f, this, targetLimb: GetAfflictionLimb(affliction));
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -584,9 +584,9 @@ namespace Barotrauma
|
||||
private set;
|
||||
}
|
||||
|
||||
private readonly List<StatusEffect> statusEffects = new List<StatusEffect>();
|
||||
private readonly Dictionary<ActionType, List<StatusEffect>> statusEffects = new Dictionary<ActionType, List<StatusEffect>>();
|
||||
|
||||
public IEnumerable<StatusEffect> StatusEffects { get { return statusEffects; } }
|
||||
public Dictionary<ActionType, List<StatusEffect>> StatusEffects { get { return statusEffects; } }
|
||||
|
||||
public Limb(Ragdoll ragdoll, Character character, LimbParams limbParams)
|
||||
{
|
||||
@@ -662,7 +662,15 @@ namespace Barotrauma
|
||||
DamageModifiers.Add(new DamageModifier(subElement, character.Name));
|
||||
break;
|
||||
case "statuseffect":
|
||||
statusEffects.Add(StatusEffect.Load(subElement, Name));
|
||||
var statusEffect = StatusEffect.Load(subElement, Name);
|
||||
if (statusEffect != null)
|
||||
{
|
||||
if (!statusEffects.ContainsKey(statusEffect.type))
|
||||
{
|
||||
statusEffects.Add(statusEffect.type, new List<StatusEffect>());
|
||||
}
|
||||
statusEffects[statusEffect.type].Add(statusEffect);
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
@@ -1159,9 +1167,9 @@ namespace Barotrauma
|
||||
private readonly List<ISerializableEntity> targets = new List<ISerializableEntity>();
|
||||
public void ApplyStatusEffects(ActionType actionType, float deltaTime)
|
||||
{
|
||||
foreach (StatusEffect statusEffect in statusEffects)
|
||||
if (!statusEffects.TryGetValue(actionType, out var statusEffectList)) { return; }
|
||||
foreach (StatusEffect statusEffect in statusEffectList)
|
||||
{
|
||||
if (statusEffect.type != actionType) { continue; }
|
||||
if (statusEffect.type == ActionType.OnDamaged)
|
||||
{
|
||||
if (!statusEffect.HasRequiredAfflictions(character.LastDamage)) { continue; }
|
||||
|
||||
@@ -481,16 +481,16 @@ namespace Barotrauma
|
||||
public bool UseHealthWindow { get; set; }
|
||||
|
||||
[Serialize(0f, IsPropertySaveable.Yes, description: "How easily the character heals from the bleeding wounds. Default 0 (no extra healing)."), Editable(MinValueFloat = 0, MaxValueFloat = 100, DecimalCount = 2)]
|
||||
public float BleedingReduction { get; private set; }
|
||||
public float BleedingReduction { get; set; }
|
||||
|
||||
[Serialize(0f, IsPropertySaveable.Yes, description: "How easily the character heals from the burn wounds. Default 0 (no extra healing)."), Editable(MinValueFloat = 0, MaxValueFloat = 100, DecimalCount = 2)]
|
||||
public float BurnReduction { get; private set; }
|
||||
public float BurnReduction { get; set; }
|
||||
|
||||
[Serialize(0f, IsPropertySaveable.Yes), Editable(MinValueFloat = 0, MaxValueFloat = 10, DecimalCount = 2)]
|
||||
public float ConstantHealthRegeneration { get; private set; }
|
||||
public float ConstantHealthRegeneration { get; set; }
|
||||
|
||||
[Serialize(0f, IsPropertySaveable.Yes), Editable(MinValueFloat = 0, MaxValueFloat = 100, DecimalCount = 2)]
|
||||
public float HealthRegenerationWhenEating { get; private set; }
|
||||
public float HealthRegenerationWhenEating { get; set; }
|
||||
|
||||
[Serialize(false, IsPropertySaveable.Yes), Editable]
|
||||
public bool StunImmunity { get; set; }
|
||||
|
||||
+3
-3
@@ -250,9 +250,9 @@ namespace Barotrauma
|
||||
}
|
||||
}
|
||||
|
||||
//Load the UI files first. This is to allow the game to render
|
||||
//the text in the loading screen as soon as possible.
|
||||
var priorityFiles = getFilesToLoad(f => f is UIStyleFile);
|
||||
//Load the UI and text files first. This is to allow the game
|
||||
//to render the text in the loading screen as soon as possible.
|
||||
var priorityFiles = getFilesToLoad(f => f is UIStyleFile || f is TextFile);
|
||||
|
||||
var remainder = getFilesToLoad(f => !priorityFiles.Contains(f));
|
||||
|
||||
|
||||
@@ -206,7 +206,7 @@ namespace Barotrauma
|
||||
var campaign = MultiPlayerCampaign.StartNew(seed ?? ToolBox.RandomSeed(8), selectedSub, settings);
|
||||
if (selectedSub != null)
|
||||
{
|
||||
campaign.Bank.TryDeduct(selectedSub.Price);
|
||||
campaign.Bank.Deduct(selectedSub.Price);
|
||||
campaign.Bank.Balance = Math.Max(campaign.Bank.Balance, MultiPlayerCampaign.MinimumInitialMoney);
|
||||
}
|
||||
return campaign;
|
||||
|
||||
@@ -161,7 +161,7 @@ namespace Barotrauma.Items.Components
|
||||
/// </summary>
|
||||
public override float GetCurrentPowerConsumption(Connection connection = null)
|
||||
{
|
||||
if (connection != this.powerIn)
|
||||
if (connection != this.powerIn || !IsActive)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
+1
-1
@@ -67,7 +67,7 @@ namespace Barotrauma.Items.Components
|
||||
/// </summary>
|
||||
public override float GetCurrentPowerConsumption(Connection connection = null)
|
||||
{
|
||||
if (connection != this.powerIn)
|
||||
if (connection != this.powerIn || !IsActive)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -179,7 +179,7 @@ namespace Barotrauma.Items.Components
|
||||
public override float GetCurrentPowerConsumption(Connection connection = null)
|
||||
{
|
||||
//There shouldn't be other power connections to this
|
||||
if (connection != this.powerIn)
|
||||
if (connection != this.powerIn || !IsActive)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -138,7 +138,11 @@ namespace Barotrauma.Items.Components
|
||||
{
|
||||
get
|
||||
{
|
||||
if (powerIn != null)
|
||||
if (PoweredByTinkering)
|
||||
{
|
||||
return 1.0f;
|
||||
}
|
||||
else if (powerIn != null)
|
||||
{
|
||||
if (powerIn?.Grid != null) { return powerIn.Grid.Voltage; }
|
||||
}
|
||||
@@ -154,6 +158,22 @@ namespace Barotrauma.Items.Components
|
||||
}
|
||||
}
|
||||
|
||||
public bool PoweredByTinkering
|
||||
{
|
||||
get
|
||||
{
|
||||
if (this is PowerContainer) { return false; }
|
||||
foreach (Repairable repairable in Item.Repairables)
|
||||
{
|
||||
if (repairable.IsTinkering && repairable.TinkeringPowersDevices)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
[Editable, Serialize(true, IsPropertySaveable.Yes, description: "Can the item be damaged by electomagnetic pulses.")]
|
||||
public bool VulnerableToEMP
|
||||
{
|
||||
@@ -459,19 +479,12 @@ namespace Barotrauma.Items.Components
|
||||
if (powered.powerIn != null && powered.powerOut != powered.powerIn)
|
||||
{
|
||||
//Get the new load for the connection
|
||||
float currLoad;
|
||||
if (powered.Item.GetComponent<Repairable>() is Repairable repairable && repairable.IsTinkering && repairable.TinkeringPowersDevices && !(powered is PowerContainer))
|
||||
{
|
||||
currLoad = 0.0f;
|
||||
}
|
||||
else
|
||||
{
|
||||
currLoad = powered.GetCurrentPowerConsumption(powered.powerIn);
|
||||
}
|
||||
float currLoad = powered.GetCurrentPowerConsumption(powered.powerIn);
|
||||
|
||||
//If its a load update its grid load
|
||||
if (currLoad >= 0)
|
||||
{
|
||||
if (powered.PoweredByTinkering) { currLoad = 0.0f; }
|
||||
powered.CurrPowerConsumption = currLoad;
|
||||
if (powered.powerIn.Grid != null)
|
||||
{
|
||||
|
||||
@@ -75,7 +75,8 @@ namespace Barotrauma
|
||||
public class RequiredItemByIdentifier : RequiredItem
|
||||
{
|
||||
public readonly Identifier ItemPrefabIdentifier;
|
||||
public ItemPrefab ItemPrefab => ItemPrefab.Prefabs[ItemPrefabIdentifier];
|
||||
public ItemPrefab ItemPrefab => ItemPrefab.Prefabs.TryGet(ItemPrefabIdentifier, out var prefab) ? prefab
|
||||
: MapEntityPrefab.FindByName(ItemPrefabIdentifier.Value) as ItemPrefab ?? throw new Exception($"No ItemPrefab with identifier or name \"{ItemPrefabIdentifier}\"");
|
||||
public override UInt32 UintIdentifier { get; }
|
||||
|
||||
public override IEnumerable<ItemPrefab> ItemPrefabs => ItemPrefab.ToEnumerable();
|
||||
|
||||
@@ -1,4 +1,3 @@
|
||||
using Lidgren.Network;
|
||||
using Microsoft.Xna.Framework;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
@@ -257,7 +256,7 @@ namespace Barotrauma.Networking
|
||||
public void WritePermissions(IWriteMessage msg)
|
||||
{
|
||||
msg.Write(ID);
|
||||
msg.Write((UInt16)Permissions);
|
||||
msg.WriteRangedInteger((int)Permissions, 0, (int)ClientPermissions.All);
|
||||
if (HasPermission(ClientPermissions.ConsoleCommands))
|
||||
{
|
||||
msg.Write((UInt16)PermittedConsoleCommands.Count);
|
||||
@@ -269,8 +268,7 @@ namespace Barotrauma.Networking
|
||||
}
|
||||
public static void ReadPermissions(IReadMessage inc, out ClientPermissions permissions, out List<DebugConsole.Command> permittedCommands)
|
||||
{
|
||||
UInt16 permissionsInt = inc.ReadUInt16();
|
||||
|
||||
int permissionsInt = inc.ReadRangedInteger(0, (int)ClientPermissions.All);
|
||||
permissions = ClientPermissions.None;
|
||||
permittedCommands = new List<DebugConsole.Command>();
|
||||
try
|
||||
@@ -298,9 +296,7 @@ namespace Barotrauma.Networking
|
||||
|
||||
public void ReadPermissions(IReadMessage inc)
|
||||
{
|
||||
ClientPermissions permissions = ClientPermissions.None;
|
||||
List<DebugConsole.Command> permittedCommands = new List<DebugConsole.Command>();
|
||||
ReadPermissions(inc, out permissions, out permittedCommands);
|
||||
ReadPermissions(inc, out ClientPermissions permissions, out List<DebugConsole.Command> permittedCommands);
|
||||
SetPermissions(permissions, permittedCommands);
|
||||
}
|
||||
|
||||
|
||||
@@ -14,7 +14,7 @@ namespace Barotrauma.IO
|
||||
private static readonly ImmutableArray<Identifier> unwritableDirs = new[] { "Content".ToIdentifier() }.ToImmutableArray();
|
||||
private static readonly ImmutableArray<Identifier> unwritableExtensions = new[]
|
||||
{
|
||||
".pdb", ".com", ".scr", ".dylib", ".so", ".a", ".app", //executables and libraries (.exe, .dll and .json handled separately in CanWrite)
|
||||
".exe", ".dll", ".json", ".pdb", ".com", ".scr", ".dylib", ".so", ".a", ".app", //executables and libraries
|
||||
".bat", ".sh", //shell scripts
|
||||
}.ToIdentifiers().ToImmutableArray();
|
||||
|
||||
@@ -39,10 +39,6 @@ namespace Barotrauma.IO
|
||||
if (!isDirectory)
|
||||
{
|
||||
Identifier extension = System.IO.Path.GetExtension(path).Replace(" ", "").ToIdentifier();
|
||||
if (unwritableExtensions.Any(e => e == extension))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
bool pathStartsWith(string prefix)
|
||||
=> path.StartsWith(prefix, StringComparison.OrdinalIgnoreCase);
|
||||
@@ -53,7 +49,7 @@ namespace Barotrauma.IO
|
||||
&& !pathStartsWith(tempDownloadDir)
|
||||
&& !pathStartsWith(workshopStagingDir)
|
||||
#endif
|
||||
&& (extension == ".dll" || extension == ".exe" || extension == ".json"))
|
||||
&& unwritableExtensions.Any(e => e == extension))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user