private List <(Room, Room)> GetRoomsToConnect() { RoomGraph graph = new RoomGraph(); graph.AddRoomsAndConnectAll(cities); RoomGraph minSpan = graph.MinSpanningTree(random, (r1, r2) => r1.DistanceToSquared(r2)); foreach (Room r in cities) { foreach (Room other in cities) { if (r == other || minSpan.connections[r].Contains(other)) { continue; } double directDist = r.DistanceTo(other); double distInGraph = GetDistanceInGraph(minSpan, r, other); if (directDist * 1.5 < distInGraph) { minSpan.AddConnectionBothWays(r, other); } } } return(minSpan.ToConnectionList()); }
void CreateRoomGraph() { current_map_graph = new RoomGraph(actual_room_count); foreach (Room current_room in current_room_list) { current_map_graph.AddRoom(current_room); } }
private double GetDistanceInGraph(RoomGraph graph, Room from, Room to) { //use Astar. My generic astar implementation is only suitable for 2D arrays at the moment, so reimplement it here... Dictionary <Room, Room> prev = new Dictionary <Room, Room>(graph.Count); Dictionary <Room, double> cost = new Dictionary <Room, double>(graph.Count); bool targetReached = false; foreach (Room r in graph.rooms) { prev.Add(r, null); cost.Add(r, double.MaxValue); } var closedList = new HashSet <Room>(); var openList = new Barely.Util.Priority_Queue.SimplePriorityQueue <Room>(); openList.Enqueue(from, 0); cost[from] = 0; prev[from] = null; while (openList.Count > 0) { Room currentRoom = openList.Dequeue(); if (currentRoom == to) { targetReached = true; break; } closedList.Add(currentRoom); foreach (Room n in graph.connections[currentRoom]) { if (closedList.Contains(n)) { continue; } double tenativeCost = cost[currentRoom] + currentRoom.DistanceTo(n); bool contains = openList.Contains(n); if (contains && tenativeCost >= cost[n]) { continue; } prev[n] = currentRoom; cost[n] = tenativeCost; tenativeCost += n.DistanceTo(to); if (contains) { openList.UpdatePriority(n, tenativeCost); } else { openList.Enqueue(n, tenativeCost); } } } Debug.Assert(cost[to] < double.MaxValue); return(cost[to]); }
List<Weapon> weapons; // a list to hold all of the weapons for the level #endregion Fields #region Constructors // constructor public Level(string mapFile) { // initializes things this.mapFile = mapFile; basicEnemies = new List<Enemy>(); walls = new List<Wall>(); weapons = new List<Weapon>(); coins = new List<Coin>(); doors = new List<Door>(); keys = new List<Key>(); disguises = new List<Disguise>(); floorSwitchers = new List<FloorSwitcher>(); font = ScreenManager.SharedManager.Content.Load<SpriteFont>("Arial"); graphics = ScreenManager.SharedManager.gDevice; spriteBatch = ScreenManager.SharedManager.sBatch; levelMap = new Map(mapFile, new int[11] { 1, 1, 1, 1, 1, int.MaxValue, int.MaxValue, int.MaxValue, int.MaxValue, 0, 0 }); roomGraph = new RoomGraph(); foreach (var groupname in levelMap.ObjectGroups.Keys) // goes through each layer in the map file { int currentFloor = int.Parse(groupname[5].ToString()) - 1; // gets the floor number of the map layer. if (groupname.Substring(6, 8) == "Entities") // the layer contains GameObjects { foreach (var entity in levelMap.ObjectGroups[groupname]) // goes through each entity and creates a GameObject if possible. { if (entity.Type == "Enemy") // adds an enemy to the basicEnemies list. { string sDir = entity.Properties.Find(x => x.Item1 == "startDirection").Item2; int dir = (sDir != null) ? int.Parse(sDir) : 3; basicEnemies.Add(EntityGenerator.GenerateEnemy(new Vector3(entity.X, entity.Y, currentFloor), entity.Properties, dir)); } else if (entity.Type == "Player") // creates the player. { player = EntityGenerator.GeneratePlayer(new Vector3(entity.X, entity.Y, currentFloor), 5, 400); } else if (entity.Type == "Wall") // adds a wall to the walls list. { walls.Add(EntityGenerator.GenerateWall(new Vector3(entity.X, entity.Y, currentFloor), entity.Width, entity.Height)); } else if (entity.Type == "LockedDoor") // adds a door to the doors list. { doors.Add(EntityGenerator.GenerateDoor(new Vector3(entity.X, entity.Y, currentFloor), doors.Count)); } else if (entity.Type == "Key") // adds a key to the keys list. { keys.Add(EntityGenerator.GenerateKey(new Vector3(entity.X, entity.Y, currentFloor), keys.Count)); } else if (entity.Type == "Weapon") // adds a weapon to the weapons list. { weapons.Add(EntityGenerator.GenerateWeapon(new Vector3(entity.X, entity.Y, currentFloor), int.Parse(entity.Properties.Find(x => x.Item1 == "durability").Item2), entity.Properties.Find(x => x.Item1 == "type").Item2)); } else if (entity.Type == "Coin") // adds a coin to the coins list. { coins.Add(EntityGenerator.GenerateCoin(new Vector3(entity.X, entity.Y, currentFloor), int.Parse(entity.Properties.Find(x => x.Item1 == "value").Item2))); } else if (entity.Type == "Disguise") //adds a disguise to the disguises list. { disguises.Add(EntityGenerator.GenerateDisguise(new Vector3(entity.X, entity.Y, currentFloor), entity.Properties.Find(x => x.Item1 == "disguiseType").Item2)); } else if (entity.Type == "FloorSwitcher") // adds a floor switcher to the floorSwitchers list. { floorSwitchers.Add(new FloorSwitcher(new Rectangle(entity.X, entity.Y, entity.Width, entity.Height), currentFloor, currentFloor + 1, bool.Parse(entity.Properties.Find(x => x.Item1 == "Horizontal").Item2))); } } } if (groupname.Contains("Room")) // layer contains rooms { foreach (var entity in levelMap.ObjectGroups[groupname]) // goes through each room object in the layer. { // creates a new RoomGraphNode and sets up it's connections. RoomGraphNode node = new RoomGraphNode(new Rectangle(entity.X, entity.Y, entity.Width, entity.Height), currentFloor, entity.Name); List<string> connections = new List<string>(); foreach (var t in entity.Properties) { if (t.Item1 != null) connections.Add(t.Item1); if (t.Item2 != null) node.validDisguises.Add(t.Item2); } roomGraph.AddNode(node, connections); } } // how much money the player needs to complete the level is 70% of the total money in the level. player.moneyNeeded = (basicEnemies.Count + coins.Count) * 70; } foreach (Door lockedDoor in doors) // if there aren't enough keys, the extra locked doors are unlocked. { if (keys[lockedDoor.keyAssociation] == null) lockedDoor.locked = false; } // sets up what part of the level to show on screen. windowSpace = new Rectangle((int)(player.location.X + (player.rectangle.Width / 2)) - (graphics.Viewport.Width / 2), (int)(player.location.Y + (player.rectangle.Height / 2)) - (graphics.Viewport.Height / 2), graphics.Viewport.Width, graphics.Viewport.Height); }
void Awake() { // Set up the map and the rooms that will be used in the dungeon map = new RoomGraph(); generateDungeon(); }
//메인 방들을 연결한 최소 신장 트리를 구하고 보스방과 플레이어방을 선택. List<RoomEdge> GetMST(List<Room> mainRoomList) { List<RoomVertex> roomVertexList = new List<RoomVertex>(); List<RoomEdge> roomEdgeList = new List<RoomEdge>(); //정점을 만듬 for (int i = 0; i < mainRoomList.Count; ++i) { var vertex = new RoomVertex(mainRoomList[i]); roomVertexList.Add(vertex); } //모든 정점을 간선으로 연결 for (int i = 0; i < roomVertexList.Count - 1; ++i) { for (int j = i + 1; j < roomVertexList.Count; ++j) { RoomVertex vertexA = roomVertexList[i]; RoomVertex vertexB = roomVertexList[j]; float weight = (mainRoomList[i].CachedTransform.position - mainRoomList[j].CachedTransform.position).sqrMagnitude; RoomEdge edge = new RoomEdge(vertexA, vertexB, (int)weight); roomEdgeList.Add(edge); } } //그래프로 만든뒤 MST를 구한다. RoomGraph graph = new RoomGraph(roomVertexList, roomEdgeList); var mst = graph.GetMST(); //플레이어 방과 보스방을고름 SelectPlayerRoomAndBossRoom(mst, roomVertexList); return mst; }