示例#1
0
 void UpdateClosestNode()
 {
     MazeNode newClosestNode = MazeController.singleton.ClosestNodeToPositon(
         transform.position);
     if (newClosestNode == null) {
         Debug.LogError("NodeTracker cannot find closest node!");
         return;
     }
     if (newClosestNode == closestNode) {
         return;
     }
     if (isEnemy) {
         if (closestNode != null) {
             closestNode.enemyOccupied = false;
             if (MazeController.singleton.debugColors) {
                 closestNode.floorRenderer.material = closestNode.floorMat;
             }
         }
         newClosestNode.enemyOccupied = true;
         if (MazeController.singleton.debugColors) {
             newClosestNode.floorRenderer.material = MazeController.singleton.debugRed;
         }
     }
     else {
         if (MazeController.singleton.debugColors) {
             if (closestNode != null) {
                 closestNode.floorRenderer.material = closestNode.floorMat;
             }
             newClosestNode.floorRenderer.material = MazeController.singleton.debugBlue;
         }
     }
     closestNode = newClosestNode;
 }
示例#2
0
        public MazeGraph(int dimX, int dimY, int dimZ)
        {
            // If bad people give us bad input, fix it.
            // Code does not respond happily to zero / negative
            // values for a dimension. What would such a maze look like?
            if (dimX < 1)
            {
                dimX = 1;
            }

            if (dimY < 1)
            {
                dimY = 1;
            }

            if (dimZ < 1)
            {
                dimZ = 1;
            }

            sizeX = dimX;
            sizeY = dimY;
            sizeZ = dimZ;
            //Allocate space for graph
            this.graph = new MazeNode[dimX, dimY, dimZ];

            //Set of edges for Kruskal's algorithm
            edges = new ArrayList();

            //Initializa all the nodes, giving XYZ coordinates
            for (int x = 0; x < dimX; x++)
            {
                for (int y = 0; y < dimY; y++)
                {
                    for (int z = 0; z < dimZ; z++)
                    {
                        //Create the nodes
                        graph[x, y, z] = new MazeNode(x, y, z);
                    }
                }
            }

            // Create our set of edges to be considered.
            // Taking all of these edges would make a complete graph
            generateEdges(dimX, dimY, dimZ);

            // Run Kruskal's MST algorithm
            // Graph connections are stored at the node level
            generateMaze(dimX, dimY, dimZ);

            //Arbitrarily define the start of our maze at 0, 0, 0
            start = graph[0, 0, 0];

            //Search the graph, maintaining an order of nodes we reached
            List<MazeNode> orderedVertices = BreadthFirstSearch(start);
            //Our goal node is the last one reached by BFS
            goal = orderedVertices[orderedVertices.Count - 1];

        }
示例#3
0
 public override void GenerateMaze(MazeNode[,] cells)
 {
     System.Random rand = new System.Random();
     if (rand.NextDouble() > 0.5)
         GenerateHorizontal(cells);
     else
         GenerateVertical(cells);
 }
示例#4
0
 public void AddConnection(Direction direction, MazeNode node)
 {
     connections[DirectionToIndex(direction)] = node;
     node.connections[DirectionToIndex(InverseDirection(direction))] = this;
     links[DirectionToIndex(direction)].adjacentNode1 = this;
     links[DirectionToIndex(direction)].adjacentNode2 = node;
     //***DEBUG***
     //AddCurrentConnections(direction, node);
 }
示例#5
0
    private MazeNode GetCurrentTile()
    {
        int x = Mathf.Abs((int)transform.position.x);
        int y = Mathf.Abs((int)transform.position.y);

        MazeNode clickedNode = MazeManager.Instance.GetNode(x, y);

        return(clickedNode);
    }
示例#6
0
    void follow()
    {
        //agent.ResetPath();
        if (Vector3.Distance(transform.position, home) < 2)
        {
            if (stuckBlocker <= 0)
            {
                if (IsStuck(newPosition, oldPosition, oldPosition2))
                {
                    posTimer = 0;
                    posTimer = 5;
                    if (TestDebug)
                    {
                        print("resetting path");
                    }
                    agent.ResetPath();
                    previous2   = previous;
                    previous    = currentNode;
                    currentNode = null;
                    State       = InuState.Flee;
                    return;
                }
            }
        }
        seen = false;
        seen = SeeObject(PlayerObject, LevelMask, home);
        if (seen)
        {
            State         = InuState.Chase;
            nextFootprint = null;
            return;
        }
        if (nextFootprint == null)
        {
            foundFootprint = SeeFootprint(allNodes, LevelMask, home);
            if (foundFootprint == null)
            {
                nextFootprint = foundFootprint;
                State         = InuState.Idle;
            }
            if (foundFootprint != null)
            {
                nextFootprint = foundFootprint;
                agent.SetDestination(foundFootprint.transform.position);
            }
        }
        else
        {
            if (Vector3.Distance(transform.position, nextFootprint.transform.position) < 2)
            {
                nextFootprint = nextFootprint.getNext();
            }

            agent.SetDestination(nextFootprint.transform.position);
        }
    }
