Build 0.20.7.0

This commit is contained in:
Markus Isberg
2022-11-18 18:13:38 +02:00
parent 8c8fd865c5
commit ecb6d40b4b
111 changed files with 1346 additions and 701 deletions
@@ -2,7 +2,6 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Xml.Linq;
namespace Barotrauma.Abilities
{
@@ -1,5 +1,5 @@
using System.Collections.Immutable;
using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework;
using System.Collections.Immutable;
namespace Barotrauma.Abilities
{
@@ -1,7 +1,4 @@
using Microsoft.Xna.Framework;
using System.Xml.Linq;
namespace Barotrauma.Abilities
namespace Barotrauma.Abilities
{
class CharacterAbilityGainSimultaneousSkill : CharacterAbility
{
@@ -15,6 +12,10 @@ namespace Barotrauma.Abilities
skillIdentifier = abilityElement.GetAttributeIdentifier("skillidentifier", "");
ignoreAbilitySkillGain = abilityElement.GetAttributeBool("ignoreabilityskillgain", true);
targetAllies = abilityElement.GetAttributeBool("targetallies", false);
if (skillIdentifier.IsEmpty)
{
DebugConsole.ThrowError($"Error in talent {CharacterTalent.DebugIdentifier}: skill identifier not defined.");
}
}
protected override void ApplyEffect(AbilityObject abilityObject)
@@ -23,13 +24,12 @@ namespace Barotrauma.Abilities
{
if (ignoreAbilitySkillGain && abilitySkillGain.GainedFromAbility) { return; }
Identifier identifier = skillIdentifier == "inherit" ? abilitySkillGain.SkillIdentifier : skillIdentifier;
if (targetAllies)
{
foreach (Character character in Character.GetFriendlyCrew(Character))
foreach (Character otherCharacter in Character.GetFriendlyCrew(Character))
{
if (character == Character) { continue; }
Character.Info?.IncreaseSkillLevel(identifier, abilitySkillGain.Value, gainedFromAbility: true);
if (otherCharacter == Character) { continue; }
otherCharacter.Info?.IncreaseSkillLevel(identifier, abilitySkillGain.Value, gainedFromAbility: true);
}
}
else
@@ -1,6 +1,4 @@
using System.Xml.Linq;
namespace Barotrauma.Abilities
namespace Barotrauma.Abilities
{
class CharacterAbilityGiveAffliction : CharacterAbility
{
@@ -18,7 +16,7 @@ namespace Barotrauma.Abilities
if (afflictionId.IsEmpty)
{
DebugConsole.ThrowError("Error in CharacterAbilityGiveAffliction - affliction identifier not set.");
DebugConsole.ThrowError($"Error in talent {CharacterTalent.DebugIdentifier}, CharacterAbilityGiveAffliction - affliction identifier not set.");
}
}
@@ -1,6 +1,4 @@
using System.Xml.Linq;
namespace Barotrauma.Abilities
namespace Barotrauma.Abilities
{
class CharacterAbilityGiveFlag : CharacterAbility
{
@@ -1,6 +1,4 @@
using System.Xml.Linq;
namespace Barotrauma.Abilities
namespace Barotrauma.Abilities
{
class CharacterAbilityGiveMoney : CharacterAbility
{
@@ -13,6 +11,11 @@ namespace Barotrauma.Abilities
{
amount = abilityElement.GetAttributeInt("amount", 0);
scalingStatIdentifier = abilityElement.GetAttributeIdentifier("scalingstatidentifier", Identifier.Empty);
if (amount == 0)
{
DebugConsole.ThrowError($"Error in talent {CharacterTalent.DebugIdentifier}, CharacterAbilityGiveMoney - amount of money set to 0.");
}
}
private void ApplyEffectSpecific(Character targetCharacter)
@@ -1,6 +1,4 @@
using System;
namespace Barotrauma.Abilities
namespace Barotrauma.Abilities
{
public enum PermanentStatPlaceholder
{
@@ -28,6 +26,10 @@ namespace Barotrauma.Abilities
public CharacterAbilityGivePermanentStat(CharacterAbilityGroup characterAbilityGroup, ContentXElement abilityElement) : base(characterAbilityGroup, abilityElement)
{
statIdentifier = abilityElement.GetAttributeIdentifier("statidentifier", Identifier.Empty);
if (statIdentifier.IsEmpty)
{
DebugConsole.ThrowError($"Error in talent \"{CharacterTalent.DebugIdentifier}\" - stat identifier not defined.");
}
string statTypeName = abilityElement.GetAttributeString("stattype", string.Empty);
statType = string.IsNullOrEmpty(statTypeName) ? StatTypes.None : CharacterAbilityGroup.ParseStatType(statTypeName, CharacterTalent.DebugIdentifier);
value = abilityElement.GetAttributeFloat("value", 0f);
@@ -11,6 +11,14 @@ namespace Barotrauma.Abilities
{
factionIdentifier = abilityElement.GetAttributeIdentifier("identifier", Identifier.Empty);
amount = abilityElement.GetAttributeFloat("amount", 0f);
if (factionIdentifier.IsEmpty)
{
DebugConsole.ThrowError($"Error in talent {CharacterTalent.DebugIdentifier}, faction identifier not defined.");
}
if (amount == 0)
{
DebugConsole.ThrowError($"Error in talent {CharacterTalent.DebugIdentifier}, amount of reputation to give is 0.");
}
}
protected override void ApplyEffect()
@@ -1,6 +1,4 @@
using System.Xml.Linq;
namespace Barotrauma.Abilities
namespace Barotrauma.Abilities
{
class CharacterAbilityGiveResistance : CharacterAbility
{
@@ -10,17 +8,23 @@ namespace Barotrauma.Abilities
public CharacterAbilityGiveResistance(CharacterAbilityGroup characterAbilityGroup, ContentXElement abilityElement) : base(characterAbilityGroup, abilityElement)
{
resistanceId = abilityElement.GetAttributeIdentifier("resistanceid", abilityElement.GetAttributeIdentifier("resistance", Identifier.Empty));
multiplier = abilityElement.GetAttributeFloat("multiplier", 1f); // rename this to resistance for consistency
multiplier = abilityElement.GetAttributeFloat("multiplier", 1f);
if (resistanceId.IsEmpty)
{
DebugConsole.ThrowError("Error in CharacterAbilityGiveResistance - resistance identifier not set.");
}
if (MathUtils.NearlyEqual(multiplier, 1))
{
DebugConsole.AddWarning($"Possible error in talent {CharacterTalent.DebugIdentifier} - multiplier set to 1, which will do nothing.");
}
}
public override void InitializeAbility(bool addingFirstTime)
{
Character.ChangeAbilityResistance(resistanceId, multiplier);
TalentResistanceIdentifier identifier = new(resistanceId, CharacterTalent.Prefab.Identifier);
Character.ChangeAbilityResistance(identifier, multiplier);
}
}
}
@@ -1,6 +1,4 @@
using System.Xml.Linq;
namespace Barotrauma.Abilities
namespace Barotrauma.Abilities
{
class CharacterAbilityGiveStat : CharacterAbility
{
@@ -1,7 +1,4 @@
using Barotrauma.Extensions;
using System.Xml.Linq;
namespace Barotrauma.Abilities
namespace Barotrauma.Abilities
{
class CharacterAbilityGiveTalentPoints : CharacterAbility
{
@@ -9,7 +6,11 @@ namespace Barotrauma.Abilities
public CharacterAbilityGiveTalentPoints(CharacterAbilityGroup characterAbilityGroup, ContentXElement abilityElement) : base(characterAbilityGroup, abilityElement)
{
amount = abilityElement.GetAttributeInt("amount", 0);
amount = abilityElement.GetAttributeInt("amount", 0);
if (amount == 0)
{
DebugConsole.ThrowError($"Error in talent {CharacterTalent.DebugIdentifier}, amount of talent points to give is 0.");
}
}
public override void InitializeAbility(bool addingFirstTime)
@@ -9,6 +9,10 @@ namespace Barotrauma.Abilities
public CharacterAbilityGiveTalentPointsToAllies(CharacterAbilityGroup characterAbilityGroup, ContentXElement abilityElement) : base(characterAbilityGroup, abilityElement)
{
amount = abilityElement.GetAttributeInt("amount", 0);
if (amount == 0)
{
DebugConsole.ThrowError($"Error in talent {CharacterTalent.DebugIdentifier}, amount of talent points to give is 0.");
}
}
public override void InitializeAbility(bool addingFirstTime)
@@ -1,6 +1,4 @@
using Barotrauma.Extensions;
using Microsoft.Xna.Framework;
using System.Xml.Linq;
namespace Barotrauma.Abilities
{
@@ -6,6 +6,10 @@ namespace Barotrauma.Abilities
public CharacterAbilityMarkAsLooted(CharacterAbilityGroup characterAbilityGroup, ContentXElement abilityElement) : base(characterAbilityGroup, abilityElement)
{
identifier = abilityElement.GetAttributeIdentifier("identifier", Identifier.Empty);
if (identifier.IsEmpty)
{
DebugConsole.ThrowError($"Error in talent {CharacterTalent.DebugIdentifier}, identifier is empty in {nameof(CharacterAbilityMarkAsLooted)}.");
}
}
protected override void ApplyEffect(AbilityObject abilityObject)
@@ -1,7 +1,4 @@
using System;
using System.Xml.Linq;
namespace Barotrauma.Abilities
namespace Barotrauma.Abilities
{
class CharacterAbilityModifyFlag : CharacterAbility
{
@@ -1,23 +1,25 @@
using System.Xml.Linq;
namespace Barotrauma.Abilities
namespace Barotrauma.Abilities
{
class CharacterAbilityModifyResistance : CharacterAbility
{
private readonly Identifier resistanceId;
private readonly float resistance;
private readonly float multiplier;
bool lastState;
public override bool AllowClientSimulation => true;
// should probably be split to different classes
public CharacterAbilityModifyResistance(CharacterAbilityGroup characterAbilityGroup, ContentXElement abilityElement) : base(characterAbilityGroup, abilityElement)
{
resistanceId = abilityElement.GetAttributeIdentifier("resistanceid", "");
resistance = abilityElement.GetAttributeFloat("resistance", 1f);
resistanceId = abilityElement.GetAttributeIdentifier("resistanceid", abilityElement.GetAttributeIdentifier("resistance", Identifier.Empty));
multiplier = abilityElement.GetAttributeFloat("multiplier", 1f);
if (resistanceId.IsEmpty)
{
DebugConsole.ThrowError("Error in CharacterAbilityModifyResistance - resistance identifier not set.");
DebugConsole.ThrowError($"Error in talent {CharacterTalent.DebugIdentifier} - resistance identifier not set in {nameof(CharacterAbilityModifyResistance)}.");
}
if (MathUtils.NearlyEqual(multiplier, 1.0f))
{
DebugConsole.AddWarning($"Possible error in talent {CharacterTalent.DebugIdentifier} - resistance set to 1, which will do nothing.");
}
}
@@ -25,7 +27,15 @@ namespace Barotrauma.Abilities
{
if (conditionsMatched != lastState)
{
Character.ChangeAbilityResistance(resistanceId, conditionsMatched ? resistance : 1 / resistance);
TalentResistanceIdentifier identifier = new(resistanceId, CharacterTalent.Prefab.Identifier);
if (conditionsMatched)
{
Character.ChangeAbilityResistance(identifier, multiplier);
}
else
{
Character.RemoveAbilityResistance(identifier);
}
lastState = conditionsMatched;
}
}
@@ -1,6 +1,4 @@
using System.Xml.Linq;
namespace Barotrauma.Abilities
namespace Barotrauma.Abilities
{
class CharacterAbilityModifyStat : CharacterAbility
{
@@ -1,5 +1,4 @@
using Microsoft.Xna.Framework;
using System.Xml.Linq;
namespace Barotrauma.Abilities
{
@@ -1,5 +1,4 @@
using System.Linq;
using System.Xml.Linq;
namespace Barotrauma.Abilities
{
@@ -1,6 +1,4 @@
using System.Xml.Linq;
namespace Barotrauma.Abilities
namespace Barotrauma.Abilities
{
class CharacterAbilityModifyValue : CharacterAbility
{
@@ -11,6 +9,10 @@ namespace Barotrauma.Abilities
{
addedValue = abilityElement.GetAttributeFloat("addedvalue", 0f);
multiplyValue = abilityElement.GetAttributeFloat("multiplyvalue", 1f);
if (MathUtils.NearlyEqual(addedValue, 0.0f) && MathUtils.NearlyEqual(multiplyValue, 1.0f))
{
DebugConsole.ThrowError($"Error in talent {CharacterTalent.DebugIdentifier}, {nameof(CharacterAbilityModifyValue)} - added value is 0 and multiplier is 1, the ability will do nothing.");
}
}
protected override void ApplyEffect(AbilityObject abilityObject)
@@ -1,6 +1,4 @@
using System.Xml.Linq;
namespace Barotrauma.Abilities
namespace Barotrauma.Abilities
{
class CharacterAbilityPutItem : CharacterAbility
{
@@ -9,7 +9,11 @@ namespace Barotrauma.Abilities
public CharacterAbilityResetPermanentStat(CharacterAbilityGroup characterAbilityGroup, ContentXElement abilityElement) : base(characterAbilityGroup, abilityElement)
{
statIdentifier = abilityElement.GetAttributeIdentifier("statidentifier", Identifier.Empty);
statIdentifier = abilityElement.GetAttributeIdentifier("statidentifier", Identifier.Empty);
if (statIdentifier.IsEmpty)
{
DebugConsole.ThrowError($"Error in talent {CharacterTalent.DebugIdentifier}, {nameof(CharacterAbilityResetPermanentStat)} - statIdentifier is empty.");
}
}
protected override void ApplyEffect(AbilityObject abilityObject)
{
@@ -1,7 +1,4 @@
using Microsoft.Xna.Framework;
using System.Xml.Linq;
namespace Barotrauma.Abilities
namespace Barotrauma.Abilities
{
class CharacterAbilityRevive : CharacterAbility
{
@@ -11,6 +11,10 @@ namespace Barotrauma.Abilities
{
identifier = abilityElement.GetAttributeIdentifier("identifier", Identifier.Empty);
value = abilityElement.GetAttributeInt("value", 0);
if (identifier.IsEmpty)
{
DebugConsole.ThrowError($"Error in talent {CharacterTalent.DebugIdentifier}, {nameof(CharacterAbilitySetMetadataInt)} - identifier is empty.");
}
}
public override void InitializeAbility(bool addingFirstTime)
@@ -1,5 +1,4 @@
using System.Collections.Generic;
using System.Xml.Linq;
namespace Barotrauma.Abilities
{
@@ -1,7 +1,5 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Xml.Linq;
namespace Barotrauma.Abilities
{
@@ -1,6 +1,4 @@
using System.Xml.Linq;
namespace Barotrauma.Abilities
namespace Barotrauma.Abilities
{
class CharacterAbilityApprenticeship : CharacterAbility
{
@@ -1,20 +1,17 @@
using System;
using System.Linq;
using System.Xml.Linq;
namespace Barotrauma.Abilities
{
class CharacterAbilityAtmosMachine : CharacterAbility
{
private readonly float addedValue;
private readonly float multiplyValue;
private readonly Identifier[] tags;
private readonly int maxMultiplyCount;
public CharacterAbilityAtmosMachine(CharacterAbilityGroup characterAbilityGroup, ContentXElement abilityElement) : base(characterAbilityGroup, abilityElement)
{
addedValue = abilityElement.GetAttributeFloat("addedvalue", 0f);
multiplyValue = abilityElement.GetAttributeFloat("multiplyvalue", 1f);
tags = abilityElement.GetAttributeIdentifierArray("tags", Array.Empty<Identifier>());
maxMultiplyCount = abilityElement.GetAttributeInt("maxmultiplycount", int.MaxValue);
}
@@ -1,11 +1,8 @@
using System.Collections.Generic;
using System.Xml.Linq;
namespace Barotrauma.Abilities
namespace Barotrauma.Abilities
{
class CharacterAbilityBountyHunter : CharacterAbility
{
private float vitalityPercentage;
private readonly float vitalityPercentage;
public CharacterAbilityBountyHunter(CharacterAbilityGroup characterAbilityGroup, ContentXElement abilityElement) : base(characterAbilityGroup, abilityElement)
{
@@ -1,6 +1,5 @@
using System.Collections.Generic;
using System.Linq;
using System.Xml.Linq;
namespace Barotrauma.Abilities
{
@@ -1,7 +1,4 @@
using Microsoft.Xna.Framework;
using System.Xml.Linq;
namespace Barotrauma.Abilities
namespace Barotrauma.Abilities
{
class CharacterAbilityMultitasker : CharacterAbility
{
@@ -1,12 +1,10 @@
using System.Xml.Linq;
namespace Barotrauma.Abilities
namespace Barotrauma.Abilities
{
class CharacterAbilityPsychoClown : CharacterAbility
{
private StatTypes statType;
private float maxValue;
private string afflictionIdentifier;
private readonly StatTypes statType;
private readonly float maxValue;
private readonly string afflictionIdentifier;
private float lastValue = 0f;
public override bool AllowClientSimulation => true;
@@ -1,8 +1,5 @@
using Barotrauma.Items.Components;
using Microsoft.Xna.Framework;
using System;
using System.Collections.Generic;
using System.Xml.Linq;
namespace Barotrauma.Abilities
{
@@ -1,8 +1,8 @@
#nullable enable
using Barotrauma.Extensions;
using System.Collections.Generic;
using System.Collections.Immutable;
using Barotrauma.Extensions;
namespace Barotrauma.Abilities
{
@@ -66,8 +66,8 @@ namespace Barotrauma
IEnumerable<TalentSubTree> blockingSubTrees = tree.TalentSubTrees.Where(tst => tst.BlockedTrees.Contains(targetTree.Identifier)),
requiredSubTrees = tree.TalentSubTrees.Where(tst => targetTree.RequiredTrees.Contains(tst.Identifier));
return requiredSubTrees.All(tst => tst.IsCompleted(selectedTalents)) && // check if we meet requirements
!blockingSubTrees.Any(tst => tst.HasAnyTalent(selectedTalents)); // check if any other talent trees are blocking this one
return requiredSubTrees.All(tst => tst.HasEnoughTalents(selectedTalents)) && // check if we meet requirements
!blockingSubTrees.Any(tst => tst.HasAnyTalent(selectedTalents) && !tst.HasMaxTalents(selectedTalents)); // check if any other talent trees are blocking this one
}
// i hate this function - markus
@@ -128,16 +128,26 @@ namespace Barotrauma
public static bool IsViableTalentForCharacter(Character character, Identifier talentIdentifier, IReadOnlyCollection<Identifier> selectedTalents)
{
if (character?.Info?.Job.Prefab == null) { return false; }
if (character.Info.GetTotalTalentPoints() - selectedTalents.Count <= 0) { return false; }
if (!JobTalentTrees.TryGet(character.Info.Job.Prefab.Identifier, out TalentTree talentTree)) { return false; }
foreach (var subTree in talentTree!.TalentSubTrees)
{
if (subTree.AllTalentIdentifiers.Contains(talentIdentifier) && subTree.HasMaxTalents(selectedTalents)) { return false; }
foreach (var talentOptionStage in subTree.TalentOptionStages)
{
bool hasTalentInThisTier = talentOptionStage.HasEnoughTalents(selectedTalents);
if (talentOptionStage.TalentIdentifiers.Contains(talentIdentifier))
{
return TalentTreeMeetsRequirements(talentTree, subTree, selectedTalents);
}
bool optionStageCompleted = talentOptionStage.HasEnoughTalents(selectedTalents);
if (!optionStageCompleted)
{
break;
}
/*bool hasTalentInThisTier = talentOptionStage.HasMaxTalents(selectedTalents);
if (!hasTalentInThisTier)
{
if (talentOptionStage.TalentIdentifiers.Contains(talentIdentifier))
@@ -145,7 +155,7 @@ namespace Barotrauma
return TalentTreeMeetsRequirements(talentTree, subTree, selectedTalents);
}
break;
}
}*/
}
}
@@ -196,7 +206,8 @@ namespace Barotrauma
public readonly ImmutableHashSet<Identifier> RequiredTrees;
public readonly ImmutableHashSet<Identifier> BlockedTrees;
public bool IsCompleted(IReadOnlyCollection<Identifier> talents) => TalentOptionStages.All(option => option.HasEnoughTalents(talents));
public bool HasEnoughTalents(IReadOnlyCollection<Identifier> talents) => TalentOptionStages.All(option => option.HasEnoughTalents(talents));
public bool HasMaxTalents(IReadOnlyCollection<Identifier> talents) => TalentOptionStages.All(option => option.HasMaxTalents(talents));
public bool HasAnyTalent(IReadOnlyCollection<Identifier> talents) => TalentOptionStages.Any(option => option.HasSelectedTalent(talents));
public TalentSubTree(ContentXElement subTreeElement)
@@ -228,6 +239,13 @@ namespace Barotrauma
public IEnumerable<Identifier> TalentIdentifiers => talentIdentifiers;
/// <summary>
/// How many talents need to be unlocked to consider this tree completed
/// </summary>
public readonly int RequiredTalents;
/// <summary>
/// How many talents can be unlocked in total
/// </summary>
public readonly int MaxChosenTalents;
/// <summary>
@@ -236,8 +254,9 @@ namespace Barotrauma
/// </summary>
public readonly Dictionary<Identifier, ImmutableHashSet<Identifier>> ShowCaseTalents = new Dictionary<Identifier, ImmutableHashSet<Identifier>>();
public bool HasEnoughTalents(CharacterInfo character) => CountMatchingTalents(character.UnlockedTalents) >= MaxChosenTalents;
public bool HasEnoughTalents(IReadOnlyCollection<Identifier> selectedTalents) => CountMatchingTalents(selectedTalents) >= MaxChosenTalents;
public bool HasEnoughTalents(CharacterInfo character) => CountMatchingTalents(character.UnlockedTalents) >= RequiredTalents;
public bool HasEnoughTalents(IReadOnlyCollection<Identifier> selectedTalents) => CountMatchingTalents(selectedTalents) >= RequiredTalents;
public bool HasMaxTalents(IReadOnlyCollection<Identifier> selectedTalents) => CountMatchingTalents(selectedTalents) >= MaxChosenTalents;
// No LINQ
public bool HasSelectedTalent(IReadOnlyCollection<Identifier> selectedTalents)
@@ -267,10 +286,15 @@ namespace Barotrauma
public TalentOption(ContentXElement talentOptionsElement, Identifier debugIdentifier)
{
MaxChosenTalents = talentOptionsElement.GetAttributeInt("maxchosentalents", 1);
MaxChosenTalents = talentOptionsElement.GetAttributeInt(nameof(MaxChosenTalents), 1);
RequiredTalents = talentOptionsElement.GetAttributeInt(nameof(RequiredTalents), MaxChosenTalents);
if (RequiredTalents > MaxChosenTalents)
{
DebugConsole.ThrowError($"Error in talent tree {debugIdentifier} - MaxChosenTalents is larger than RequiredTalents.");
}
HashSet<Identifier> identifiers = new HashSet<Identifier>();
foreach (ContentXElement talentOptionElement in talentOptionsElement.Elements())
{
Identifier elementName = talentOptionElement.Name.ToIdentifier();
@@ -293,6 +317,15 @@ namespace Barotrauma
}
talentIdentifiers = identifiers.ToImmutableHashSet();
if (RequiredTalents > talentIdentifiers.Count)
{
DebugConsole.ThrowError($"Error in talent tree {debugIdentifier} - completing a stage of the tree requires more talents than there are in the stage.");
}
if (MaxChosenTalents > talentIdentifiers.Count)
{
DebugConsole.ThrowError($"Error in talent tree {debugIdentifier} - maximum number of talents to choose is larger than the number of talents.");
}
}
}
}