Make Attack use ChildActivities
This commit is contained in:
@@ -39,8 +39,6 @@ namespace OpenRA.Mods.Common.Activities
|
|||||||
|
|
||||||
WDist minRange;
|
WDist minRange;
|
||||||
WDist maxRange;
|
WDist maxRange;
|
||||||
Activity turnActivity;
|
|
||||||
Activity moveActivity;
|
|
||||||
AttackStatus attackStatus = AttackStatus.UnableToAttack;
|
AttackStatus attackStatus = AttackStatus.UnableToAttack;
|
||||||
|
|
||||||
public Attack(Actor self, Target target, bool allowMovement, bool forceAttack)
|
public Attack(Actor self, Target target, bool allowMovement, bool forceAttack)
|
||||||
@@ -73,6 +71,12 @@ namespace OpenRA.Mods.Common.Activities
|
|||||||
|
|
||||||
public override Activity Tick(Actor self)
|
public override Activity Tick(Actor self)
|
||||||
{
|
{
|
||||||
|
if (ChildActivity != null)
|
||||||
|
{
|
||||||
|
ChildActivity = ActivityUtils.RunActivity(self, ChildActivity);
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
if (IsCanceling)
|
if (IsCanceling)
|
||||||
return NextActivity;
|
return NextActivity;
|
||||||
|
|
||||||
@@ -114,12 +118,10 @@ namespace OpenRA.Mods.Common.Activities
|
|||||||
|
|
||||||
// Move towards the last known position
|
// Move towards the last known position
|
||||||
wasMovingWithinRange = true;
|
wasMovingWithinRange = true;
|
||||||
return ActivityUtils.SequenceActivities(self,
|
QueueChild(self, move.MoveWithinRange(target, WDist.Zero, lastVisibleMaximumRange, checkTarget.CenterPosition, Color.Red), true);
|
||||||
move.MoveWithinRange(target, WDist.Zero, lastVisibleMaximumRange, checkTarget.CenterPosition, Color.Red),
|
return this;
|
||||||
this);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
turnActivity = moveActivity = null;
|
|
||||||
attackStatus = AttackStatus.UnableToAttack;
|
attackStatus = AttackStatus.UnableToAttack;
|
||||||
|
|
||||||
foreach (var attack in attackTraits.Where(x => !x.IsTraitDisabled))
|
foreach (var attack in attackTraits.Where(x => !x.IsTraitDisabled))
|
||||||
@@ -128,26 +130,17 @@ namespace OpenRA.Mods.Common.Activities
|
|||||||
attack.IsAiming = status == AttackStatus.Attacking || status == AttackStatus.NeedsToTurn;
|
attack.IsAiming = status == AttackStatus.Attacking || status == AttackStatus.NeedsToTurn;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (attackStatus.HasFlag(AttackStatus.Attacking))
|
|
||||||
return this;
|
|
||||||
|
|
||||||
if (attackStatus.HasFlag(AttackStatus.NeedsToTurn))
|
|
||||||
return turnActivity;
|
|
||||||
|
|
||||||
if (attackStatus.HasFlag(AttackStatus.NeedsToMove))
|
if (attackStatus.HasFlag(AttackStatus.NeedsToMove))
|
||||||
{
|
|
||||||
wasMovingWithinRange = true;
|
wasMovingWithinRange = true;
|
||||||
return moveActivity;
|
|
||||||
}
|
if (attackStatus >= AttackStatus.NeedsToTurn)
|
||||||
|
return this;
|
||||||
|
|
||||||
return NextActivity;
|
return NextActivity;
|
||||||
}
|
}
|
||||||
|
|
||||||
protected virtual AttackStatus TickAttack(Actor self, AttackFrontal attack)
|
protected virtual AttackStatus TickAttack(Actor self, AttackFrontal attack)
|
||||||
{
|
{
|
||||||
if (IsCanceling)
|
|
||||||
return AttackStatus.UnableToAttack;
|
|
||||||
|
|
||||||
if (!target.IsValidFor(self))
|
if (!target.IsValidFor(self))
|
||||||
return AttackStatus.UnableToAttack;
|
return AttackStatus.UnableToAttack;
|
||||||
|
|
||||||
@@ -168,10 +161,7 @@ namespace OpenRA.Mods.Common.Activities
|
|||||||
var sightRange = rs != null ? rs.Range : WDist.FromCells(2);
|
var sightRange = rs != null ? rs.Range : WDist.FromCells(2);
|
||||||
|
|
||||||
attackStatus |= AttackStatus.NeedsToMove;
|
attackStatus |= AttackStatus.NeedsToMove;
|
||||||
moveActivity = ActivityUtils.SequenceActivities(self,
|
QueueChild(self, move.MoveWithinRange(target, sightRange, target.CenterPosition, Color.Red), true);
|
||||||
move.MoveWithinRange(target, sightRange, target.CenterPosition, Color.Red),
|
|
||||||
this);
|
|
||||||
|
|
||||||
return AttackStatus.NeedsToMove;
|
return AttackStatus.NeedsToMove;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -196,10 +186,7 @@ namespace OpenRA.Mods.Common.Activities
|
|||||||
|
|
||||||
attackStatus |= AttackStatus.NeedsToMove;
|
attackStatus |= AttackStatus.NeedsToMove;
|
||||||
var checkTarget = useLastVisibleTarget ? lastVisibleTarget : target;
|
var checkTarget = useLastVisibleTarget ? lastVisibleTarget : target;
|
||||||
moveActivity = ActivityUtils.SequenceActivities(self,
|
QueueChild(self, move.MoveWithinRange(target, minRange, maxRange, checkTarget.CenterPosition, Color.Red), true);
|
||||||
move.MoveWithinRange(target, minRange, maxRange, checkTarget.CenterPosition, Color.Red),
|
|
||||||
this);
|
|
||||||
|
|
||||||
return AttackStatus.NeedsToMove;
|
return AttackStatus.NeedsToMove;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -208,13 +195,12 @@ namespace OpenRA.Mods.Common.Activities
|
|||||||
if (!Util.FacingWithinTolerance(facing.Facing, desiredFacing, ((AttackFrontalInfo)attack.Info).FacingTolerance))
|
if (!Util.FacingWithinTolerance(facing.Facing, desiredFacing, ((AttackFrontalInfo)attack.Info).FacingTolerance))
|
||||||
{
|
{
|
||||||
attackStatus |= AttackStatus.NeedsToTurn;
|
attackStatus |= AttackStatus.NeedsToTurn;
|
||||||
turnActivity = ActivityUtils.SequenceActivities(self, new Turn(self, desiredFacing), this);
|
QueueChild(self, new Turn(self, desiredFacing), true);
|
||||||
return AttackStatus.NeedsToTurn;
|
return AttackStatus.NeedsToTurn;
|
||||||
}
|
}
|
||||||
|
|
||||||
attackStatus |= AttackStatus.Attacking;
|
attackStatus |= AttackStatus.Attacking;
|
||||||
attack.DoAttack(self, target, armaments);
|
attack.DoAttack(self, target, armaments);
|
||||||
|
|
||||||
return AttackStatus.Attacking;
|
return AttackStatus.Attacking;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -40,8 +40,6 @@ namespace OpenRA.Mods.Common.Activities
|
|||||||
Target lastVisibleTarget;
|
Target lastVisibleTarget;
|
||||||
protected CPos lastVisibleTargetLocation;
|
protected CPos lastVisibleTargetLocation;
|
||||||
bool useLastVisibleTarget;
|
bool useLastVisibleTarget;
|
||||||
|
|
||||||
Activity inner;
|
|
||||||
bool repath;
|
bool repath;
|
||||||
|
|
||||||
public MoveAdjacentTo(Actor self, Target target, WPos? initialTargetPosition = null, Color? targetLineColor = null)
|
public MoveAdjacentTo(Actor self, Target target, WPos? initialTargetPosition = null, Color? targetLineColor = null)
|
||||||
@@ -69,7 +67,7 @@ namespace OpenRA.Mods.Common.Activities
|
|||||||
repath = true;
|
repath = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
protected virtual bool ShouldStop(Actor self, CPos oldTargetPosition)
|
protected virtual bool ShouldStop(Actor self)
|
||||||
{
|
{
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
@@ -95,23 +93,21 @@ namespace OpenRA.Mods.Common.Activities
|
|||||||
lastVisibleTargetLocation = self.World.Map.CellContaining(target.CenterPosition);
|
lastVisibleTargetLocation = self.World.Map.CellContaining(target.CenterPosition);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Target is equivalent to checkTarget variable in other activities
|
||||||
|
// value is either lastVisibleTarget or target based on visibility and validity
|
||||||
|
var targetIsValid = Target.IsValidFor(self);
|
||||||
var oldUseLastVisibleTarget = useLastVisibleTarget;
|
var oldUseLastVisibleTarget = useLastVisibleTarget;
|
||||||
useLastVisibleTarget = targetIsHiddenActor || !target.IsValidFor(self);
|
useLastVisibleTarget = targetIsHiddenActor || !targetIsValid;
|
||||||
|
|
||||||
// Update target lines if required
|
// Update target lines if required
|
||||||
if (useLastVisibleTarget != oldUseLastVisibleTarget && targetLineColor.HasValue)
|
if (useLastVisibleTarget != oldUseLastVisibleTarget && targetLineColor.HasValue)
|
||||||
self.SetTargetLine(useLastVisibleTarget ? lastVisibleTarget : target, targetLineColor.Value, false);
|
self.SetTargetLine(useLastVisibleTarget ? lastVisibleTarget : target, targetLineColor.Value, false);
|
||||||
|
|
||||||
// Target is hidden or dead, and we don't have a fallback position to move towards
|
// Target is hidden or dead, and we don't have a fallback position to move towards
|
||||||
if (useLastVisibleTarget && !lastVisibleTarget.IsValidFor(self))
|
var noTarget = useLastVisibleTarget && !lastVisibleTarget.IsValidFor(self);
|
||||||
return NextActivity;
|
|
||||||
|
|
||||||
// Target is equivalent to checkTarget variable in other activities
|
|
||||||
// value is either lastVisibleTarget or target based on visibility and validity
|
|
||||||
var targetIsValid = Target.IsValidFor(self);
|
|
||||||
|
|
||||||
// Inner move order has completed.
|
// Inner move order has completed.
|
||||||
if (inner == null)
|
if (ChildActivity == null)
|
||||||
{
|
{
|
||||||
// We are done here if the order was cancelled for any
|
// We are done here if the order was cancelled for any
|
||||||
// reason except the target moving.
|
// reason except the target moving.
|
||||||
@@ -119,24 +115,24 @@ namespace OpenRA.Mods.Common.Activities
|
|||||||
return NextActivity;
|
return NextActivity;
|
||||||
|
|
||||||
// Target has moved, and MoveAdjacentTo is still valid.
|
// Target has moved, and MoveAdjacentTo is still valid.
|
||||||
inner = Mobile.MoveTo(() => CalculatePathToTarget(self));
|
ChildActivity = Mobile.MoveTo(() => CalculatePathToTarget(self));
|
||||||
repath = false;
|
repath = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Cancel the current path if the activity asks to stop, or asks to repath
|
// Cancel the current path if the activity asks to stop, or asks to repath
|
||||||
// The repath happens once the move activity stops in the next cell
|
// The repath happens once the move activity stops in the next cell
|
||||||
var shouldStop = ShouldStop(self, oldTargetLocation);
|
var shouldStop = ShouldStop(self);
|
||||||
var shouldRepath = targetIsValid && !repath && ShouldRepath(self, oldTargetLocation);
|
var shouldRepath = targetIsValid && !repath && ShouldRepath(self, oldTargetLocation);
|
||||||
if (shouldStop || shouldRepath)
|
if (shouldStop || shouldRepath || noTarget)
|
||||||
{
|
{
|
||||||
if (inner != null)
|
if (ChildActivity != null)
|
||||||
inner.Cancel(self);
|
ChildActivity.Cancel(self);
|
||||||
|
|
||||||
repath = shouldRepath;
|
repath = shouldRepath;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Ticks the inner move activity to actually move the actor.
|
// Ticks the inner move activity to actually move the actor.
|
||||||
inner = ActivityUtils.RunActivity(self, inner);
|
ChildActivity = ActivityUtils.RunActivity(self, ChildActivity);
|
||||||
|
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
@@ -161,18 +157,10 @@ namespace OpenRA.Mods.Common.Activities
|
|||||||
|
|
||||||
public override IEnumerable<Target> GetTargets(Actor self)
|
public override IEnumerable<Target> GetTargets(Actor self)
|
||||||
{
|
{
|
||||||
if (inner != null)
|
if (ChildActivity != null)
|
||||||
return inner.GetTargets(self);
|
return ChildActivity.GetTargets(self);
|
||||||
|
|
||||||
return Target.None;
|
return Target.None;
|
||||||
}
|
}
|
||||||
|
|
||||||
public override void Cancel(Actor self, bool keepQueue = false)
|
|
||||||
{
|
|
||||||
if (!IsCanceling && inner != null)
|
|
||||||
inner.Cancel(self);
|
|
||||||
|
|
||||||
base.Cancel(self);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -29,16 +29,16 @@ namespace OpenRA.Mods.Common.Activities
|
|||||||
this.maxRange = maxRange;
|
this.maxRange = maxRange;
|
||||||
}
|
}
|
||||||
|
|
||||||
protected override bool ShouldStop(Actor self, CPos oldTargetPosition)
|
protected override bool ShouldStop(Actor self)
|
||||||
{
|
{
|
||||||
// We are now in range. Don't move any further!
|
// We are now in range. Don't move any further!
|
||||||
// HACK: This works around the pathfinder not returning the shortest path
|
// HACK: This works around the pathfinder not returning the shortest path
|
||||||
return AtCorrectRange(self.CenterPosition) && Mobile.CanInteractWithGroundLayer(self);
|
return AtCorrectRange(self.CenterPosition) && Mobile.CanInteractWithGroundLayer(self);
|
||||||
}
|
}
|
||||||
|
|
||||||
protected override bool ShouldRepath(Actor self, CPos oldTargetPosition)
|
protected override bool ShouldRepath(Actor self, CPos targetLocation)
|
||||||
{
|
{
|
||||||
return lastVisibleTargetLocation != oldTargetPosition && (!AtCorrectRange(self.CenterPosition)
|
return lastVisibleTargetLocation != targetLocation && (!AtCorrectRange(self.CenterPosition)
|
||||||
|| !Mobile.CanInteractWithGroundLayer(self));
|
|| !Mobile.CanInteractWithGroundLayer(self));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user