示例#7
0
    public static MazeNode[,] GenerateFloor3()
    {
        MazeNode[,] tutorial3 = new MazeNode[6, 5];
        for (int i = 0; i < 6; i++)
        {
            for (int j = 0; j < 5; j++)
            {
                tutorial3[i, j]       = new MazeNode(j, i);
                tutorial3[i, j].Floor = -2;
            }
        }

        tutorial3[0, 0].AddEdge(tutorial3[0, 1]);
        tutorial3[0, 1].AddEdge(tutorial3[1, 1]);
        tutorial3[1, 1].AddEdge(tutorial3[2, 1]);
        tutorial3[2, 1].AddEdge(tutorial3[3, 1]);
        tutorial3[3, 1].AddEdge(tutorial3[3, 2]);
        tutorial3[3, 2].AddEdge(tutorial3[3, 3]);
        tutorial3[3, 3].AddEdge(tutorial3[3, 4]);
        tutorial3[3, 4].AddEdge(tutorial3[2, 4]);
        tutorial3[2, 4].AddEdge(tutorial3[1, 4]);
        tutorial3[1, 4].AddEdge(tutorial3[0, 4]);
        tutorial3[0, 4].AddEdge(tutorial3[0, 3]);
        tutorial3[0, 3].AddEdge(tutorial3[1, 3]);
        tutorial3[1, 3].AddEdge(tutorial3[2, 3]);
        tutorial3[2, 3].AddEdge(tutorial3[2, 2]);
        tutorial3[2, 2].AddEdge(tutorial3[1, 2]);
        tutorial3[1, 2].AddEdge(tutorial3[0, 2]);
        tutorial3[2, 1].AddEdge(tutorial3[2, 0]);
        tutorial3[2, 0].AddEdge(tutorial3[1, 0]);
        tutorial3[2, 0].AddEdge(tutorial3[3, 0]);
        tutorial3[3, 0].AddEdge(tutorial3[4, 0]);
        tutorial3[4, 0].AddEdge(tutorial3[4, 1]);
        tutorial3[4, 1].AddEdge(tutorial3[4, 2]);
        tutorial3[4, 2].AddEdge(tutorial3[4, 3]);
        tutorial3[4, 1].AddEdge(tutorial3[5, 1]);
        tutorial3[5, 1].AddEdge(tutorial3[5, 0]);
        tutorial3[5, 1].AddEdge(tutorial3[5, 2]);
        tutorial3[5, 2].AddEdge(tutorial3[5, 3]);
        tutorial3[5, 3].AddEdge(tutorial3[5, 4]);
        tutorial3[5, 4].AddEdge(tutorial3[4, 4]);

        tutorial3[0, 1].actor = ActorType.Oni;
        tutorial3[4, 3].actor = ActorType.Oni;
        tutorial3[5, 3].actor = ActorType.Oni;
        tutorial3[0, 3].actor = ActorType.Oni;
        tutorial3[1, 1].actor = ActorType.Spike_Trap;
        tutorial3[2, 0].actor = ActorType.Spike_Trap;
        tutorial3[1, 3].actor = ActorType.Spike_Trap;

        tutorial3[0, 2].actor             = ActorType.Ladder;
        tutorial3[4, 4].actor             = ActorType.Ladder;
        MazeGenerator.tutorialSections[2] = tutorial3[0, 2];

        return(tutorial3);
    }
示例#8
0
    public Edge(MazeNode cell1, MazeNode cell2, bool isConnected)
    {
        Random.seed = Seed;
        Seed += SeedIncrement;

        cellOne = cell1;
        cellTwo = cell2;
        connected = isConnected;
        weight = (Random.value * 1000.0f);
    }
示例#9
0
    public int GetKeyFromNode(MazeNode mn)
    {
        int key = 0;

        key += mn.Col;
        key += mn.Row << 6;
        key += mn.Floor << 12;
        //print("getkeyfromnode " + key);
        return(key);
    }
示例#10
0
    public void AddOpenNode(int x, int y, MazeRoom room)
    {
        MazeNode node = GetOrCreateNode(x, y);

        node.IsOpen              = true;
        node.Image               = CreateRectSprite(node.Rect, Color.yellow, FloorType.Room);
        node.IsRoom              = true;
        node.Room                = room;
        node.Room.NumberOfNodes += 1;
    }
示例#11
0
 public static void SetIntersectionNodes(MazeNode root)
 {
     foreach (MazeNode n in nodesInSection(root))
     {
         if (n.GetAdjacentNodes().Count > 2)
         {
             n.Intersection = true;
         }
     }
 }
示例#12
0
 private void RemoveCurrentDeadEnd()
 {
     if (currentDeadEndNode != null)
     {
         currentDeadEndNode.Image.color = Color.clear;
         currentDeadEndNode.IsHidden    = true;
         currentDeadEndNode             = null;
     }
     RemoveDeadEnds();
 }
