Ejemplo n.º 1
0
    /// <summary>
    /// this method will create the path that the object has to take.
    /// </summary>
    /// <param name="startPosition"></param>
    /// <param name="endPosition"></param>

    IEnumerator FindPath(Vector3 startPosition, Vector3 endPosition)
    {
        Stopwatch sw = new Stopwatch();

        sw.Start();

        Vector3[] waypoints   = new Vector3[0];
        bool      PathSuccess = false;

        //converts the vector3 position to the node on the map.
        Node startNode = Grid.NodeFromWorldPoint(startPosition);
        Node endNode   = Grid.NodeFromWorldPoint(endPosition);

        //list for containing all the open nodes.
        Heap <Node> openSet = new Heap <Node>(Grid.MaxSize);

        //HashSEt holds a set of objects making it easy to check if a certain object is already in it.
        HashSet <Node> closedSet = new HashSet <Node>();

        openSet.Add(startNode);

        while (openSet.Count > 0)
        {
            //find node in open set with lowest f cost
            Node currentNode = openSet.RemoveFirst();



            closedSet.Add(currentNode);

            //if the node found with lowest fcost is the target, return.
            if (currentNode == endNode)
            {
                //if path is found, stop the stopWatch

                sw.Stop();
                print("path found " + sw.ElapsedMilliseconds + "ms");

                //if path is found, it is successful.
                PathSuccess = true;

                //if pathFound, exit out of the loop.
                break;
            }

            foreach (Node neighbor in Grid.getNeighbors(currentNode))
            {
                //if the neighbor is not traversable or is already in the closed set, skip
                if (!neighbor.walkable || closedSet.Contains(neighbor))
                {
                    continue;
                }
                //add the movement penalty to the cost to the neighbor too.
                int newMovementCostToNeighbor = currentNode.gCost + getDistance(currentNode, neighbor) + neighbor.movementPenalty;

                // if the distance between the current node and the neighbor is less than the gcost or neighbor is not in the open list
                if (newMovementCostToNeighbor < neighbor.gCost || !openSet.Contains(neighbor))
                {
                    neighbor.gCost = newMovementCostToNeighbor;
                    neighbor.hCost = getDistance(neighbor, endNode);

                    neighbor.parent = currentNode;

                    if (!openSet.Contains(neighbor))
                    {
                        openSet.Add(neighbor);
                    }
                    else
                    {
                        openSet.UpdateItem(neighbor);
                    }
                }
            }
        }

        //makes it wait for one frame.
        yield return(null);

        //after  finding the path:
        //if a path has been found, store each node of the path into the array.
        if (PathSuccess)
        {
            waypoints = ReTracePath(startNode, endNode);
        }
        //the reqested data has been obtained.Process is finished
        requestManager.FinishedProcessingPath(waypoints, PathSuccess);
    }