Grant condition by unit stance

This commit is contained in:
atlimit8
2017-05-24 11:29:10 -05:00
committed by Paul Chote
parent 5834d7615b
commit cadfbe8a29
2 changed files with 46 additions and 7 deletions

View File

@@ -169,7 +169,7 @@ namespace OpenRA.Mods.Common.Scripting
if (!Enum<UnitStance>.TryParse(value, true, out stance))
throw new LuaException("Unknown stance type '{0}'".F(value));
autotarget.Stance = stance;
autotarget.SetStance(Self, stance);
}
}

View File

@@ -32,6 +32,9 @@ namespace OpenRA.Mods.Common.Traits
[Desc("Possible values are HoldFire, ReturnFire, Defend and AttackAnything. Used for human players.")]
public readonly UnitStance InitialStance = UnitStance.Defend;
[Desc("Stance-condition key-value pairs for specifying condition granting by stance.")]
public readonly Dictionary<UnitStance, string> ConditionByStance = new Dictionary<UnitStance, string>();
[Desc("Allow the player to change the unit stance.")]
public readonly bool EnableStances = true;
@@ -45,24 +48,54 @@ namespace OpenRA.Mods.Common.Traits
public readonly bool TargetWhenDamaged = true;
[GrantedConditionReference]
public IEnumerable<string> GrantedConditions { get { return ConditionByStance.Values; } }
public override object Create(ActorInitializer init) { return new AutoTarget(init, this); }
}
public enum UnitStance { HoldFire, ReturnFire, Defend, AttackAnything }
public class AutoTarget : ConditionalTrait<AutoTargetInfo>, INotifyIdle, INotifyDamage, ITick, IResolveOrder, ISync
public class AutoTarget : ConditionalTrait<AutoTargetInfo>, INotifyIdle, INotifyDamage, ITick, IResolveOrder, ISync, INotifyCreated
{
readonly IEnumerable<AttackBase> activeAttackBases;
readonly AttackFollow[] attackFollows;
[Sync] int nextScanTime = 0;
public UnitStance Stance;
public UnitStance Stance { get { return stance; } }
[Sync] public Actor Aggressor;
[Sync] public Actor TargetedActor;
// NOT SYNCED: do not refer to this anywhere other than UI code
public UnitStance PredictedStance;
UnitStance stance;
ConditionManager conditionManager;
int conditionToken = ConditionManager.InvalidConditionToken;
public void SetStance(Actor self, UnitStance value)
{
if (stance == value)
return;
stance = value;
ApplyStanceCondition(self);
}
void ApplyStanceCondition(Actor self)
{
if (conditionManager == null)
return;
if (conditionToken != ConditionManager.InvalidConditionToken)
conditionToken = conditionManager.RevokeCondition(self, conditionToken);
string condition;
if (Info.ConditionByStance.TryGetValue(stance, out condition))
conditionToken = conditionManager.GrantCondition(self, condition);
}
public AutoTarget(ActorInitializer init, AutoTargetInfo info)
: base(info)
{
@@ -70,18 +103,24 @@ namespace OpenRA.Mods.Common.Traits
activeAttackBases = self.TraitsImplementing<AttackBase>().ToArray().Where(Exts.IsTraitEnabled);
if (init.Contains<StanceInit>())
Stance = init.Get<StanceInit, UnitStance>();
stance = init.Get<StanceInit, UnitStance>();
else
Stance = self.Owner.IsBot || !self.Owner.Playable ? info.InitialStanceAI : info.InitialStance;
stance = self.Owner.IsBot || !self.Owner.Playable ? info.InitialStanceAI : info.InitialStance;
PredictedStance = Stance;
PredictedStance = stance;
attackFollows = self.TraitsImplementing<AttackFollow>().ToArray();
}
void INotifyCreated.Created(Actor self)
{
conditionManager = self.TraitOrDefault<ConditionManager>();
ApplyStanceCondition(self);
}
public void ResolveOrder(Actor self, Order order)
{
if (order.OrderString == "SetUnitStance" && Info.EnableStances)
Stance = (UnitStance)order.ExtraData;
SetStance(self, (UnitStance)order.ExtraData);
}
public void Damaged(Actor self, AttackInfo e)