示例#13
0
    public static MazeNode findNode(MazeNode n, int direction)
    {
        int              deltaX;
        int              deltaY;
        MazeNode         current;
        Stack <MazeNode> visited  = new Stack <MazeNode>();
        Stack <MazeNode> visited2 = new Stack <MazeNode>();

        visited.Push(n);
        visited2.Push(n);

        if (direction == 0)
        {
            deltaX = -1;
            deltaY = 0;
        }
        else if (direction == 1)
        {
            deltaX = 0;
            deltaY = 1;
        }
        else if (direction == 2)
        {
            deltaX = 1;
            deltaY = 0;
        }
        else if (direction == 3)
        {
            deltaX = 0;
            deltaY = -1;
        }
        else
        {
            return(null);
        }

        while (visited.Count > 0)
        {
            current = visited.Pop();
            foreach (MazeNode node in current.GetAdjacentNodes())
            {
                if (!visited2.Contains(node))
                {
                    visited.Push(node);
                    visited2.Push(node);
                    if (node.Col == n.Col + deltaX && node.Row == n.Row + deltaY)
                    {
                        return(node);
                    }
                }
            }
        }

        return(null);
    }
示例#14
0
        /* Construa uma SPANNING TREE com o nó raiz indicado    KRUSKAL ALGORIGHT/*
         * O algoritmo de Kruskal é um algoritmo de amplitude mínima que encontra uma borda com o menor peso possível que conecta quaisquer duas árvores na floresta.
         * É um algoritmo guloso na teoria dos grafos , pois encontra uma árvore geradora mínima para um grafo ponderado conectado, adicionando arcos de custo crescente em cada etapa.
         *  Isso significa que ele encontra um subconjunto das arestas que formam uma árvore que inclui todos os vértices , onde o peso total de todas as arestas da árvore é minimizado.
         *  Se o gráfico não estiver conectado, ele encontrará uma floresta de extensão mínima(uma árvore de abrangência mínima para cada componente conectado.
         * Esse algoritmo apareceu pela primeira vez em Proceedings ofthe American Mathematical Society, pp. 48-50 em 1956, e foi escrito por Joseph Kruskal.*/


        public static void FindSpanningTree(ref MazeNode root)
        {
            Random rand = new Random();


            // Defina o predecessor do nó raiz para que saibamos que ele está na árvore.
            root.Predecessor = root;


            List <MazeLink> links = new List <MazeLink>();


            foreach (MazeNode neighbor in root.Neighbors)
            {
                if (neighbor != null)
                {
                    links.Add(new MazeLink(root, neighbor));
                }
            }


            // Adiciona os outros nós à árvore.
            while (links.Count > 0)
            {
                // Escolha um link aleatório.
                int      link_num = rand.Next(0, links.Count);
                MazeLink link     = links[link_num];
                links.RemoveAt(link_num);


                // Adicione este link à árvore.
                MazeNode to_node = link.ToNode;
                link.ToNode.Predecessor = link.FromNode;


                // Remove quaisquer links da lista desse ponto
                for (int i = links.Count - 1; i >= 0; i--)
                {
                    if (links[i].ToNode.Predecessor != null)
                    {
                        links.RemoveAt(i);
                    }
                }


                // Adiciona os links do to_node à lista
                foreach (MazeNode neighbor in to_node.Neighbors)
                {
                    if ((neighbor != null) && (neighbor.Predecessor == null))
                    {
                        links.Add(new MazeLink(to_node, neighbor));
                    }
                }
            }
        }
示例#15
0
    private List <MazeNode> GetNeighbors(MazeNode node)
    {
        if (neighborLists.ContainsKey(node))
        {
            return(neighborLists[node]);
        }
        List <MazeNode> neighbors = FindNeighbors(node, positions);

        neighborLists[node] = neighbors;
        return(neighbors);
    }
示例#16
0
    private MazeNode GetNode(GridPosition Position)
    {
        MazeNode Node = null;

        if (m_NodeList.ContainsKey(Position))
        {
            Node = m_NodeList[Position];
        }

        return(Node);
    }
示例#17
0
    public override void GenerateMaze(MazeNode[,] cells)
    {
        List<MazeNode> visitedCells = new List<MazeNode>();
        bool buildingTrees = true;
        while (buildingTrees)
        {
            visitedCells.Clear();
            Edge cheapestConnection = FindCheapestLink(cells);
            if (cheapestConnection == null)
                buildingTrees = false;
            else
                cheapestConnection.Connected = true;
        }

        //now, connect the trees
        visitedCells.Clear();
        HashSet<MazeNode> partOfMaze = new HashSet<MazeNode>();
        partOfMaze.Add(cells[0, 0]);
        foreach (MazeNode cell in partOfMaze)
        {
            foreach (Edge conn in cell.Edges)
            {
                if (conn.Connected)
                    visitedCells.Add(conn.MazeCellOne == cell ? conn.MazeCellTwo : conn.MazeCellOne);
            }
        }
        foreach (MazeNode cell in visitedCells)
            partOfMaze.Add(cell);

        List<Edge> neighbors = new List<Edge>();
        while (partOfMaze.Count < cells.Length)
        {
            //find all neighbors
            foreach (MazeNode cell in partOfMaze)
            {
                foreach (Edge conn in cell.Edges)
                {
                    if (!conn.Connected)
                        neighbors.Add(conn);
                }
            }

            //find cheapest connection
            Edge cheapest = neighbors[0];
            foreach (Edge conn in neighbors)
            {
                if (conn.Weight < cheapest.Weight)
                    cheapest = conn;
            }

            cheapest.Connected = true;
            partOfMaze.Add(partOfMaze.Contains(cheapest.MazeCellOne) ? cheapest.MazeCellTwo : cheapest.MazeCellOne);
        }
    }
