Newer
Older
DungeonShooting / DungeonShooting_Godot / src / game / room / RoomManager.cs
@小李xl 小李xl on 7 Mar 2023 10 KB 备份
  1. using System;
  2. using System.Collections.Generic;
  3. using Godot;
  4.  
  5. /// <summary>
  6. /// 房间管理器
  7. /// </summary>
  8. public partial class RoomManager : Node2D
  9. {
  10. /// <summary>
  11. /// //对象根节点
  12. /// </summary>
  13. [Export] public Node2D NormalLayer;
  14. /// <summary>
  15. /// 对象根节点, 带y轴排序功能
  16. /// </summary>
  17. [Export] public Node2D YSortLayer;
  18. /// <summary>
  19. /// 地图根节点
  20. /// </summary>
  21. [Export] public TileMap TileRoot;
  22.  
  23. /// <summary>
  24. /// 玩家对象
  25. /// </summary>
  26. public Player Player { get; private set; }
  27. private DungeonTile _dungeonTile;
  28. private AutoTileConfig _autoTileConfig;
  29. private Font _font;
  30. private GenerateDungeon _generateDungeon;
  31.  
  32. private int _affiliationIndex = 0;
  33.  
  34. //房间内所有静态导航网格数据
  35. private static List<NavigationPolygonData> _roomStaticNavigationList = new List<NavigationPolygonData>();
  36. public override void _Ready()
  37. {
  38. TileRoot.YSortEnabled = false;
  39. //FloorTileMap.NavigationVisibilityMode = TileMap.VisibilityMode.ForceShow;
  40. _font = ResourceManager.Load<Font>(ResourcePath.resource_font_cn_font_36_tres);
  41.  
  42. var nowTicks = DateTime.Now.Ticks;
  43. //生成地牢房间
  44. _generateDungeon = new GenerateDungeon();
  45. _generateDungeon.Generate();
  46. //填充地牢
  47. _autoTileConfig = new AutoTileConfig();
  48. _dungeonTile = new DungeonTile(TileRoot);
  49. _dungeonTile.AutoFillRoomTile(_autoTileConfig, _generateDungeon.StartRoom);
  50. //生成寻路网格, 这一步操作只生成过道的导航
  51. _dungeonTile.GenerateNavigationPolygon(DungeonTile.AisleFloorMapLayer);
  52. //挂载过道导航区域
  53. _dungeonTile.MountNavigationPolygon(this);
  54. //过道导航区域数据
  55. var aisleData = _dungeonTile.GetPolygonData();
  56. _roomStaticNavigationList.AddRange(aisleData);
  57. //门导航区域数据
  58. _roomStaticNavigationList.AddRange(_dungeonTile.GetConnectDoorPolygonData());
  59. //创建过道的归属区域
  60. CreateAisleAffiliation(aisleData);
  61. //初始化所有房间
  62. _generateDungeon.EachRoom(InitRoom);
  63.  
  64. GD.Print("生成地牢用时: " + (DateTime.Now.Ticks - nowTicks) / 10000 + "毫秒");
  65.  
  66. //播放bgm
  67. SoundManager.PlayMusic(ResourcePath.resource_sound_bgm_Intro_ogg, -17f);
  68.  
  69. //创建玩家
  70. Player = ActivityObject.Create<Player>(ActivityIdPrefix.Role + "0001");
  71. Player.Position = new Vector2(30, 30);
  72. Player.Name = "Player";
  73. Player.PutDown(RoomLayerEnum.YSortLayer);
  74. Player.PickUpWeapon(ActivityObject.Create<Weapon>(ActivityIdPrefix.Weapon + "0001"));
  75. Player.PickUpWeapon(ActivityObject.Create<Weapon>(ActivityIdPrefix.Weapon + "0002"));
  76. // Player.PickUpWeapon(ActivityObject.Create<Weapon>(ActivityIdPrefix.Weapon + "0004"));
  77. Player.PickUpWeapon(ActivityObject.Create<Weapon>(ActivityIdPrefix.Weapon + "0003"));
  78.  
  79. ActivityObject.Create<Gun>(ActivityIdPrefix.Weapon + "0001").PutDown(new Vector2(35, 35), RoomLayerEnum.YSortLayer);
  80. //相机跟随玩家
  81. GameCamera.Main.SetFollowTarget(Player);
  82. //修改鼠标指针
  83. var cursor = GameApplication.Instance.Cursor;
  84. cursor.SetGuiMode(false);
  85. cursor.SetMountRole(Player);
  86. }
  87.  
  88. /// <summary>
  89. /// 获取指定层级根节点
  90. /// </summary>
  91. /// <param name="layerEnum"></param>
  92. /// <returns></returns>
  93. public Node2D GetRoomLayer(RoomLayerEnum layerEnum)
  94. {
  95. switch (layerEnum)
  96. {
  97. case RoomLayerEnum.NormalLayer:
  98. return NormalLayer;
  99. case RoomLayerEnum.YSortLayer:
  100. return YSortLayer;
  101. }
  102.  
  103. return null;
  104. }
  105.  
  106. public override void _Process(double delta)
  107. {
  108. Enemy.UpdateEnemiesView();
  109. if (GameApplication.Instance.Debug)
  110. {
  111. QueueRedraw();
  112. }
  113. }
  114.  
  115. public override void _Draw()
  116. {
  117. if (GameApplication.Instance.Debug)
  118. {
  119. if (_dungeonTile != null)
  120. {
  121. // DrawLine(new Vector2(0, -5000), new Vector2(0, 5000), Colors.Green);
  122. // DrawLine(new Vector2(-5000, 0), new Vector2(5000, 0), Colors.Green);
  123. //绘制ai寻路区域
  124. Utils.DrawNavigationPolygon(this, _roomStaticNavigationList.ToArray());
  125. }
  126. //绘制房间区域
  127. //DrawRoomInfo(_generateDungeon.StartRoom);
  128. }
  129. }
  130.  
  131. // 初始化房间
  132. private void InitRoom(RoomInfo roomInfo)
  133. {
  134. //挂载房间导航区域
  135. MountNavFromRoomInfo(roomInfo);
  136. //创建门
  137. CreateDoor(roomInfo);
  138. //创建房间归属区域
  139. CreateRoomAisleAffiliation(roomInfo);
  140. //创建敌人
  141. foreach (var roomInfoActivityMark in roomInfo.ActivityMarks)
  142. {
  143. //roomInfoActivityMark.BeReady(roomInfo);
  144. }
  145. }
  146. //挂载房间导航区域
  147. private void MountNavFromRoomInfo(RoomInfo roomInfo)
  148. {
  149. var polygonArray = roomInfo.RoomSplit.RoomInfo.NavigationList.ToArray();
  150. var polygon = new NavigationPolygon();
  151. var offset = roomInfo.GetOffsetPosition();
  152. for (var i = 0; i < polygonArray.Length; i++)
  153. {
  154. var navigationPolygonData = polygonArray[i];
  155. var polygonPointArray = navigationPolygonData.ConvertPointsToVector2Array();
  156. //这里的位置需要加上房间位置
  157. for (var j = 0; j < polygonPointArray.Length; j++)
  158. {
  159. polygonPointArray[j] = polygonPointArray[j] + roomInfo.GetWorldPosition() - offset;
  160. }
  161. polygon.AddOutline(polygonPointArray);
  162. var points = new List<SerializeVector2>();
  163. for (var j = 0; j < polygonPointArray.Length; j++)
  164. {
  165. points.Add(new SerializeVector2(polygonPointArray[j]));
  166. }
  167. //存入汇总列表
  168. _roomStaticNavigationList.Add(new NavigationPolygonData(navigationPolygonData.Type, points));
  169. }
  170. polygon.MakePolygonsFromOutlines();
  171. var navigationPolygon = new NavigationRegion2D();
  172. navigationPolygon.Name = "NavigationRegion" + (GetChildCount() + 1);
  173. navigationPolygon.NavigationPolygon = polygon;
  174. AddChild(navigationPolygon);
  175. }
  176.  
  177. //创建门
  178. private void CreateDoor(RoomInfo roomInfo)
  179. {
  180. foreach (var doorInfo in roomInfo.Doors)
  181. {
  182. var door = ActivityObject.Create<RoomDoor>(ActivityIdPrefix.Other + "0001");
  183. doorInfo.Door = door;
  184. Vector2 offset;
  185. switch (doorInfo.Direction)
  186. {
  187. case DoorDirection.E:
  188. offset = new Vector2(-0.5f, 2);
  189. break;
  190. case DoorDirection.W:
  191. offset = new Vector2(0.5f, 2);
  192. break;
  193. case DoorDirection.S:
  194. offset = new Vector2(2f, -0.5f);
  195. break;
  196. case DoorDirection.N:
  197. offset = new Vector2(2f, 0.5f);
  198. break;
  199. default: offset = new Vector2();
  200. break;
  201. }
  202. door.Position = (doorInfo.OriginPosition + offset) * GenerateDungeon.TileCellSize;
  203. door.Init(doorInfo);
  204. door.OpenDoor();
  205. door.PutDown(RoomLayerEnum.NormalLayer, false);
  206. }
  207. }
  208.  
  209. //创建房间归属区域
  210. private void CreateRoomAisleAffiliation(RoomInfo roomInfo)
  211. {
  212. var affiliation = new AffiliationArea();
  213. affiliation.Name = "AffiliationArea" + (_affiliationIndex++);
  214. affiliation.Init(new Rect2(roomInfo.GetWorldPosition(), roomInfo.Size * GenerateDungeon.TileCellSize));
  215. roomInfo.Affiliation = affiliation;
  216. TileRoot.AddChild(affiliation);
  217. }
  218. //创建过道归属区域
  219. private void CreateAisleAffiliation(NavigationPolygonData[] aisleData)
  220. {
  221. foreach (var aisle in aisleData)
  222. {
  223. var affiliation = new AffiliationArea();
  224. affiliation.Name = "AffiliationArea" + (_affiliationIndex++);
  225. affiliation.Init(aisle.ConvertPointsToVector2Array());
  226. TileRoot.AddChild(affiliation);
  227. }
  228. }
  229. //绘制房间区域, debug 用
  230. private void DrawRoomInfo(RoomInfo room)
  231. {
  232. var cellSize = TileRoot.CellQuadrantSize;
  233. var pos1 = (room.Position + room.Size / 2) * cellSize;
  234. //绘制下一个房间
  235. foreach (var nextRoom in room.Next)
  236. {
  237. var pos2 = (nextRoom.Position + nextRoom.Size / 2) * cellSize;
  238. DrawLine(pos1, pos2, Colors.Red);
  239. DrawRoomInfo(nextRoom);
  240. }
  241.  
  242. DrawString(_font, pos1, room.Id.ToString());
  243.  
  244. //绘制门
  245. foreach (var roomDoor in room.Doors)
  246. {
  247. var originPos = roomDoor.OriginPosition * cellSize;
  248. switch (roomDoor.Direction)
  249. {
  250. case DoorDirection.E:
  251. DrawLine(originPos, originPos + new Vector2(3, 0) * cellSize, Colors.Yellow);
  252. DrawLine(originPos + new Vector2(0, 4) * cellSize, originPos + new Vector2(3, 4) * cellSize,
  253. Colors.Yellow);
  254. break;
  255. case DoorDirection.W:
  256. DrawLine(originPos, originPos - new Vector2(3, 0) * cellSize, Colors.Yellow);
  257. DrawLine(originPos + new Vector2(0, 4) * cellSize, originPos - new Vector2(3, -4) * cellSize,
  258. Colors.Yellow);
  259. break;
  260. case DoorDirection.S:
  261. DrawLine(originPos, originPos + new Vector2(0, 3) * cellSize, Colors.Yellow);
  262. DrawLine(originPos + new Vector2(4, 0) * cellSize, originPos + new Vector2(4, 3) * cellSize,
  263. Colors.Yellow);
  264. break;
  265. case DoorDirection.N:
  266. DrawLine(originPos, originPos - new Vector2(0, 3) * cellSize, Colors.Yellow);
  267. DrawLine(originPos + new Vector2(4, 0) * cellSize, originPos - new Vector2(-4, 3) * cellSize,
  268. Colors.Yellow);
  269. break;
  270. }
  271. //绘制房间区域
  272. DrawRect(new Rect2(room.Position * cellSize, room.Size * cellSize), Colors.Blue, false);
  273.  
  274. if (roomDoor.HasCross && roomDoor.RoomInfo.Id < roomDoor.ConnectRoom.Id)
  275. {
  276. DrawRect(new Rect2(roomDoor.Cross * cellSize, new Vector2(cellSize * 4, cellSize * 4)), Colors.Yellow, false);
  277. }
  278. }
  279. }
  280. }