Пример #1
0
    public void OnDrawGizmos()
    {
        int debugX = (int)(debugObject.position.x / 160);
        int debugY = (int)(debugObject.position.z / 160);

        List <int> connected = navGraph.associatedNodes[debugX, debugY];

        foreach (int i in connected)
        {
            PortalGraph.PortalNode node = navGraph.nodes[i];
            bool    horiz    = node.isHorizontal;
            Vector2 nodePos  = node.getPosition();
            Vector3 position = new Vector3(nodePos.x, 0, nodePos.y);
            Vector3 size     = Vector3.one * 5;
            if (horiz)
            {
                size += Vector3.right * (node.size) * FlowFieldHandler.grid.getSpacing();
            }
            else
            {
                size += Vector3.forward * (node.size) * FlowFieldHandler.grid.getSpacing();
            }
            Gizmos.DrawSphere(position, 6);
            Gizmos.DrawCube(position, size);

            foreach (int j in node.connectedNodes)
            {
                Vector2 nodePos2 = navGraph.nodes[j].getPosition();
                Vector3 otherPos = new Vector3(nodePos2.x, 0, nodePos2.y);
                Debug.DrawLine(position, otherPos);
            }
        }

        for (int x = 0; x < 16; x++)
        {
            for (int y = 0; y < 16; y++)
            {
                Handles.Label(new Vector3(x, 0, y) * 10 + 10 * FlowGrid.gridResolution * new Vector3(debugX, 0, debugY) + Vector3.up * 45, FlowFieldHandler.grid.getBuilding((x + debugX * 16) * 10, (y + debugY * 16) * 10) + "");
            }
        }

        int subX = (int)(debugObject.position.x % 160) / 10;
        int subY = (int)(debugObject.position.z % 160) / 10;

        Handles.Label(debugObject.position, "" + subX + " " + subY);
        Gizmos.DrawCube(new Vector3((subX + debugX * 16) * 10, 50, (subY + debugY * 16) * 10), Vector3.one * 10);

        if (subX > 0)
        {
            if (FlowFieldHandler.grid.getBuilding(((subX - 1) + debugX * 16) * 10, (subY + debugY * 16) * 10) == -1)
            {
                Gizmos.DrawCube(new Vector3(((subX - 1) + debugX * 16) * 10, 50, (subY + debugY * 16) * 10), Vector3.one * 10);
            }
        }
        if (subY > 0)
        {
            if (FlowFieldHandler.grid.getBuilding((subX + debugX * 16) * 10, ((subY - 1) + debugY * 16) * 10) == -1)
            {
                Gizmos.DrawCube(new Vector3(((subX) + debugX * 16) * 10, 50, (subY - 1 + debugY * 16) * 10), Vector3.one * 10);
            }
        }
        if (subX < 16 - 1)
        {
            if (FlowFieldHandler.grid.getBuilding(((subX + 1) + debugX * 16) * 10, (subY + debugY * 16) * 10) == -1)
            {
                Gizmos.DrawCube(new Vector3(((subX + 1) + debugX * 16) * 10, 50, (subY + debugY * 16) * 10), Vector3.one * 10);
            }
        }
        if (subY < 16 - 1)
        {
            if (FlowFieldHandler.grid.getBuilding((subX + debugX * 16) * 10, ((subY + 1) + debugY * 16) * 10) == -1)
            {
                Gizmos.DrawCube(new Vector3(((subX) + debugX * 16) * 10, 50, (subY + 1 + debugY * 16) * 10), Vector3.one * 10);
            }
        }



        return;

        foreach (PortalGraph.PortalNode node in navGraph.nodes)
        {
            bool    horiz    = node.isHorizontal;
            Vector2 nodePos  = node.getPosition();
            Vector3 position = new Vector3(nodePos.x, 0, nodePos.y);
            Vector3 size     = Vector3.one * 5;
            if (horiz)
            {
                size += Vector3.right * (node.size) * 10;
            }
            else
            {
                size += Vector3.forward * (node.size) * 10;
            }
            Gizmos.DrawSphere(position, 6);
            Gizmos.DrawCube(position, size);

            foreach (int i in node.connectedNodes)
            {
                Vector2 nodePos2 = navGraph.nodes[i].getPosition();
                Vector3 otherPos = new Vector3(nodePos2.x, 0, nodePos2.y);
                Debug.DrawLine(position, otherPos);
            }
        }
    }