示例#18
0
    MazeNode GetNeighbor(int x, int y)
    {
        MazeNode neighbor = null;

        if (x > -1 && x < tiles.GetLength(0) && y > -1 && y < tiles.GetLength(1))
        {
            neighbor = tiles[x, y];
        }

        return(neighbor);
    }
示例#19
0
    public static void SetClickZone(int x, int y)
    {
        List <MazeNode> clickArea = new List <MazeNode>();

        MazeBuilder.current = maze.Find(n => n.xy == "(" + x + ", " + y + ")");
        clickArea           = MazeNode.getRange(MazeBuilder.current, MazeBuilder.moveRange);
        foreach (MazeNode area in clickArea)
        {
            ground[area.x][area.y].GetComponent <FloorController>().makeClickable();
        }
    }
示例#20
0
    private int GetDistance(MazeNode nodeA, MazeNode nodeB)
    {
        int dstX = Mathf.Abs(nodeA.NodeX - nodeB.NodeX);
        int dstY = Mathf.Abs(nodeA.NodeY - nodeB.NodeY);

        if (dstX > dstY)
        {
            return(14 * dstY + 10 * (dstX - dstY));
        }
        return(14 * dstX + 10 * (dstY - dstX));
    }
示例#21
0
    public void AddWallNode(int x, int y, bool isCorner, MazeRoom room, OrthogonalDirection wallPosition)
    {
        MazeNode node = GetOrCreateNode(x, y);

        node.IsWall              = true;
        node.IsCornerWall        = isCorner;
        node.Room                = room;
        node.WallPosition        = wallPosition;
        node.Image               = CreateRectSprite(node.Rect, Color.white, FloorType.Room);
        node.Room.NumberOfNodes += 1;
    }
示例#22
0
    private GameObject InstantiateRoom(MazeNode node)
    {
        GameObject room = Instantiate(roomPrefab);

        room.GetComponent <RoomScript>().SetupFromNode(node);
        if (node.RType == MazeNode.RoomType.LevelStart)
        {
            startRoom = room;
        }
        return(room);
    }
示例#23
0
    private List <MazeNode> ChooseFirstNode()
    {
        int x = Random.Range(m_LeftEdge, m_RightEdge);
        int y = Random.Range(m_BottomEdge, m_TopEdge);

        MazeNode FirstNode = CreateNode(x, y);

        List <MazeNode> NodeList = new List <MazeNode>();

        NodeList.Add(FirstNode);
        return(NodeList);
    }
示例#24
0
 public override bool Equals(System.Object obj)
 {
     if ((obj == null) || !this.GetType().Equals(obj.GetType()))
     {
         return(false);
     }
     else
     {
         MazeNode node = (MazeNode)obj;
         return(node.Rect == this.Rect);
     }
 }
示例#25
0
 protected void moveToNextNode()
 {
     if (nodes.Count == 0)
     {
         targetNode = null;
         return;
     }
     targetNode = nodes.Dequeue();
     direction = (targetNode.transform.position - transform.position).normalized;
     Debug.Log(targetNode.transform.position + " " + transform.position);
     animated.SetDirection(getAnimationDirection());
 }
示例#26
0
 private void CreateCells(MazeNode[,] maze, List <MazeNode> emptyCells)
 {
     for (int x = 0; x < maze.GetLength(0); x++)
     {
         for (int y = 0; y < maze.GetLength(1); y++)
         {
             MazeNode newNode = new MazeNode(new Vector2Int(x, y));
             maze[x, y] = newNode;
             emptyCells.Add(newNode);
         }
     }
 }
示例#27
0
    void look()
    {
        posTimer   = 30;
        posTimer2  = 25;
        lookTimer -= Time.deltaTime;
        if (TestDebug)
        {
            print("lookTimer" + lookTimer);
        }
        if (FleeInu(LevelMask, home))
        {
            State = OniState.Flee;
            return;
        }
        seen = false;
        seen = SeeObject(PlayerObject, LevelMask, home);
        if (seen)
        {
            //if player has been seen chase
            awake = true;
            State = OniState.Chase;
            return;
        }
        foundFootprint = SeeFootprint(allNodes, LevelMask, home);
        if (foundFootprint != null)
        {
            //if footprints found follow
            nextFootprint = foundFootprint;
            State         = OniState.Follow;
            return;
        }
        transform.Rotate(Vector3.up * (360 * Time.deltaTime));
        if (lookTimer <= 0)
        {
            if (root != null)
            {
                lookBlocker = 10;
                //old destination reached, update patrol path
                closest = null;
                closest = UpdateClosest(closest, nodes, currentNode, previous, previous2, rb);
                if (closest != null)
                {
                    previous2   = previous;
                    previous    = currentNode;
                    currentNode = closest;
                }

                State = OniState.Patrol;
                return;
            }
        }
    }
    /// <summary>
    /// Returns wether node is connected ot node whose normal should be oriented up.
    /// </summary>
    /// <returns><c>true</c>, if node is connect to node whose normal should be up, <c>false</c> otherwise.</returns>
    /// <param name="node">Node.</param>
    private bool IsNodeConnectedToOrientedUp(MazeNode node)
    {
        bool answer = false;

        foreach (MazeNode neigh in node.ConnectedNeighbors)
        {
            answer = IsNodePositionOrientedUp(neigh); if (answer)
            {
                break;
            }
        }
        return(answer);
    }
