public override OrderInvalidReason Validate() { var r = _InitialMovement.Validate(); // Unit is not stopping in this tile. Ignore stack limit. if (r != OrderInvalidReason.NONE && r != OrderInvalidReason.UNIT_STACK_LIMIT) { return(r); } r = Attacker.CanEnter(ExitTile, true); if (r != OrderInvalidReason.NONE) { return(r); } r = Attacker.CanEnter(AttackTile, false, true); if (r != OrderInvalidReason.NONE) { return(r); } var distance1 = _InitialMovement.Path.Destination.Rules.GetMoveCost(_InitialMovement.Unit, AttackTile, false, true); var distance2 = AttackTile.Rules.GetMoveCost(_InitialMovement.Unit, ExitTile, false, false); if (distance1.UnableReason != OrderInvalidReason.NONE) { return(distance1.UnableReason); } if (distance2.UnableReason != OrderInvalidReason.NONE) { return(distance2.UnableReason); } _MovementPath = new Path <Tile>(_InitialMovement.Path); _MovementPath.Add(AttackTile, distance1.Cost); _MovementPath.Add(ExitTile, distance2.Cost); if (!Attacker.Configuration.HasUnlimitedMovement() && _MovementPath.Distance > Attacker.RemainingMovement) { return(OrderInvalidReason.UNIT_NO_MOVE); } return(Attacker.CanAttack(AttackMethod.OVERRUN, TreatStackAsArmored, null, UseSecondaryWeapon)); }
public bool AutomateMovement(Unit Unit, bool Halted) { if (StopEarly(Unit.Army)) { return(true); } var path = new Path <Tile>( Unit.Army.Match.Map.Tiles[Origin.X, Origin.Y], Unit.Army.Match.Map.Tiles[Destination.X, Destination.Y], t => true, (t, j) => { var rules = t.GetPathOverlayRules(j); if (rules == null || !rules.RoadMove) { return(float.MaxValue); } return(1); }, (t, j) => t.HeuristicDistanceTo(j), t => t.Neighbors(), (t, j) => t == j); int i = 0; for (; i < path.Count; ++i) { if (path[i] == Unit.Position) { break; } } for (int d = 0; i < path.Count && d < Speed; ++i, ++d) { if (StopCondition.Matches(path[i])) { Halted = true; break; } if (i < path.Count - 1 && path[i + 1].Units.Count() > 0) { break; } } var o = new MovementOrder(Unit, path[i], false, !Halted); if (Unit.Army.Match.ExecuteOrder(o) != OrderInvalidReason.NONE) { throw new Exception(string.Format("Could not move unit {0} to {1}: {2}", Unit, path[i], o.Validate())); } return(Halted); }