// Returns neighbouring tiles of the parameter tile (N,E,S,W) public List <BaseTile> GetNeighbours(BaseTile baseTile) { var neighbours = new List <BaseTile>(); for (int x = -1; x <= 1; x++) { for (int y = -1; y <= 1; y++) { if (x == 0 && y == 0) { continue; } int checkX = baseTile.gridX + x; int checkY = baseTile.gridY + y; if (checkX != baseTile.gridX && checkY != baseTile.gridY) { continue; } if (checkX >= 0 && checkX < BoardSize && checkY >= 0 && checkY < BoardSize) { neighbours.Add(tileArray[checkX, checkY]); } } } return(neighbours); }
private int GetDistance(BaseTile a, BaseTile b) { var dstX = Mathf.Abs(a.gridX - b.gridX); var dstY = Mathf.Abs(a.gridY - b.gridY); if (dstX > dstY) { return(14 * dstY + 10 * (dstX - dstY)); } return(14 * dstX + 10 * (dstY - dstX)); }
private List <BaseTile> RetracePath(BaseTile start, BaseTile end) { var path = new List <BaseTile>(); var current = end; while (current != start) { path.Add(current); current = current.parent; } path.Reverse(); return(path); }
public List <BaseTile> FindPath(BaseTile start, BaseTile target) { var openSet = new List <BaseTile>(); var closedSet = new HashSet <BaseTile>(); openSet.Add(start); while (openSet.Count > 0) { BaseTile current = openSet[0]; for (var i = 1; i < openSet.Count; i++) { if (openSet[i].fCost < current.fCost || openSet[i].fCost == current.fCost && openSet[i].hCost < current.hCost) { current = openSet[i]; } } openSet.Remove(current); closedSet.Add(current); if (current == target) { return(RetracePath(start, target)); } foreach (BaseTile neighbour in boardCalculator.GetNeighbours(current)) { if (!neighbour.IsWalkable() || closedSet.Contains(neighbour)) { continue; } var newMovementCostToNeighbour = current.gCost + GetDistance(current, neighbour); if (newMovementCostToNeighbour >= neighbour.gCost && openSet.Contains(neighbour)) { continue; } neighbour.gCost = newMovementCostToNeighbour; neighbour.hCost = GetDistance(neighbour, target); neighbour.parent = current; if (!openSet.Contains(neighbour)) { openSet.Add(neighbour); } } } return(null); }