示例#29
0
    public void GenerateSimpleFloor(int Size, EMazeAlgorithm Algorithm)
    {
        m_Floors.Clear();

        MazeFloor Floor = new MazeFloor();

        Floor.GenerateSimpleFloor(Size, Algorithm);
        m_Floors.Add(Floor);

        m_EntryNode = new MazeNode();

        UpdateNodeMap();
    }
示例#30
0
    public void GenerateComplexFloor(int SectorCount, int SectorSpacing)
    {
        m_Floors.Clear();

        MazeFloor Floor = new MazeFloor();

        Floor.GenerateComplexFloor(SectorCount, SectorSpacing);
        m_Floors.Add(Floor);

        m_EntryNode = new MazeNode();

        UpdateNodeMap();
    }
示例#31
0
    private void CheckRouteOptions(int row, int column)//List<int[]> routeStartOptions)
    {
        MazeNode     nodeToVisit = mazeNodes[row, column];
        List <int[]> neighbors   = FindNeighbors(nodeToVisit);

        mazeNodes[row, column].isVisited = true;

        totalNodesLeft--;
        if (neighbors.Any())
        {
            RouteOptionsLeft.AddRange(neighbors);
        }
    }
示例#32
0
    private void SpawnBoss()
    {
        Boss            bossPrefab = Resources.Load <Boss>("Boss");
        Boss            boss       = Instantiate(bossPrefab, transform);
        List <MazeRoom> rooms      = mapGenerator.Rooms.FindAll(room => !room.IsEnd && !room.IsStart);
        MazeRoom        bossRoom   = rooms[Random.Range(0, rooms.Count)];

        bossRoom.HasBoss = true;
        MazeNode bossNode = mapGenerator.GetRandomEmptyNodeCloseToCenter(bossRoom);

        boss.transform.position = mapGenerator.GetScaled(bossNode.Rect.position);
        boss.Initialize(LevelManager.main.LevelNumber);
    }
示例#33
0
    public static List <MazeNode> GetIntersectionNodes(MazeNode root)
    {
        List <MazeNode> intersections = new List <MazeNode>();

        foreach (MazeNode n in nodesInSection(root))
        {
            if (n.Intersection)
            {
                intersections.Add(n);
            }
        }
        return(intersections);
    }
示例#34
0
 public void AddCurrentConnections(Direction direction, MazeNode node, bool isMainPath = false)
 {
     currentConnections[DirectionToIndex(direction)] = node;
     node.currentConnections[DirectionToIndex(InverseDirection(direction))] = this;
     links[DirectionToIndex(direction)].wall.SetActive(false);
     links[DirectionToIndex(direction)].wallCollider.gameObject.layer = 2;
     //links[DirectionToIndex(direction)].wall.transform.localPosition = Vector3.up * 3f;
     if (isMainPath) {
         links[DirectionToIndex(direction)].onMainPath = true;
         if (MazeController.singleton.debugColors) {
             links[DirectionToIndex(direction)].floorRenderer.material = MazeController.singleton.debugYellow;
         }
     }
 }
示例#35
0
    public void InitMaze(int mazeSizeX, int mazeSizeY)
    {
        mazeMatrix = new MazeNode[mazeSizeX, mazeSizeY];
        MazeSizeX  = mazeSizeX;
        MazeSizeY  = mazeSizeY;

        for (int i = 0; i < MazeSizeX; i++)
        {
            for (int j = 0; j < MazeSizeY; j++)
            {
                mazeMatrix[i, j] = new MazeNode(i, j);
            }
        }
    }
示例#36
0
    public static void GenerateMessages(MazeNode root, System.Random rand)
    {
        LinkedList <MazeNode> exitPath = GetPath2(root, FarthestDeadEndFromNode(root));
        int max = exitPath.Count;

        int[] places    = { -1, -1, -1 };
        int   placement = 0;

        for (int i = 0; i < 3; i++)
        {
            bool match = false;
            int  temp  = (int)rand.Next(0, max);
            if (root.Floor == 0)
            {
                //print(temp);
                for (int j = 0; j < 3; j++)
                {
                    if (match)
                    {
                        break;
                    }
                    if (temp == places[j])
                    {
                        i--;
                        match = true;
                    }
                }
            }
            if (!match)
            {
                places[i] = temp;
            }
        }

        foreach (MazeNode n in exitPath)
        {
            if (root.Floor == 0)
            {
                //print("exitpath not empty");
                foreach (int place in places)
                {
                    if (placement == place)
                    {
                        n.MessageNode = true;
                    }
                }
            }
            placement++;
        }
    }