Пример #2
0
    public PathRequest calcPath(Vector2 start, Vector2 end, bool reset = false, PathRequest appendTarget = null)
    {
        //TODO generating portal maps

        PathRequest request = (appendTarget == null) ? new PathRequest(grid.getSpacing()) : appendTarget;

        int startChunkX = (int)(start.x / mapSize);
        int startChunkY = (int)(start.y / mapSize);

        int startX = (int)(start.x % mapSize);
        int startY = (int)(start.y % mapSize);

        int endChunkX = (int)(end.x / mapSize);
        int endChunkY = (int)(end.y / mapSize);

        int endX = (int)(end.x % mapSize);
        int endY = (int)(end.y % mapSize);

        //TODO add in detection for which start nodes it has access to.

        PortalGraph.PortalNode startNode = null;
        PortalGraph.PortalNode endNode   = null;


        //TODO add an index to the MapDataChunk that stores the index of which portal each square has access to.
        foreach (int i in navGraph.associatedNodes[startChunkX, startChunkY])
        {
            PortalGraph.PortalNode testNode = navGraph.nodes[i];
            int nodeX;
            int nodeY;

            if (testNode.isHorizontal)
            {
                nodeY = testNode.side ? 0 : FlowGrid.gridResolution - 1;
                nodeX = testNode.startIndex;
            }
            else
            {
                nodeX = testNode.side ? 0 : FlowGrid.gridResolution - 1;
                nodeY = testNode.startIndex;
            }

            var mapChunk = mapData[startChunkX, startChunkY];
            if (pathfinding.calculatePath(mapChunk, mapChunk.AStarGrid[startX, startY], mapChunk.AStarGrid[nodeX, nodeY], true))
            {
                startNode = testNode;
                break;
            }
        }

        foreach (int i in navGraph.associatedNodes[endChunkX, endChunkY])
        {
            PortalGraph.PortalNode testNode = navGraph.nodes[i];
            int nodeX;
            int nodeY;

            if (testNode.isHorizontal)
            {
                nodeY = testNode.side ? 0 : FlowGrid.gridResolution - 1;
                nodeX = testNode.startIndex;
            }
            else
            {
                nodeX = testNode.side ? 0 : FlowGrid.gridResolution - 1;
                nodeY = testNode.startIndex;
            }

            var mapChunk = mapData[endChunkX, endChunkY];
            if (pathfinding.calculatePath(mapChunk, mapChunk.AStarGrid[endX, endY], mapChunk.AStarGrid[nodeX, nodeY], true))
            {
                endNode = testNode;
                break;
            }
        }

        if (startNode == null)
        {
            Debug.LogError("Unit is trapped!");
        }
        if (endNode == null)
        {
            Debug.LogError("Requested Destination is inaccessible");
        }

        pathfinding.calculatePath(navGraph, startNode, endNode, reset);
        List <AStarNode> path = pathfinding.path;

        FlowGrid   finalGrid;
        Vector2Int pos = new Vector2Int(endChunkX, endChunkY);

        finalGrid = (!request.chunkSteps.ContainsKey(pos)) ? new FlowGrid() : request.chunkSteps[pos];
        finalGrid.integrationField[(int)(end.x % FlowGrid.gridResolution), (int)(end.y % FlowGrid.gridResolution)] = 0;
        finalGrid.dirtySquares.Add(new Vector2Int((int)(end.x % FlowGrid.gridResolution), (int)(end.y % FlowGrid.gridResolution)));
        finalGrid.chunkX = endChunkX;
        finalGrid.chunkY = endChunkY;
        finalGrid.compute();
        if (!request.chunkSteps.ContainsKey(pos))
        {
            request.chunkSteps.Add(pos, finalGrid);
        }
        else
        {
            request.chunkSteps[pos] = finalGrid;
        }



        FlowGrid lastGrid = finalGrid;

        for (int i = 1; i < path.Count; i++)//trace from the end to the start
        {
            PortalGraph.PortalNode last    = (PortalGraph.PortalNode)path[i - 1];
            PortalGraph.PortalNode current = (PortalGraph.PortalNode)path[i];

            Vector2Int portalIndex = new Vector2Int(last.portalX, last.portalY);

            if (last.gridX != current.gridX || last.gridY != current.gridY)
            {
                FlowGrid newGrid;
                bool     hasVisited = request.chunkSteps.ContainsKey(new Vector2Int(current.gridX, current.gridY));
                newGrid = hasVisited ? request.chunkSteps[new Vector2Int(current.gridX, current.gridY)] : new FlowGrid();



                newGrid.chunkX = current.gridX;
                newGrid.chunkY = current.gridY;
                if (last.isHorizontal)
                {
                    int yIndex    = !last.side ? 0 : FlowGrid.gridResolution - 1;
                    int yIndexNot = last.side ? 0 : FlowGrid.gridResolution - 1;
                    for (int j = 0; j < last.size; j++)
                    {
                        newGrid.integrationField[last.startIndex + j, yIndex] = lastGrid.integrationField[last.startIndex + j, yIndexNot] + 1;
                        newGrid.dirtySquares.Add(new Vector2Int(last.startIndex + j, yIndex));
                    }
                }
                else
                {
                    int xIndex    = !last.side ? 0 : FlowGrid.gridResolution - 1;
                    int xIndexNot = last.side ? 0 : FlowGrid.gridResolution - 1;
                    for (int j = 0; j < last.size; j++)
                    {
                        newGrid.integrationField[xIndex, last.startIndex + j] = lastGrid.integrationField[xIndexNot, last.startIndex + j] + 1;
                        newGrid.dirtySquares.Add(new Vector2Int(xIndex, last.startIndex + j));
                    }
                }

                newGrid.compute();

                if (last.isHorizontal)
                {
                    int yIndex = !last.side ? 0 : FlowGrid.gridResolution - 1;
                    for (int j = 0; j < last.size; j++)
                    {
                        newGrid.directionField[last.startIndex + j, yIndex] = last.side ? 4 : 0;
                    }
                }
                else
                {
                    int xIndex = !last.side ? 0 : FlowGrid.gridResolution - 1;
                    for (int j = 0; j < last.size; j++)
                    {
                        newGrid.directionField[xIndex, last.startIndex + j] = last.side ? 2 : 6;
                    }
                }

                if (!hasVisited)
                {
                    request.chunkSteps.Add(new Vector2Int(current.gridX, current.gridY), newGrid);
                }
                else
                {
                    request.chunkSteps[new Vector2Int(current.gridX, current.gridY)] = newGrid;
                }
                lastGrid = newGrid;
            }
        }


        return(request);
    }
