int ManhattenDist(GridNodes nodeA, GridNodes nobeB) { int ix = Mathf.Abs(nodeA.gridPosX - nobeB.gridPosX); int iy = Mathf.Abs(nodeA.gridPosY - nobeB.gridPosY); return(ix + iy); }
private bool PopulateGridNodesFromGridPropertiesDictionary(SceneName sceneName, Vector2Int startGridPosition, Vector2Int endGridPosition) { // Get grid properties dictionary for the scene // SceneSave sceneSave; // if (GridPropertiesManager.Instance.GameObjectSave.sceneData.TryGetValue(sceneName.ToString(), out sceneSave)) // { // Get Dict grid property details // if (sceneSave.gridPropertyDetailsDictionary != null) // { // Get grid height and width if (GridPropertiesManager.Instance.GetGridDimensions(sceneName, out Vector2Int gridDimensions, out Vector2Int gridOrigin)) { // Create nodes grid based on grid properties dictionary gridNodes = new GridNodes(gridDimensions.x, gridDimensions.y); gridWidth = gridDimensions.x; gridHeight = gridDimensions.y; originX = gridOrigin.x; originY = gridOrigin.y; // Create openNodeList openNodeList = new List <Node>(); // Create closed Node List closedNodeList = new HashSet <Node>(); }
void gridGen() { grid = new GridNodes[gridSizeX, gridSizeY]; Vector3 botLeft = transform.position - Vector3.right * worldSize.x / 2 - Vector3.forward * worldSize.y / 2; //find the bottom left // Debug.Log(botLeft); for (int x = 0; x < gridSizeX; x++) { for (int y = 0; y < gridSizeY; y++) { Vector3 nodeWordlPos = botLeft + Vector3.right * (x * tileDiameter + tileRad) + Vector3.forward * (y * tileDiameter + tileRad); // finding the node tiles world pos //Debug.Log(nodeWordlPos); bool Wall = true; if (Physics.CheckSphere(nodeWordlPos, tileRad, wallMask)) { Wall = false; } grid[x, y] = new GridNodes(Wall, nodeWordlPos, x, y); // Debug.Log(nodeWordlPos.x); //Debug.Log(nodeWordlPos.y); } } }
void getFoundPath(GridNodes cStartNode, GridNodes cEndNode) { List <GridNodes> foundPath = new List <GridNodes>(); List <Vector3> v3foundPath = new List <Vector3>(); GridNodes current = cEndNode; while (current != cStartNode) { foundPath.Add(current); v3foundPath.Add(current.pos); current = current.Parent; } foundPath.Reverse(); v3foundPath.Reverse(); grid.foundPath = foundPath; storedPath = v3foundPath; }
public List <GridNodes> GetNeighbours(GridNodes node) { List <GridNodes> neighbours = new List <GridNodes>(); for (int x = -1; x <= 1; x++) { for (int y = -1; y <= 1; y++) { if (x == 0 && y == 0) { continue; } // Debug.Log(node.gridPosX); int checkX = node.gridPosX + x; int checkY = node.gridPosY + y; if (checkX >= 0 && checkX < gridSizeX && checkY >= 0 && checkY < gridSizeY) { neighbours.Add(grid[checkX, checkY]); } } } return(neighbours); }
//private void Update() //{ // pathFind(startPos.position, targetPos.position); //} public void pathFind(Vector3 cStartPos, Vector3 cTargetPos) { // Debug.Log("happens"); GridNodes startNode = grid.NodeFromWorldPos(cStartPos); GridNodes targetNode = grid.NodeFromWorldPos(cTargetPos); List <GridNodes> openList = new List <GridNodes>(); HashSet <GridNodes> closedList = new HashSet <GridNodes>(); openList.Add(startNode); int counter = 0; finishedPath = false; while (openList.Count > 0) { GridNodes current = openList[0]; for (int i = 1; i < openList.Count; i++) { if (openList[i].FCost < current.FCost || openList[i].FCost == current.FCost && openList[i].distFromEnd < current.distFromEnd) { current = openList[i]; //Debug.Log(i); } } counter++; openList.Remove(current); closedList.Add(current); if (current == targetNode) { getFoundPath(startNode, targetNode); finishedPath = true; //Debug.Log("path found: " + counter); break; } foreach (GridNodes Neighbor in grid.GetNeighbours(current)) { if (!Neighbor.isObstructed || closedList.Contains(Neighbor)) { continue; } int moveCost = current.distFromStart + ManhattenDist(current, Neighbor); if (!openList.Contains(Neighbor) || moveCost < Neighbor.FCost) { Neighbor.distFromStart = moveCost; Neighbor.distFromEnd = ManhattenDist(Neighbor, targetNode); Neighbor.Parent = current; if (!openList.Contains(Neighbor)) { openList.Add(Neighbor); } } } } }
void Awake() { iA = GetComponent <IA>(); grid = GameObject.Find("GridObject").GetComponent <GridNodes>(); path = new List <Vector3>(); }
/// <summary> /// This method will populate all of the nodes in a tileMap for a given scene, and store within them members from the GridPropertyDetailsDictionary /// including the bool isNPCObstacle, and isPath properties. /// </summary> /// <param name="sceneName"></param> /// <param name="startGridPosition"></param> /// <param name="endGridPosition"></param> /// <returns> populates all of the nodes in the current scene tilemap GridNodes with properties from the GridPropertiesDictionary isPath and isNPCObstacle, and Returns a bool /// stating if it was successful or not. </returns> private bool PopulateGridNodesFromGridPropertiesDictionary(SceneName sceneName, Vector2Int startGridPosition, Vector2Int endGridPosition) { // Get the grid properties dictionary for the given scene in the SceneSave, where the GridPropertiesDictionary is stored (and saved/loaded) SceneSave sceneSave; // Get the SceneData (dictionary of all saved items in that scene) for this scene, if it exists if (GridPropertiesManager.Instance.GameObjectSave.sceneData.TryGetValue(sceneName.ToString(), out sceneSave)) { // Get the dict of grid property details stored in the SceneSave, if it exists if (sceneSave.gridPropertyDetailsDictionary != null) { // Get the grid height, width, and origin of the current scene if the sceneName was found in the dictionary if (GridPropertiesManager.Instance.GetGridDimensions(sceneName, out Vector2Int gridDimensions, out Vector2Int gridOrigin)) { // Create a GridNodes (list of all nodes in a grid for the current scene) based on the grid properties dictionary just obtained, // And populate the grid dimensions and origin for AStar gridNodes = new GridNodes(gridDimensions.x, gridDimensions.y); gridWidth = gridDimensions.x; gridHeight = gridDimensions.y; originX = gridOrigin.x; originY = gridOrigin.y; // Create the openNodeList to be used to store nodes to be checked openNodeList = new List <Node>(); // create the closedNodeList to be used to store already checked nodes closedNodeList = new HashSet <Node>(); } // Just return false if we didn't find a dictionary for this scene else { return(false); } // Populate the start node, from gridNodes.GetGridNode which returns the node in the GridNode array at that position. Subtract the origins because the origin is different in every scene // Tile maps have an origin in the CENTER of the map, we subtract the origin so we start at the bottom left as usual startNode = gridNodes.GetGridNode(startGridPosition.x - gridOrigin.x, startGridPosition.y - gridOrigin.y); // Populate the target node in the same way targetNode = gridNodes.GetGridNode(endGridPosition.x - gridOrigin.x, endGridPosition.y - gridOrigin.y); // Loop through every square in the grid, and populate the obstacle and path info for the each grid square for (int x = 0; x < gridDimensions.x; x++) { for (int y = 0; y < gridDimensions.y; y++) { // Get the gridPropertyDetails for the current square we are looking at (this will have members like isDiggable, isPath, isNPCObstacle, etc), adjusted by the origin as well GridPropertyDetails gridPropertyDetails = GridPropertiesManager.Instance.GetGridPropertyDetails(x + gridOrigin.x, y + gridOrigin.y, sceneSave.gridPropertyDetailsDictionary); // As long as we found the details for that square, populate the obstacle bool and penalty. If not, just quit out and return false from this method if (gridPropertyDetails != null) { // If the current square is an obstacle, create a node at that grid location (obtained from the gridNodes array GetGridNode at this position), // and say so in the Node isObstacle member if (gridPropertyDetails.isNPCObstacle == true) { Node node = gridNodes.GetGridNode(x, y); node.isObstacle = true; } if (gridPropertyDetails.seedItemCode == 10000 || gridPropertyDetails.seedItemCode == 10009 || gridPropertyDetails.seedItemCode == 10010 || gridPropertyDetails.seedItemCode == 10011 || gridPropertyDetails.seedItemCode == 10014 || gridPropertyDetails.seedItemCode == 10016 || gridPropertyDetails.seedItemCode == 10022 || gridPropertyDetails.seedItemCode == 10023) // I added this if statement so that things like trees, rocks, etc are considered obstacles for the path finding algorithm to navigate around { Node node = gridNodes.GetGridNode(x, y); node.isObstacle = true; } // Else, if the current square is a path, create a node at that grid location (obtained from the gridNodes array GetGridNode at this position), // and populate it's movement penalty with pathMovementPenalty else if (gridPropertyDetails.isPath == true) { Node node = gridNodes.GetGridNode(x, y); node.movementPenalty = pathMovementPenalty; } // Else, if the current square is not a path or obstacle, create a node at that grid location (obtained from the gridNodes array GetGridNode at this position), // and populate it's movement penalty with defaultMovementPenalty else { Node node = gridNodes.GetGridNode(x, y); node.movementPenalty = defaultMovementPenalty; } } } } } else { return(false); } }
private bool PopulateGridNodesFromGridPropertiesDictionary(SceneName sceneName, Vector2Int startGridPosition, Vector2Int endGridPosition) { // Get grid properties dictionary for the scene SceneSave sceneSave; if (GridPropertiesManager.Instance.GameObjectSave.sceneData.TryGetValue(sceneName.ToString(), out sceneSave)) { // Get Dict grid property details if (sceneSave.gridPropertyDetailsDictionary != null) { // Get grid height and width if (GridPropertiesManager.Instance.GetGridDimensions(sceneName, out Vector2Int gridDimensions, out Vector2Int gridOrigin)) { // Create nodes grid based on grid properties dictionary gridNodes = new GridNodes(gridDimensions.x, gridDimensions.y); gridWidth = gridDimensions.x; gridHeight = gridDimensions.y; originX = gridOrigin.x; originY = gridOrigin.y; // Create openNodeList openNodeList = new List <Node>(); // Create closed Node List closedNodeList = new HashSet <Node>(); } else { return(false); } // Populate start node startNode = gridNodes.GetGridNode(startGridPosition.x - gridOrigin.x, startGridPosition.y - gridOrigin.y); // Populate target node targetNode = gridNodes.GetGridNode(endGridPosition.x - gridOrigin.x, endGridPosition.y - gridOrigin.y); // populate obstacle and path info for grid for (int x = 0; x < gridDimensions.x; x++) { for (int y = 0; y < gridDimensions.y; y++) { GridPropertyDetails gridPropertyDetails = GridPropertiesManager.Instance.GetGridPropertyDetails(x + gridOrigin.x, y + gridOrigin.y, sceneSave.gridPropertyDetailsDictionary); if (gridPropertyDetails != null) { // If NPC obstacle if (gridPropertyDetails.isNPCObstacle == true) { Node node = gridNodes.GetGridNode(x, y); node.isObstacle = true; } else if (gridPropertyDetails.isPath == true) { Node node = gridNodes.GetGridNode(x, y); node.movementPenalty = pathMovementPenalty; } else { Node node = gridNodes.GetGridNode(x, y); node.movementPenalty = defaultMovementPenalty; } } } } } else { return(false); } }