示例#37
0
 /// <summary>
 /// Uses a variation of Prims algorthm to select which edges are part of the minimum spanning tree
 /// http://en.wikipedia.org/wiki/Prim's_algorithm
 /// </summary>
 /// <param name="nodes">A complete weighted lattice graph</param>
 public override void GenerateMaze(MazeNode[,] nodes)
 {
     HashSet<MazeNode> visitedNodes = new HashSet<MazeNode>();
     while (true)
     {
         visitedNodes.Clear();
         Edge minimumEdge = FindMinimumEdge(nodes[0, 00], visitedNodes);
         if (minimumEdge == null)
         {
             return;
         }
         minimumEdge.Connected = true;
     }
 }
示例#38
0
    //function called at initialization of oni
    void Start()
    {
        //intialize variables
        anim             = GetComponentInChildren <Animator>();
        rb               = GetComponent <Rigidbody>();
        home             = gameObject.transform.position;
        startingRotation = gameObject.transform.rotation;
        actorID          = GetComponent <Actor>();
        State            = OniState.Idle;
        animState        = OniAnim.Idle;
        awake            = false;
        PlayerObject     = GameObject.FindGameObjectWithTag("Player");
        oldPosition      = home;
        posTimer         = 6;
        posTimer2        = 23;
        root             = MazeGenerator.getSectionBasedOnLocation(home);
        if (root != null)
        {
            nodes = MazeGenerator.GetIntersectionNodes(root);
        }
        fleeTimer  = 5;
        fleeingInu = false;

        currentNode = StartingNode;
        //find home node based on location, a nodes location is its individual values - 8 and then divided by 6
        column = (int)((home.x - 8) / 6);
        row    = (int)((home.z - 8) / 6);
        //print("oni home: x " + home.x + " col: " + column + " z: " + home.z + " row: " + row);
        allNodes = MazeGenerator.nodesInSection(root);

        foreach (MazeNode n in allNodes)
        {
            if (n.Col == column && n.Row == row)
            {
                homeNode = n;
            }
        }

        floor = homeNode.Floor;

        agent = GetComponent <NavMeshAgent>();
        //turn of default nav mesh movement as it doesn't include gravity
        agent.updatePosition = false;
        agent.updateRotation = true;
        agent.nextPosition   = transform.position;
        //transform.position = agent.nextPosition;
        agent.Warp(transform.position);
        //print("trans" + transform.position);
        //print("nav" + agent.nextPosition);
    }
示例#39
0
    public override void RetracePath(MazeNode startNode, MazeNode endNode)
    {
        List <MazeNode> path        = new List <MazeNode>();
        MazeNode        currentNode = endNode;

        while (currentNode != startNode)
        {
            path.Add(currentNode);
            currentNode = currentNode.ParentNode;
        }
        path.Reverse();

        this.path = path;
    }
示例#40
0
    Edge FindCheapestLink(MazeNode[,] cells)
    {
        Edge cheapestConnection = null;
        for (int x = 0; x < cells.GetLength(0); x++)
        {
            for (int y = 0; y < cells.GetLength(0); y++)
            {
                MazeNode cell = cells[x, y];
                if (cell.ConnectedNodes == 0)
                {
                    foreach (Edge conn in cell.Edges)
                    {
                        if (cheapestConnection == null || conn.Weight < cheapestConnection.Weight)
                            cheapestConnection = conn;
                    }
                }
            }
        }

        return cheapestConnection;
    }
示例#41
0
    /// <summary>
    /// Recursive function which traverses cells selecting the minimum edge in the graph
    /// </summary>
    Edge FindMinimumEdge(MazeNode node, HashSet<MazeNode> visitedNodes)
    {
        // If the cell is null, it's the edge of the graph. If we've already visited it, ignore it
        if (node == null || visitedNodes.Contains(node))
        {
            return null;
        }
        visitedNodes.Add(node);

        Edge minimumEdge = null;

        //For all surroundeding edges
        foreach (Edge edge in node.Edges)
        {
            if (edge != null)
            {
                Edge candidate = null;
                MazeNode otherNode = edge.MazeCellOne == node ? edge.MazeCellTwo : edge.MazeCellOne;

                if (edge.Connected)
                {
                    candidate = FindMinimumEdge(otherNode, visitedNodes);
                }
                else if (otherNode.ConnectedNodes <= 0) // if the otherNode isn't already in the tree, this edge is a candidate
                {
                    candidate = edge;
                }

                if (candidate != null)
                {
                    if (minimumEdge == null || candidate.Weight < minimumEdge.Weight)
                    {
                        minimumEdge = candidate;
                    }
                }
            }
        }

        return minimumEdge;
    }
示例#42
0
    public virtual void GenerateMaze(MazeNode[,] cells)
    {
        for (int x = 0; x < cells.GetLength(0); x++)
        {
            for (int y = 0; y < cells.GetLength(1); y++)
            {
                MazeNode cell = cells[x, y];

                if (cell.Right != null)
                {
                    cell.Right.Connected = true;
                    cell.Right.MazeCellOne.Left.Connected = true;
                }

                if (cell.Above != null)
                {
                    cell.Above.Connected = true;
                    cell.Above.MazeCellOne.Below.Connected = true;
                }
            }
        }
    }