Пример #3
0
    public PortalGraph generateGraph()
    {
        PortalGraph graph = new PortalGraph(mapSize);

        for (int x = 0; x < 2 * mapSize - 2; x++)
        {
            bool horiz = x % 2 == 0;
            for (int y = 0; y < mapSize - 1 + (horiz ? -1 : 0); y++)
            {
                bool sideA;
                bool sideB;

                if (horiz)//TODO simplify these lines of code
                {
                    sideA = FlowFieldHandler.grid.getBuilding((x / 2 * FlowGrid.gridResolution * FlowFieldHandler.grid.getSpacing()), (y * FlowGrid.gridResolution * FlowFieldHandler.grid.getSpacing()) + (FlowGrid.gridResolution - 1) * FlowFieldHandler.grid.getSpacing()) == -1;
                    sideB = FlowFieldHandler.grid.getBuilding((x / 2 * FlowGrid.gridResolution * FlowFieldHandler.grid.getSpacing()), (y * FlowGrid.gridResolution * FlowFieldHandler.grid.getSpacing()) + (FlowGrid.gridResolution) * FlowFieldHandler.grid.getSpacing()) == -1;
                }
                else
                {
                    sideA = FlowFieldHandler.grid.getBuilding(((x - 1) / 2 * FlowGrid.gridResolution * FlowFieldHandler.grid.getSpacing()) + (FlowGrid.gridResolution - 1) * FlowFieldHandler.grid.getSpacing(), y * FlowGrid.gridResolution * FlowFieldHandler.grid.getSpacing()) == -1;
                    sideB = FlowFieldHandler.grid.getBuilding(((x - 1) / 2 * FlowGrid.gridResolution * FlowFieldHandler.grid.getSpacing()) + (FlowGrid.gridResolution) * FlowFieldHandler.grid.getSpacing(), y * FlowGrid.gridResolution * FlowFieldHandler.grid.getSpacing()) == -1;
                }


                bool foundPortal = sideA && sideB;

                int startIndex = -1;
                int size       = -1;

                if (foundPortal)
                {
                    startIndex = 0;
                    size       = 1;
                }

                for (int i = 1; i < FlowGrid.gridResolution; i++)
                {
                    if (horiz)
                    {
                        sideA = FlowFieldHandler.grid.getBuilding((x / 2 * FlowGrid.gridResolution * FlowFieldHandler.grid.getSpacing()) + i * FlowFieldHandler.grid.getSpacing(), (y * FlowGrid.gridResolution * FlowFieldHandler.grid.getSpacing()) + (FlowGrid.gridResolution - 1) * FlowFieldHandler.grid.getSpacing()) == -1;
                        sideB = FlowFieldHandler.grid.getBuilding((x / 2 * FlowGrid.gridResolution * FlowFieldHandler.grid.getSpacing()) + i * FlowFieldHandler.grid.getSpacing(), (y * FlowGrid.gridResolution * FlowFieldHandler.grid.getSpacing()) + (FlowGrid.gridResolution) * FlowFieldHandler.grid.getSpacing()) == -1;

                        //Debug.Log("Horiz: " + new Vector2((x / 2 * FlowGrid.gridResolution * 10) + i * 10, (y * FlowGrid.gridResolution * 10) + (FlowGrid.gridResolution - 1) * 10));
                        //Debug.Log(FlowField.grid.getBuilding((x / 2 * FlowGrid.gridResolution * 10) + i * 10, (y * FlowGrid.gridResolution * 10) + (FlowGrid.gridResolution - 1) * 10));
                        //Debug.Log(FlowField.grid.getBuilding((x / 2 * FlowGrid.gridResolution * 10) + i * 10, (y * FlowGrid.gridResolution * 10) + (FlowGrid.gridResolution) * 10));
                    }
                    else
                    {
                        sideA = FlowFieldHandler.grid.getBuilding(((x - 1) / 2 * FlowGrid.gridResolution * FlowFieldHandler.grid.getSpacing()) + (FlowGrid.gridResolution - 1) * FlowFieldHandler.grid.getSpacing(), y * FlowGrid.gridResolution * FlowFieldHandler.grid.getSpacing() + i * FlowFieldHandler.grid.getSpacing()) == -1;
                        sideB = FlowFieldHandler.grid.getBuilding(((x - 1) / 2 * FlowGrid.gridResolution * FlowFieldHandler.grid.getSpacing()) + (FlowGrid.gridResolution) * FlowFieldHandler.grid.getSpacing(), y * FlowGrid.gridResolution * FlowFieldHandler.grid.getSpacing() + i * FlowFieldHandler.grid.getSpacing()) == -1;

                        //Debug.Log("Vert: " + new Vector2((x / 2 * FlowGrid.gridResolution * 10), (y * FlowGrid.gridResolution * 10) + (FlowGrid.gridResolution - 1) * 10 + i * 10));
                        //Debug.Log(FlowField.grid.getBuilding((x / 2 * FlowGrid.gridResolution * 10) + (FlowGrid.gridResolution - 1) * 10, (y * FlowGrid.gridResolution * 10 + i * 10)));
                        //Debug.Log(FlowField.grid.getBuilding((x / 2 * FlowGrid.gridResolution * 10) + (FlowGrid.gridResolution) * 10, (y * FlowGrid.gridResolution * 10 + i * 10)));
                    }

                    if (sideA && sideB)
                    {
                        if (foundPortal)
                        {
                            size++;
                        }
                        else
                        {
                            foundPortal = true;
                            startIndex  = i;
                            size        = 1;
                        }
                    }
                    else
                    {
                        if (foundPortal)
                        {
                            foundPortal = false;

                            graph.AddPortal(x, y, size, startIndex);
                        }
                    }
                }
                if (foundPortal)
                {
                    graph.AddPortal(x, y, size, startIndex);
                }
            }
        }

        for (int x = 0; x < mapSize; x++)
        {
            for (int y = 0; y < mapSize; y++)
            {
                List <int> portalIndices = graph.associatedNodes[x, y];
                for (int i = 0; i < portalIndices.Count; i++)
                {
                    int startX;
                    int startY;
                    int startPortalIndex = portalIndices[i];

                    PortalGraph.PortalNode start = graph.nodes[startPortalIndex];
                    bool isHoriz = start.isHorizontal;
                    if (isHoriz)
                    {
                        startX = start.startIndex;
                        startY = (start.side ? 0 : FlowGrid.gridResolution - 1);
                    }
                    else
                    {
                        startY = start.startIndex;
                        startX = (start.side ? 0 : FlowGrid.gridResolution - 1);
                    }
                    for (int j = i + 1; j < portalIndices.Count; j++)
                    {
                        int targetX;
                        int targetY;
                        int targetPortalIndex = portalIndices[j];

                        PortalGraph.PortalNode target = graph.nodes[targetPortalIndex];
                        isHoriz = target.isHorizontal;
                        if (isHoriz)
                        {
                            targetX = target.startIndex;
                            targetY = (target.side ? 0 : FlowGrid.gridResolution - 1);
                        }
                        else
                        {
                            targetY = target.startIndex;
                            targetX = (target.side ? 0 : FlowGrid.gridResolution - 1);
                        }
                        bool foundPath = pathfinding.calculatePath(mapData[x, y], mapData[x, y].AStarGrid[startX, startY], mapData[x, y].AStarGrid[targetX, targetY]);
                        if (foundPath)
                        {
                            graph.Connect(startPortalIndex, targetPortalIndex);
                        }
                    }
                }
            }
        }

        return(graph);
    }