public void setThreadedNodeArray(GameObject[,] originalNodes) { pathNodes = new ThreadedWorldTile[originalNodes.GetLength(0), originalNodes.GetLength(1)]; for (int x = 0; x < originalNodes.GetLength(0) - 1; x++) { for (int y = 0; y < originalNodes.GetLength(1) - 1; y++) { GameObject g = originalNodes [x, y]; if (g == null) { } else { WorldTile wt = g.GetComponent <WorldTile> (); if (wt == null) { } else { ThreadedWorldTile t = new ThreadedWorldTile(); t.gridX = wt.gridX; t.gridY = wt.gridY; t.worldPos = wt.transform.position; t.walkable = wt.walkable; pathNodes [x, y] = t; } } } } for (int x = 0; x < originalNodes.GetLength(0) - 1; x++) { for (int y = 0; y < originalNodes.GetLength(1) - 1; y++) { GameObject g = originalNodes [x, y]; if (g == null) { } else { WorldTile wt = g.GetComponent <WorldTile> (); if (wt == null) { } else { ThreadedWorldTile t = pathNodes [x, y]; t.myNeighbours = new List <ThreadedWorldTile> (); foreach (WorldTile n in wt.myNeighbours) { t.myNeighbours.Add(pathNodes [n.gridX, n.gridY]); } } } } } }
int GetDistance(ThreadedWorldTile nodeA, ThreadedWorldTile nodeB) { int dstX = Mathf.Abs(nodeA.gridX - nodeB.gridX); int dstY = Mathf.Abs(nodeA.gridY - nodeB.gridY); if (dstX > dstY) { return(14 * dstY + 10 * (dstX - dstY)); } return(14 * dstX + 10 * (dstY - dstX)); }
void threaded_RetracePath(ThreadedWorldTile startNode, ThreadedWorldTile targetNode, ref List <ThreadedWorldTile> store) { List <ThreadedWorldTile> path = new List <ThreadedWorldTile>(); ThreadedWorldTile currentNode = targetNode; while (currentNode != startNode) { path.Add(currentNode); currentNode = currentNode.parent; } path.Reverse(); store = path; }
ThreadedWorldTile threaded_getNearestWalkableTiles(int gridX, int gridY) { ThreadedWorldTile invalidTile = Pathfinding.me.pathNodes[gridX, gridY]; foreach (ThreadedWorldTile t in invalidTile.myNeighbours) { if (t.walkable == true) { return(t); } } return(null); }
public ThreadedWorldTile threadedGetNearest(Vector3 pos) { ThreadedWorldTile retVal = null; ThreadedWorldTile fallback; int xInd = 0, yInd = 0; bool xDone = false, yDone = false; while (retVal == null) { ThreadedWorldTile wt = Pathfinding.me.pathNodes [xInd, yInd]; if (wt.worldPos.y < pos.y) { yInd++; } else { yDone = true; } if (wt.worldPos.x < pos.x) { xInd++; } else { xDone = true; } if (xDone == true && yDone == true) { retVal = wt; fallback = wt; } } return(retVal); }
public void findPath(int sX, int sY, int eX, int eY, ref List <ThreadedWorldTile> store) { ThreadedWorldTile startNode = Pathfinding.me.pathNodes[sX, sY]; //had a bug where the method would go through all the tiles in the grid causing a lag spike, just added a condititon to check for a nearby walkable tile, if its null after this it just abandons the path ThreadedWorldTile endNode = Pathfinding.me.pathNodes[eX, eY]; if (startNode.walkable == false) { startNode = threaded_getNearestWalkableTiles(startNode.gridX, startNode.gridY); } if (endNode.walkable == false) { endNode = threaded_getNearestWalkableTiles(endNode.gridX, endNode.gridY); } if (startNode == null || endNode == null) { return; } List <ThreadedWorldTile> openSet = new List <ThreadedWorldTile>(); HashSet <ThreadedWorldTile> closedSet = new HashSet <ThreadedWorldTile>(); openSet.Add(startNode); while (openSet.Count > 0) { ThreadedWorldTile node = openSet[0]; for (int i = 1; i < openSet.Count; i++) { if (openSet[i].fCost < node.fCost || openSet[i].fCost == node.fCost) { if (openSet[i].hCost < node.hCost) { node = openSet[i]; } } } openSet.Remove(node); closedSet.Add(node); if (node == endNode) { threaded_RetracePath(startNode, endNode, ref store); return; } foreach (ThreadedWorldTile neighbour in node.myNeighbours) { if (!neighbour.walkable || closedSet.Contains(neighbour) || neighbour == null || node == null) { continue; } int newCostToNeighbour = node.gCost + GetDistance(node, neighbour); if (newCostToNeighbour < neighbour.gCost || !openSet.Contains(neighbour)) { neighbour.gCost = newCostToNeighbour; neighbour.hCost = GetDistance(neighbour, endNode); neighbour.parent = node; if (!openSet.Contains(neighbour)) { openSet.Add(neighbour); } } } } }