示例#43
0
    private static void GenerateHorizontal(MazeNode[,] cells)
    {
        for (int x = 0; x < cells.GetLength(0); x++)
        {
            for (int y = 0; y < cells.GetLength(1); y++)
            {
                MazeNode cell = cells[x, y];
                bool noRoof = false;
                if (y % 2 == 1)
                {
                    if (x == cells.GetLength(0) - 1)
                    {
                        noRoof = true;
                    }
                }
                else
                {
                    if (x == 0)
                    {
                        noRoof = true;
                    }
                }

                if (noRoof && cell.Above != null)
                {
                    cell.Above.Connected = true;
                    cell.Above.MazeCellOne.Below.Connected = true;
                }

                if (cell.Right != null)
                {
                    cell.Right.Connected = true;
                    cell.Right.MazeCellOne.Left.Connected = true;
                }

            }
        }
    }
 void SpawnPlayer()
 {
     if (playerPrefab == null) {
         Debug.LogWarning("No player prefab assigned to MazeController!");
         return;
     }
     if (spawnPlayer) {
         GameObject spawnedPlayer = Instantiate(playerPrefab, startNode.transform.position, Quaternion.identity) as GameObject;
         player = spawnedPlayer.GetComponent<NodeTracker>();
         player.closestNode = startNode;
         playerNode = startNode;
     }
 }
 void SpawnNote(MazeNode node, int noteIndex)
 {
     GameObject newNote = Instantiate(notePrefab, node.transform.position, Quaternion.identity) as GameObject;
     NotePickup noteScript = newNote.GetComponent<NotePickup>();
     noteScript.SetNoteText(NoteManager.singleton.allNotes[noteIndex]);
 }
 void SwapWalls(MazeNode evadeNode)
 {
     AgentEvade(playerNode, evadeNode, 0, wallSwapDepth, EvadeUseMode.wallPlacement);
     CreateLoops(1, 0, doColors: true);
 }
 void SpawnWraith(MazeNode node, bool realWraith)
 {
     if (debugColors) {
         node.floorRenderer.material = debugRed;
     }
     if (wraithPrefab == null) {
         Debug.LogError("Maze Controller wraith prefab not set!");
         return;
     }
     GameObject newWraith = Instantiate(wraithPrefab, node.transform.position, Quaternion.identity) as GameObject;
     NodeTracker wraithTracker = newWraith.GetComponent<NodeTracker>();
     if (wraithTracker == null) {
         Debug.LogError("Wraith prefab needs a NodeTracker script!");
         return;
     }
     wraithTracker.closestNode = node;
     node.enemyOccupied = true;
     WraithAI ai = newWraith.GetComponent<WraithAI>();
     if (ai == null) {
         Debug.LogError("Wraith prefab needs an AI script!");
         return;
     }
     ai.SetReal(realWraith);
     ai.player = player;
 }
 void Update()
 {
     if (useDebugKeys) {
         if (Input.GetKeyDown(aStarKey)) {
             StartCoroutine(AStarAgent());
         }
         if (Input.GetKeyDown(searchKey)) {
             ClearNodesSearched();
             AgentSearch(playerNode, 0);
         }
         if (Input.GetKeyDown(evadeKey)) {
             ClearNodesSearched();
             AgentEvade(playerNode, exitNode, 0, evadeDistance);
         }
         if (Input.GetKeyDown(clearKey)) {
             ClearDebugColors();
         }
         if (Input.GetKeyDown(showPathKey)) {
             ShowGoldenPath();
         }
         if (Input.GetKeyDown(showLoopsKey)) {
             DetectLoops();
         }
         if (Input.GetKeyDown(toggleDebugKey)) {
             debugColors = !debugColors;
         }
     }
     if (debugColors) {
         if (colorsOff) {
             ShowGoldenPath();
             colorsOff = false;
         }
     }
     if (!debugColors) {
         if (!colorsOff) {
             ClearDebugColors();
             colorsOff = true;
         }
     }
     if (!swapWalls && wallTimer != null) {
         StopCoroutine(wallTimer);
         wallTimer = null;
     }
     if (swapWalls && wallTimer == null) {
         wallTimer = StartCoroutine(WallSwappingTimer(wallSwapTime));
     }
     if (player != null) {
         playerNode = player.closestNode;
     }
     exit.cubeRenderer.material = debugBlack;
 }
示例#49
0
 void Awake()
 {
     nodeTracker = GetComponent<NodeTracker>();
     motor = GetComponent<Motor>();
     currentBehavior = AIState.idle;
     hasLineOfSight = false;
     lastKnownPlayerLocation = null;
     freezeAI = false;
     matController = GetComponent<AgentMaterialController>();
 }
示例#50
0
 public MazeEdge(MazeNode first, MazeNode second)
 {
     joinedNodes = new MazeNode[2] {first, second};
 }
示例#51
0
 void StartSearching()
 {
     currentBehavior = AIState.searching;
     guessedNextPlayerLocation = null;
     currentSearchNode = lastKnownPlayerLocation;
     nextSearchNode = null;
     target = lastKnownPlayerLocation.transform;
     decrementSearchTimer = false;
     if (enraged) {
         currentSearchTime = enragedSearchTime;
     }
     else {
         currentSearchTime = searchTime;
     }
 }
