internal override MGPumCommand calculateCommand() { int enemyID = 1 - playerID; //List<MGPumUnit> possibleMovers = new List<MGPumUnit>; foreach (MGPumUnit unit in state.getAllUnitsInZone(MGPumZoneType.Battlegrounds, this.playerID)) { if (stateOracle.canAttack(unit) && unit.currentRange > 0) { MGPumField goal = state.getField(unit.field.coords + Vector2Int.up); if (goal != null && goal.unit != null && goal.unit.ownerID == enemyID) { MGPumAttackChainMatcher matcher = unit.getAttackMatcher(); MGPumFieldChain chain = new MGPumFieldChain(this.playerID, matcher); chain.add(unit.field); chain.add(goal); MGPumAttackCommand command = new MGPumAttackCommand(playerID, chain, unit); return(command); } } if (stateOracle.canMove(unit) && unit.currentSpeed > 0) { //possibleMovers.Add(unit); MGPumField goal = state.getField(unit.field.coords + Vector2Int.up); if (goal != null) { if (goal.unit == null) { MGPumMoveChainMatcher matcher = unit.getMoveMatcher(); MGPumFieldChain chain = new MGPumFieldChain(this.playerID, matcher); chain.add(unit.field); chain.add(goal); MGPumMoveCommand command = new MGPumMoveCommand(this.playerID, chain, unit); return(command); } } } } return(new MGPumEndTurnCommand(this.playerID)); }
//find path for moving and return it MGPumMoveCommand findPath(MGPumField field, MGPumUnit unit) { // can we find this out in a better way? queued = new bool[8, 8]; tilesToVisit = new SortedSet <Vector2Int>(new AStarComparer(field.coords)); predecessors = new Dictionary <Vector2Int, Vector2Int>(); //distance = new Dictionary<Vector2Int, int>(); tilesToVisit.Add(unit.field.coords); queued[unit.field.coords.x, unit.field.coords.y] = true; int recursion = 0; int maxRecursion = 500; while (tilesToVisit.Count > 0) { recursion++; if (recursion > maxRecursion) { break; } Vector2Int position = tilesToVisit.Min; tilesToVisit.Remove(position); if (!state.fields.inBounds(position)) { continue; } //touchedTiles.Add(position); if (position == field.coords) { List <Vector2Int> path = new List <Vector2Int>(); path.Add(position); //reconstruct path in reverse while (predecessors.ContainsKey(path[0])) { path.Insert(0, predecessors[path[0]]); } MGPumMoveChainMatcher matcher = unit.getMoveMatcher(); MGPumFieldChain chain = new MGPumFieldChain(unit.ownerID, matcher); for (int i = 0; i < path.Count; i++) { chain.add(state.getField(path[i])); } if (chain.isValidChain()) { MGPumMoveCommand mc = new MGPumMoveCommand(this.playerID, chain, unit); return(mc); } continue; } foreach (Vector2Int direction in getDirections()) { Vector2Int neighbor = position + direction; if (!state.fields.inBounds(neighbor)) { continue; } if (!queued[neighbor.x, neighbor.y] && state.getUnitForField(state.getField(neighbor)) == null) { queued[neighbor.x, neighbor.y] = true; tilesToVisit.Add(neighbor); predecessors.Add(neighbor, position); //distance.Add(neighbor, ) } } } return(null); }