diff --git a/DungeonShooting_Godot/resource/map/tileMaps/Test1/inlet/Start/Preinstall.json b/DungeonShooting_Godot/resource/map/tileMaps/Test1/inlet/Start/Preinstall.json index 279b625..c43c818 100644 --- a/DungeonShooting_Godot/resource/map/tileMaps/Test1/inlet/Start/Preinstall.json +++ b/DungeonShooting_Godot/resource/map/tileMaps/Test1/inlet/Start/Preinstall.json @@ -1 +1 @@ -[{"Name":"Preinstall1","Weight":100,"Remark":"","AutoFill":true,"WaveList":[[{"Position":{"X":39,"Y":8},"Size":{"X":0,"Y":0},"SpecialMarkType":1,"DelayTime":0,"MarkList":[]},{"Position":{"X":-16,"Y":-18},"Size":{"X":16,"Y":16},"SpecialMarkType":0,"DelayTime":0,"MarkList":[{"Id":"weapon0001","Weight":100,"Attr":{"CurrAmmon":"30","ResidueAmmo":"210"},"Altitude":8,"VerticalSpeed":0}]},{"Position":{"X":52,"Y":65},"Size":{"X":16,"Y":16},"SpecialMarkType":0,"DelayTime":0,"MarkList":[{"Id":"$RandomProp","Weight":100,"Attr":null,"Altitude":16,"VerticalSpeed":0}]}],[{"Position":{"X":59,"Y":-5},"Size":{"X":16,"Y":16},"SpecialMarkType":0,"DelayTime":1,"MarkList":[{"Id":"$RandomGun","Weight":100,"Attr":null,"Altitude":16,"VerticalSpeed":0}]},{"Position":{"X":11,"Y":-46},"Size":{"X":16,"Y":16},"SpecialMarkType":0,"DelayTime":0,"MarkList":[{"Id":"$RandomProp","Weight":100,"Attr":null,"Altitude":8,"VerticalSpeed":0}]}]]}] \ No newline at end of file +[{"Name":"Preinstall1","Weight":100,"Remark":"","AutoFill":true,"WaveList":[[{"Position":{"X":39,"Y":8},"Size":{"X":0,"Y":0},"SpecialMarkType":1,"DelayTime":0,"MarkList":[]},{"Position":{"X":-16,"Y":-18},"Size":{"X":16,"Y":16},"SpecialMarkType":0,"DelayTime":0,"MarkList":[{"Id":"weapon0001","Weight":100,"Attr":{"CurrAmmon":"30","ResidueAmmo":"210"},"Altitude":8,"VerticalSpeed":0}]},{"Position":{"X":52,"Y":65},"Size":{"X":16,"Y":16},"SpecialMarkType":0,"DelayTime":0,"MarkList":[{"Id":"$RandomProp","Weight":100,"Attr":null,"Altitude":16,"VerticalSpeed":0}]}],[{"Position":{"X":59,"Y":-5},"Size":{"X":16,"Y":16},"SpecialMarkType":0,"DelayTime":1,"MarkList":[{"Id":"$RandomGun","Weight":100,"Attr":null,"Altitude":16,"VerticalSpeed":0}]},{"Position":{"X":11,"Y":-46},"Size":{"X":16,"Y":16},"SpecialMarkType":0,"DelayTime":0,"MarkList":[{"Id":"$RandomProp","Weight":100,"Attr":null,"Altitude":8,"VerticalSpeed":0}]},{"Position":{"X":72,"Y":-39},"Size":{"X":16,"Y":16},"SpecialMarkType":0,"DelayTime":2,"MarkList":[{"Id":"$RandomEnemy","Weight":100,"Attr":null,"Altitude":0,"VerticalSpeed":0}]}]]}] \ No newline at end of file diff --git a/DungeonShooting_Godot/src/framework/map/DungeonTileMap.cs b/DungeonShooting_Godot/src/framework/map/DungeonTileMap.cs index 1aef2f9..0caf026 100644 --- a/DungeonShooting_Godot/src/framework/map/DungeonTileMap.cs +++ b/DungeonShooting_Godot/src/framework/map/DungeonTileMap.cs @@ -38,17 +38,17 @@ /// /// 根据 startRoom 和 config 数据自动填充 tileMap 参数中的地图数据, 该函数为协程函数 /// - public IEnumerator AutoFillRoomTile(AutoTileConfig config, RoomInfo startRoomInfo, SeedRandom random) + public IEnumerator AutoFillRoomTile(AutoTileConfig config, RoomInfo startRoomInfo, World world) { _connectNavigationItemList.Clear(); - yield return _AutoFillRoomTile(config, startRoomInfo, random); + yield return _AutoFillRoomTile(config, startRoomInfo, world); } - private IEnumerator _AutoFillRoomTile(AutoTileConfig config, RoomInfo roomInfo, SeedRandom random) + private IEnumerator _AutoFillRoomTile(AutoTileConfig config, RoomInfo roomInfo, World world) { foreach (var info in roomInfo.Next) { - yield return _AutoFillRoomTile(config, info, random); + yield return _AutoFillRoomTile(config, info, world); } //铺房间 @@ -155,7 +155,7 @@ else { var weights = roomInfo.RoomSplit.Preinstall.Select(info => info.Weight).ToArray(); - var index = random.RandomWeight(weights); + var index = world.Random.RandomWeight(weights); preinstallInfo = roomInfo.RoomSplit.Preinstall[index]; } } @@ -163,7 +163,7 @@ var roomPreinstall = new RoomPreinstall(roomInfo, preinstallInfo); roomInfo.RoomPreinstall = roomPreinstall; //执行预处理操作 - roomPreinstall.Pretreatment(random); + roomPreinstall.Pretreatment(world); } // yield break; diff --git a/DungeonShooting_Godot/src/framework/map/RandomPool.cs b/DungeonShooting_Godot/src/framework/map/RandomPool.cs new file mode 100644 index 0000000..a55040a --- /dev/null +++ b/DungeonShooting_Godot/src/framework/map/RandomPool.cs @@ -0,0 +1,45 @@ + +using Config; + +public class RandomPool +{ + /// + /// 随机数生成器 + /// + public SeedRandom Random { get; } + + /// + /// 所属世界 + /// + public World World { get; } + + public RandomPool(World world) + { + World = world; + Random = world.Random; + } + + /// + /// 获取随机武器 + /// + public ExcelConfig.ActivityBase GetRandomWeapon() + { + return Random.RandomChoose(PreinstallMarkManager.GetMarkConfigsByType(ActivityType.Weapon)); + } + + /// + /// 获取随机敌人 + /// + public ExcelConfig.ActivityBase GetRandomEnemy() + { + return Random.RandomChoose(PreinstallMarkManager.GetMarkConfigsByType(ActivityType.Enemy)); + } + + /// + /// 获取随机道具 + /// + public ExcelConfig.ActivityBase GetRandomProp() + { + return Random.RandomChoose(PreinstallMarkManager.GetMarkConfigsByType(ActivityType.Prop)); + } +} \ No newline at end of file diff --git a/DungeonShooting_Godot/src/framework/map/preinstall/ActivityMark.cs b/DungeonShooting_Godot/src/framework/map/preinstall/ActivityMark.cs index 0d266af..b1e974b 100644 --- a/DungeonShooting_Godot/src/framework/map/preinstall/ActivityMark.cs +++ b/DungeonShooting_Godot/src/framework/map/preinstall/ActivityMark.cs @@ -10,7 +10,7 @@ public string Id { get; set; } /// - /// 刷新位置 + /// 刷新位置, 单位: 像素 /// public Vector2 Position { get; set; } diff --git a/DungeonShooting_Godot/src/framework/map/preinstall/RoomPreinstall.cs b/DungeonShooting_Godot/src/framework/map/preinstall/RoomPreinstall.cs index 6be9480..0cfc64b 100644 --- a/DungeonShooting_Godot/src/framework/map/preinstall/RoomPreinstall.cs +++ b/DungeonShooting_Godot/src/framework/map/preinstall/RoomPreinstall.cs @@ -80,7 +80,7 @@ /// /// 预处理操作 /// - public void Pretreatment(SeedRandom random) + public void Pretreatment(World world) { if (_runPretreatment) { @@ -111,60 +111,60 @@ else { var tempArray = markInfo.MarkList.Select(item => item.Weight).ToArray(); - var index = random.RandomWeight(tempArray); + var index = world.Random.RandomWeight(tempArray); markInfoItem = markInfo.MarkList[index]; } var activityBase = PreinstallMarkManager.GetMarkConfig(markInfoItem.Id); - mark.ActivityType = (ActivityType)activityBase.Type; mark.Attr = markInfoItem.Attr; mark.VerticalSpeed = markInfoItem.VerticalSpeed; mark.Altitude = markInfoItem.Altitude; - - - if (mark.ActivityType == ActivityType.Other) //其他类型 + if (activityBase is RandomActivityBase) //随机物体 { - //判断是否是随机标记 if (markInfoItem.Id == PreinstallMarkManager.Weapon.Id) //随机武器 { - mark.Id = Utils.Random.RandomChoose(PreinstallMarkManager.GetMarkConfigsByType(ActivityType.Weapon))?.Id; + mark.Id = world.RandomPool.GetRandomWeapon()?.Id; + mark.ActivityType = ActivityType.Weapon; } else if (markInfoItem.Id == PreinstallMarkManager.Enemy.Id) //随机敌人 { - mark.Id = Utils.Random.RandomChoose(PreinstallMarkManager.GetMarkConfigsByType(ActivityType.Enemy))?.Id; + mark.Id = world.RandomPool.GetRandomEnemy()?.Id; + mark.ActivityType = ActivityType.Enemy; } else if (markInfoItem.Id == PreinstallMarkManager.Prop.Id) //随机道具 { - mark.Id = Utils.Random.RandomChoose(PreinstallMarkManager.GetMarkConfigsByType(ActivityType.Prop))?.Id; + mark.Id = world.RandomPool.GetRandomProp()?.Id; + mark.ActivityType = ActivityType.Prop; } else //非随机物体 { - mark.Id = markInfoItem.Id; - } - } - else if (mark.ActivityType == ActivityType.Enemy) //敌人类型 - { - _hsaEnemy = true; - mark.Id = markInfoItem.Id; - mark.DerivedAttr = new Dictionary(); - if (!mark.Attr.TryGetValue("Face", out var face) || face == "0") //随机方向 - { - mark.DerivedAttr.Add("Face", - random.RandomChoose( - ((int)FaceDirection.Left).ToString(), - ((int)FaceDirection.Right).ToString() - ) - ); - } - else //指定方向 - { - mark.DerivedAttr.Add("Face", face); + Debug.LogError("未知的随机物体:" + markInfoItem.Id); + continue; } } else { mark.Id = markInfoItem.Id; + mark.ActivityType = (ActivityType)activityBase.Type; + if (mark.ActivityType == ActivityType.Enemy) //敌人类型 + { + _hsaEnemy = true; + mark.DerivedAttr = new Dictionary(); + if (!mark.Attr.TryGetValue("Face", out var face) || face == "0") //随机方向 + { + mark.DerivedAttr.Add("Face", + world.Random.RandomChoose( + ((int)FaceDirection.Left).ToString(), + ((int)FaceDirection.Right).ToString() + ) + ); + } + else //指定方向 + { + mark.DerivedAttr.Add("Face", face); + } + } } } else if (markInfo.SpecialMarkType == SpecialMarkType.BirthPoint) //玩家出生标记 @@ -183,16 +183,35 @@ var pos = markInfo.Position.AsVector2(); var birthRect = markInfo.Size.AsVector2(); var tempPos = new Vector2( - random.RandomRangeInt((int)(pos.X - birthRect.X / 2), (int)(pos.X + birthRect.X / 2)), - random.RandomRangeInt((int)(pos.Y - birthRect.Y / 2), (int)(pos.Y + birthRect.Y / 2)) + world.Random.RandomRangeInt((int)(pos.X - birthRect.X / 2), (int)(pos.X + birthRect.X / 2)), + world.Random.RandomRangeInt((int)(pos.Y - birthRect.Y / 2), (int)(pos.Y + birthRect.Y / 2)) ); //var offset = RoomInfo.RoomSplit.RoomInfo.Position.AsVector2I(); //mark.Position = RoomInfo.GetWorldPosition() + tempPos - offset; mark.Position = RoomInfo.ToGlobalPosition(tempPos); wave.Add(mark); } - - //排序操作 + } + + //自动填充操作 + if (RoomPreinstallInfo.AutoFill) + { + var tempWave = GetOrCreateWave(0); + var mark = new ActivityMark(); + mark.Id = world.RandomPool.GetRandomWeapon().Id; + mark.MarkType = SpecialMarkType.Normal; + mark.ActivityType = ActivityType.Weapon; + mark.Attr = null; + mark.VerticalSpeed = 0; + mark.Altitude = 8; + mark.DelayTime = 0; + mark.Position = new Vector2(64, 64); + tempWave.Add(mark); + } + + //排序操作 + foreach (var wave in WaveList) + { wave.Sort((a, b) => (int)(a.DelayTime * 1000 - b.DelayTime * 1000)); } } @@ -450,6 +469,10 @@ //初始化物体属性 private void InitAttr(ActivityObject activityObject, ActivityMark activityMark) { + if (activityMark.Attr == null) + { + return; + } if (activityMark.ActivityType == ActivityType.Weapon) //武器类型 { var weapon = (Weapon)activityObject; @@ -489,4 +512,14 @@ } } } + + private List GetOrCreateWave(int waveIndex) + { + while (WaveList.Count <= waveIndex) + { + WaveList.Add(new List()); + } + + return WaveList[waveIndex]; + } } \ No newline at end of file diff --git a/DungeonShooting_Godot/src/game/GameApplication.cs b/DungeonShooting_Godot/src/game/GameApplication.cs index 142cc7d..2195385 100644 --- a/DungeonShooting_Godot/src/game/GameApplication.cs +++ b/DungeonShooting_Godot/src/game/GameApplication.cs @@ -160,7 +160,7 @@ /// /// 创建新的 World 对象, 相当于清理房间 /// - public World CreateNewWorld() + public World CreateNewWorld(SeedRandom random) { if (World != null) { @@ -169,6 +169,7 @@ } World = ResourceManager.LoadAndInstantiate(ResourcePath.scene_World_tscn); World.InitLayer(); + World.InitRandomPool(random); SceneRoot.AddChild(World); return World; } diff --git a/DungeonShooting_Godot/src/game/room/DungeonManager.cs b/DungeonShooting_Godot/src/game/room/DungeonManager.cs index b16c876..16f626f 100644 --- a/DungeonShooting_Godot/src/game/room/DungeonManager.cs +++ b/DungeonShooting_Godot/src/game/room/DungeonManager.cs @@ -49,7 +49,7 @@ /// 自动图块配置 /// public AutoTileConfig AutoTileConfig { get; private set; } - + private UiBase _prevUi; private DungeonTileMap _dungeonTileMap; private DungeonGenerator _dungeonGenerator; @@ -223,7 +223,7 @@ } yield return 0; //创建世界场景 - World = GameApplication.Instance.CreateNewWorld(); + World = GameApplication.Instance.CreateNewWorld(random); yield return 0; var group = GameApplication.Instance.RoomConfig[CurrConfig.GroupName]; var tileSetSplit = GameApplication.Instance.TileSetConfig[group.TileSet]; @@ -231,7 +231,7 @@ //填充地牢 AutoTileConfig = new AutoTileConfig(0, tileSetSplit.TileSetInfo.Sources[0].Terrain[0]); _dungeonTileMap = new DungeonTileMap(World.TileRoot); - yield return _dungeonTileMap.AutoFillRoomTile(AutoTileConfig, _dungeonGenerator.StartRoomInfo, random); + yield return _dungeonTileMap.AutoFillRoomTile(AutoTileConfig, _dungeonGenerator.StartRoomInfo, World); //yield return _dungeonTileMap.AddOutlineTile(AutoTileConfig.WALL_BLOCK); //生成寻路网格, 这一步操作只生成过道的导航 diff --git a/DungeonShooting_Godot/src/game/room/World.cs b/DungeonShooting_Godot/src/game/room/World.cs index 73ab5ec..94faa5a 100644 --- a/DungeonShooting_Godot/src/game/room/World.cs +++ b/DungeonShooting_Godot/src/game/room/World.cs @@ -66,6 +66,16 @@ /// public List Enemy_InstanceList { get; } = new List(); + /// + /// 随机数对象 + /// + public SeedRandom Random { get; private set; } + + /// + /// 随机对象池 + /// + public RandomPool RandomPool { get; private set; } + private bool _pause = false; private List _coroutineList; @@ -181,4 +191,13 @@ { ProxyCoroutineHandler.ProxyStopAllCoroutine(ref _coroutineList); } + + /// + /// 初始化随机池 + /// + public void InitRandomPool(SeedRandom random) + { + Random = random; + RandomPool = new RandomPool(this); + } } \ No newline at end of file diff --git a/DungeonShooting_Godot/src/game/ui/mapEditorSelectObject/MapEditorSelectObjectPanel.cs b/DungeonShooting_Godot/src/game/ui/mapEditorSelectObject/MapEditorSelectObjectPanel.cs index 8976ca7..79b68f0 100644 --- a/DungeonShooting_Godot/src/game/ui/mapEditorSelectObject/MapEditorSelectObjectPanel.cs +++ b/DungeonShooting_Godot/src/game/ui/mapEditorSelectObject/MapEditorSelectObjectPanel.cs @@ -1,3 +1,4 @@ + using System; using System.Collections.Generic; using System.Linq;