示例#52
0
 void Search()
 {
     if (guessedNextPlayerLocation == null) {
         if (player.closestNode != lastKnownPlayerLocation) {
             guessedNextPlayerLocation = player.closestNode;
         }
     }
     if (AtTarget()) {
         decrementSearchTimer = true;
     }
     if (decrementSearchTimer) {
         if (nextSearchNode == null) {
             nextSearchNode = guessedNextPlayerLocation;
         }
         if (HasLineOfSight()) {
             return;
         }
         if (AtTarget()) {
             FindNextSearchNode();
         }
         target = currentSearchNode.transform;
         currentSearchTime -= Time.fixedDeltaTime;
         if (currentSearchTime <= 0f) {
             Calm();
         }
     }
     MoveToTarget();
 }
示例#53
0
 public Edge(MazeNode cell, MazeNode cell2)
     : this(cell, cell2, false) { }
示例#54
0
 void Calm()
 {
     enraged = false;
     currentSpeed = idleSpeed;
     currentBehavior = AIState.idle;
     lastKnownPlayerLocation = null;
     guessedNextPlayerLocation = null;
 }
 void SetExit()
 {
     int x;
     int z;
     MazeNode.Direction d;
     if (Random.value >= .5f) {
         //Use Z Axis
         z = Random.Range(0, nodeHeight - 1);
         if (Random.value >= .5f) {
             //Left
             x = 0;
             d = MazeNode.Direction.left;
         }
         else {
             //Right
             x = nodeWidth - 1;
             d = MazeNode.Direction.right;
         }
     }
     else {
         //Use X Axis
         x = Random.Range(0, nodeWidth - 1);
         if (Random.value >= .5f) {
             //Top
             z = 0;
             d = MazeNode.Direction.up;
         }
         else {
             //Bottom
             z = nodeHeight - 1;
             d = MazeNode.Direction.down;
         }
     }
     exitNode = mazeNodes[x][z];
     exit = exitNode.links[MazeNode.DirectionToIndex(d)];
     startNode = mazeNodes[nodeWidth - 1 - x][nodeHeight - 1 - z];
     playerNode = startNode;
     if (debugColors) {
         exitNode.floorRenderer.material = debugGreen;
         exit.cubeRenderer.material = debugBlack;
         startNode.floorRenderer.material = debugWhite;
     }
 }
 void DetermineDistancesFromGoal(MazeNode startNode, float distance = 0f)
 {
     if (startNode.distanceToGoal > distance) {
         startNode.distanceToGoal = distance;
     }
     //***DEBUG***
     /*
     if (debugColors) {
         startNode.floorRenderer.material.color = new Color(0f, distance / 200f, 0f);
     }
     */
     foreach (MazeNode node in startNode.currentConnections) {
         if (node == null) {
             continue;
         }
         float newDist = distance + GetHeuristic(startNode, node, AStarMode.manhattan);
         if (node.distanceToGoal <= newDist) {
             continue;
         }
         DetermineDistancesFromGoal(node, newDist);
     }
 }
 bool PlaceWall(MazeNode node1, MazeNode node2)
 {
     if (node1.enemyOccupied || node2.enemyOccupied || node1 == playerNode || node2 == playerNode) {
         return false;
     }
     node1.DisconnectFromNode(node2);
     if (AgentSearch(node1, 0, mode: SearchUseMode.checkExitPath)) {
         return true;
     }
     node1.ConnectToNode(node2);
     return false;
 }
示例#58
0
 void FindNextSearchNode()
 {
     MazeNode bestNode = null;
     float furthestDist = 0f;
     foreach (MazeNode node in nextSearchNode.currentConnections) {
         if (node == null) {
             continue;
         }
         if (node == currentSearchNode) {
             continue;
         }
         float dist = MazeController.singleton.GetHeuristic(nextSearchNode, node, MazeController.AStarMode.randomEuclidian, searchRandom);
         if (dist > furthestDist) {
             bestNode = node;
             furthestDist = dist;
         }
     }
     if (bestNode == null) {
         Calm();
         return;
     }
     currentSearchNode = nextSearchNode;
     nextSearchNode = bestNode;
 }
 void CarvePath(MazeNode start, int stopChance, bool connectStragglers = false)
 {
     if (start.connectedToMain && connectStragglers) {
         return;
     }
     List<MazeNode> nodes = new List<MazeNode>(start.connections);
     List<MazeNode> randNodes = new List<MazeNode>();
     while (nodes.Count > 0) {
         int rand = Random.Range(0, nodes.Count - 1);
         randNodes.Add(nodes[rand]);
         nodes.RemoveAt(rand);
     }
     foreach (MazeNode node in randNodes) {
         if (node == null) {
             continue;
         }
         if (node.connectedToMain && !connectStragglers) {
             continue;
         }
         if (Random.Range(0, stopChance) == 0 && !connectStragglers) {
             return;
         }
         node.ConnectToNode(start);
         if (!connectStragglers) {
             node.connectedToMain = true;
             unconnected.Remove(node);
         }
         CarvePath(node, stopChance, connectStragglers);
         if (connectStragglers) {
             start.connectedToMain = true;
             unconnected.Remove(start);
             return;
         }
     }
 }
示例#60
0
 void Chase()
 {
     lastKnownPlayerLocation = player.closestNode;
     target = player.transform;
     MoveToTarget();
 }