diff --git a/DungeonShooting_Godot/project.godot b/DungeonShooting_Godot/project.godot index c5ef034..90120ee 100644 --- a/DungeonShooting_Godot/project.godot +++ b/DungeonShooting_Godot/project.godot @@ -11,7 +11,7 @@ [application] config/name="DungeonShooting" -run/main_scene="res://scene/Main.tscn" +run/main_scene="res://scene/test/TestGenerateDungeon.tscn" config/icon="res://icon.png" [autoload] diff --git a/DungeonShooting_Godot/scene/test/TestGenerateDungeon.tscn b/DungeonShooting_Godot/scene/test/TestGenerateDungeon.tscn new file mode 100644 index 0000000..0e29338 --- /dev/null +++ b/DungeonShooting_Godot/scene/test/TestGenerateDungeon.tscn @@ -0,0 +1,33 @@ +[gd_scene load_steps=4 format=2] + +[ext_resource path="res://src/test/TestGenerateDungeon.cs" type="Script" id=1] +[ext_resource path="res://resource/sprite/environment/itch-io-DungeonTileset4/16x16 dungeon ii wall reconfig v04 spritesheet.png" type="Texture" id=2] + +[sub_resource type="TileSet" id=1] +0/name = "16x16 dungeon ii wall reconfig v04 spritesheet.png 0" +0/texture = ExtResource( 2 ) +0/tex_offset = Vector2( 0, 0 ) +0/modulate = Color( 1, 1, 1, 1 ) +0/region = Rect2( 0, 128, 16, 16 ) +0/tile_mode = 0 +0/occluder_offset = Vector2( 0, 0 ) +0/navigation_offset = Vector2( 0, 0 ) +0/shape_offset = Vector2( 0, 0 ) +0/shape_transform = Transform2D( 1, 0, 0, 1, 0, 0 ) +0/shape_one_way = false +0/shape_one_way_margin = 0.0 +0/shapes = [ ] +0/z_index = 0 + +[node name="TestGenerateDungeon" type="Node2D"] +script = ExtResource( 1 ) +TileMapPath = NodePath("TileMap") +Camera = NodePath("Camera2D") + +[node name="Camera2D" type="Camera2D" parent="."] +current = true + +[node name="TileMap" type="TileMap" parent="."] +tile_set = SubResource( 1 ) +cell_size = Vector2( 16, 16 ) +format = 1 diff --git a/DungeonShooting_Godot/src/framework/Component.cs b/DungeonShooting_Godot/src/framework/Component.cs index c07223d..abe716f 100644 --- a/DungeonShooting_Godot/src/framework/Component.cs +++ b/DungeonShooting_Godot/src/framework/Component.cs @@ -178,7 +178,7 @@ } /// - /// 当该组件挂载到GameObject上时调用 + /// 当该组件挂载到 ActivityObject 上时调用 /// public virtual void OnMount() { diff --git a/DungeonShooting_Godot/src/framework/Grid.cs b/DungeonShooting_Godot/src/framework/Grid.cs index 8aa0229..782da26 100644 --- a/DungeonShooting_Godot/src/framework/Grid.cs +++ b/DungeonShooting_Godot/src/framework/Grid.cs @@ -1,8 +1,50 @@  +using System.Collections.Generic; +using System.Linq; +using Godot; + /// /// 网格数据结构 /// -public class Grid +public class Grid { + private Dictionary> _map = new Dictionary>(); + + public bool Contains(int x, int y) + { + return false; + } + public void Set(int x, int y, T data) + { + if (_map.TryGetValue(x, out var value)) + { + value[y] = data; + } + else + { + value = new Dictionary(); + value.Add(y, data); + _map.Add(x, value); + } + } + + public T Get(int x, int y) + { + if (_map.TryGetValue(x, out var value)) + { + return value[y]; + } + return default; + } + + public void AddRect(Vector2 pos, Vector2 size) + { + + } + + public bool TestRect() + { + return true; + } } diff --git a/DungeonShooting_Godot/src/framework/MoveController.cs b/DungeonShooting_Godot/src/framework/MoveController.cs deleted file mode 100644 index 184116c..0000000 --- a/DungeonShooting_Godot/src/framework/MoveController.cs +++ /dev/null @@ -1,225 +0,0 @@ - -using System.Collections.Generic; -using Godot; - -/// -/// 移动控制器, 物体运动由力来控制, 不同方向的力速度最终会汇总 -/// -public class MoveController : Component -{ - private static long _index = 0; - - /// - /// 玩家受到的外力的集合 - /// - private readonly List _forceList = new List(); - - /// - /// 这个速度就是玩家当前物理帧移动的真实速率, 该速度由物理帧循环更新, 并不会马上更新 - /// 该速度就是 BasisVelocity + 外力总和 - /// - public Vector2 Velocity => _velocity; - - private Vector2 _velocity = Vector2.Zero; - - - /// - /// 玩家的基础移动速率 - /// - public Vector2 BasisVelocity - { - get => _basisVelocity; - set => _basisVelocity = value; - } - - private Vector2 _basisVelocity = Vector2.Zero; - - /// - /// 获取所有外力对象 - /// - public ExternalForce[] GetAllForce() - { - return _forceList.ToArray(); - } - - /// - /// 快速窗口一个外力, 该外力为匿名外力, 当速率变为 0 时自动销毁 - /// - /// 外力速率 - /// 阻力大小 - public ExternalForce AddForce(Vector2 velocity, float resistance) - { - var force = AddForce("_anonymity_" + _index++); - force.Velocity = velocity; - force.Resistance = resistance; - return force; - } - - /// - /// 根据名称添加一个外力, 并返回创建的外力的对象, 如果存在这个名称的外力, 移除之前的外力 - /// - public ExternalForce AddForce(string name) - { - var f = new ExternalForce(name); - AddForce(f); - return f; - } - - /// - /// 根据对象添加一个外力力, 如果存在这个名称的外力, 移除之前的外力 - /// - public T AddForce(T force) where T : ExternalForce - { - RemoveForce(force.Name); - _forceList.Add(force); - return force; - } - - /// - /// 根据名称移除一个外力 - /// - public void RemoveForce(string name) - { - for (var i = 0; i < _forceList.Count; i++) - { - if (_forceList[i].Name == name) - { - _forceList.RemoveAt(i); - return; - } - } - } - - /// - /// 根据名称获取一个外力 - /// - public ExternalForce GetForce(string name) - { - for (var i = 0; i < _forceList.Count; i++) - { - var externalForce = _forceList[i]; - if (externalForce.Name == name) - { - return externalForce; - } - } - - return null; - } - - /// - /// 检车是否有当前名称的外力对象 - /// - public bool ContainsForce(string name) - { - for (var i = 0; i < _forceList.Count; i++) - { - var externalForce = _forceList[i]; - if (externalForce.Name == name) - { - return true; - } - } - - return false; - } - - /// - /// 根据对象移除一个外力 - /// - public void RemoveForce(ExternalForce force) - { - RemoveForce(force.Name); - } - - /// - /// 移除所有外力 - /// - public void ClearForce() - { - _forceList.Clear(); - } - - public override void PhysicsProcess(float delta) - { - if (_basisVelocity == Vector2.Zero && _forceList.Count == 0) - { - return; - } - - //先调用更新 - var externalForces = _forceList.ToArray(); - foreach (var fore in externalForces) - { - if (fore.Enable) - fore.PhysicsProcess(delta); - } - - //外力总和 - var finallyEf = new Vector2(); - foreach (var fore in externalForces) - { - if (fore.Enable) - finallyEf += fore.Velocity; - } - - //最终速率 - var finallyVelocity = _basisVelocity + finallyEf; - - if (finallyVelocity != Vector2.Zero) - { - //计算移动 - _velocity = ActivityObject.MoveAndSlide(finallyVelocity); - if (_velocity.x == 0f && _basisVelocity.x * finallyVelocity.x > 0) - { - _basisVelocity.x = 0; - } - - if (_velocity.y == 0f && _basisVelocity.y * finallyVelocity.y > 0) - { - _basisVelocity.y = 0; - } - - //调整外力速率 - if (externalForces.Length > 0) - { - for (var i = 0; i < _forceList.Count; i++) - { - var force = _forceList[i]; - if (force.Enable) - { - var velocity = force.Velocity; - force.Velocity = new Vector2( - _velocity.x == 0f && velocity.x * finallyVelocity.x > 0 ? 0 : velocity.x, - _velocity.y == 0f && velocity.y * finallyVelocity.y > 0 ? 0 : velocity.y - ); - - if (force.Resistance != 0) - { - force.Velocity = force.Velocity.MoveToward(Vector2.Zero, force.Resistance * delta); - } - - if (force.AutoDestroy && force.Velocity == Vector2.Zero) - { - _forceList.RemoveAt(i--); - } - } - } - } - } - else - { - _velocity = finallyEf; - } - } - - public override void DebugDraw() - { - var globalRotation = GlobalRotation; - ActivityObject.DrawLine(Vector2.Zero, BasisVelocity.Rotated(-globalRotation), Colors.Yellow); - foreach (var force in _forceList) - { - ActivityObject.DrawLine(Vector2.Zero, force.Velocity.Rotated(-globalRotation), Colors.YellowGreen); - } - } -} \ No newline at end of file diff --git a/DungeonShooting_Godot/src/framework/components/MoveController.cs b/DungeonShooting_Godot/src/framework/components/MoveController.cs new file mode 100644 index 0000000..184116c --- /dev/null +++ b/DungeonShooting_Godot/src/framework/components/MoveController.cs @@ -0,0 +1,225 @@ + +using System.Collections.Generic; +using Godot; + +/// +/// 移动控制器, 物体运动由力来控制, 不同方向的力速度最终会汇总 +/// +public class MoveController : Component +{ + private static long _index = 0; + + /// + /// 玩家受到的外力的集合 + /// + private readonly List _forceList = new List(); + + /// + /// 这个速度就是玩家当前物理帧移动的真实速率, 该速度由物理帧循环更新, 并不会马上更新 + /// 该速度就是 BasisVelocity + 外力总和 + /// + public Vector2 Velocity => _velocity; + + private Vector2 _velocity = Vector2.Zero; + + + /// + /// 玩家的基础移动速率 + /// + public Vector2 BasisVelocity + { + get => _basisVelocity; + set => _basisVelocity = value; + } + + private Vector2 _basisVelocity = Vector2.Zero; + + /// + /// 获取所有外力对象 + /// + public ExternalForce[] GetAllForce() + { + return _forceList.ToArray(); + } + + /// + /// 快速窗口一个外力, 该外力为匿名外力, 当速率变为 0 时自动销毁 + /// + /// 外力速率 + /// 阻力大小 + public ExternalForce AddForce(Vector2 velocity, float resistance) + { + var force = AddForce("_anonymity_" + _index++); + force.Velocity = velocity; + force.Resistance = resistance; + return force; + } + + /// + /// 根据名称添加一个外力, 并返回创建的外力的对象, 如果存在这个名称的外力, 移除之前的外力 + /// + public ExternalForce AddForce(string name) + { + var f = new ExternalForce(name); + AddForce(f); + return f; + } + + /// + /// 根据对象添加一个外力力, 如果存在这个名称的外力, 移除之前的外力 + /// + public T AddForce(T force) where T : ExternalForce + { + RemoveForce(force.Name); + _forceList.Add(force); + return force; + } + + /// + /// 根据名称移除一个外力 + /// + public void RemoveForce(string name) + { + for (var i = 0; i < _forceList.Count; i++) + { + if (_forceList[i].Name == name) + { + _forceList.RemoveAt(i); + return; + } + } + } + + /// + /// 根据名称获取一个外力 + /// + public ExternalForce GetForce(string name) + { + for (var i = 0; i < _forceList.Count; i++) + { + var externalForce = _forceList[i]; + if (externalForce.Name == name) + { + return externalForce; + } + } + + return null; + } + + /// + /// 检车是否有当前名称的外力对象 + /// + public bool ContainsForce(string name) + { + for (var i = 0; i < _forceList.Count; i++) + { + var externalForce = _forceList[i]; + if (externalForce.Name == name) + { + return true; + } + } + + return false; + } + + /// + /// 根据对象移除一个外力 + /// + public void RemoveForce(ExternalForce force) + { + RemoveForce(force.Name); + } + + /// + /// 移除所有外力 + /// + public void ClearForce() + { + _forceList.Clear(); + } + + public override void PhysicsProcess(float delta) + { + if (_basisVelocity == Vector2.Zero && _forceList.Count == 0) + { + return; + } + + //先调用更新 + var externalForces = _forceList.ToArray(); + foreach (var fore in externalForces) + { + if (fore.Enable) + fore.PhysicsProcess(delta); + } + + //外力总和 + var finallyEf = new Vector2(); + foreach (var fore in externalForces) + { + if (fore.Enable) + finallyEf += fore.Velocity; + } + + //最终速率 + var finallyVelocity = _basisVelocity + finallyEf; + + if (finallyVelocity != Vector2.Zero) + { + //计算移动 + _velocity = ActivityObject.MoveAndSlide(finallyVelocity); + if (_velocity.x == 0f && _basisVelocity.x * finallyVelocity.x > 0) + { + _basisVelocity.x = 0; + } + + if (_velocity.y == 0f && _basisVelocity.y * finallyVelocity.y > 0) + { + _basisVelocity.y = 0; + } + + //调整外力速率 + if (externalForces.Length > 0) + { + for (var i = 0; i < _forceList.Count; i++) + { + var force = _forceList[i]; + if (force.Enable) + { + var velocity = force.Velocity; + force.Velocity = new Vector2( + _velocity.x == 0f && velocity.x * finallyVelocity.x > 0 ? 0 : velocity.x, + _velocity.y == 0f && velocity.y * finallyVelocity.y > 0 ? 0 : velocity.y + ); + + if (force.Resistance != 0) + { + force.Velocity = force.Velocity.MoveToward(Vector2.Zero, force.Resistance * delta); + } + + if (force.AutoDestroy && force.Velocity == Vector2.Zero) + { + _forceList.RemoveAt(i--); + } + } + } + } + } + else + { + _velocity = finallyEf; + } + } + + public override void DebugDraw() + { + var globalRotation = GlobalRotation; + ActivityObject.DrawLine(Vector2.Zero, BasisVelocity.Rotated(-globalRotation), Colors.Yellow); + foreach (var force in _forceList) + { + ActivityObject.DrawLine(Vector2.Zero, force.Velocity.Rotated(-globalRotation), Colors.YellowGreen); + } + } +} \ No newline at end of file diff --git a/DungeonShooting_Godot/src/framework/components/StateBase.cs b/DungeonShooting_Godot/src/framework/components/StateBase.cs new file mode 100644 index 0000000..c4d2d17 --- /dev/null +++ b/DungeonShooting_Godot/src/framework/components/StateBase.cs @@ -0,0 +1,92 @@ +using System; + +/// +/// 状态基类 +/// +public abstract class StateBase where T : ActivityObject where S : Enum +{ + /// + /// 当前活跃的状态对象实例 + /// + public StateBase CurrStateBase => StateController.CurrStateBase; + + /// + /// 当前对象对应的状态枚举 + /// + public S State { get; } + + /// + /// 当前状态对象挂载的角色对象 + /// + public T Master { get; set; } + + /// + /// 当前状态对象所处的状态机对象 + /// + public StateController StateController { get; set; } + + public StateBase(S state) + { + State = state; + } + + /// + /// 当从其他状态进入到当前状态时调用 + /// + /// 上一个状态类型 + /// 切换当前状态时附带的参数 + public virtual void Enter(S prev, params object[] args) + { + + } + + /// + /// 如果当前状态已被激活, 物理帧每帧更新 + /// + public virtual void PhysicsProcess(float delta) + { + + } + + /// + /// 是否允许切换至下一个状态, 该函数由状态机控制器调用, 不需要手动调用 + /// + /// 下一个状态类型 + public virtual bool CanChangeState(S next) + { + return true; + } + + /// + /// 从当前状态退出时调用 + /// + /// 下一个状态类型 + public virtual void Exit(S next) + { + + } + + /// + /// 当启用 debug 后调用该函数, 调试绘制, 需要调用 Master 身上的绘制函数 + /// + public virtual void DebugDraw() + { + + } + + /// + /// 立即切换到下一个指定状态, 并且这一帧会被调用 PhysicsProcess + /// + public void ChangeState(S next, params object[] args) + { + StateController.ChangeState(next, args); + } + + /// + /// 切换到下一个指定状态, 下一帧才会调用 PhysicsProcess + /// + public void ChangeStateLate(S next, params object[] args) + { + StateController.ChangeStateLate(next, args); + } +} \ No newline at end of file diff --git a/DungeonShooting_Godot/src/framework/components/StateController.cs b/DungeonShooting_Godot/src/framework/components/StateController.cs new file mode 100644 index 0000000..969dcdf --- /dev/null +++ b/DungeonShooting_Godot/src/framework/components/StateController.cs @@ -0,0 +1,145 @@ +using System; +using Godot; +using System.Collections.Generic; + +/// +/// 对象状态机控制器 +/// +public class StateController : Component where T : ActivityObject where S : Enum +{ + /// + /// 获取当前状态 + /// + public S CurrState => CurrStateBase != null ? CurrStateBase.State : default; + + /// + /// 当前活跃的状态对象实例 + /// + public StateBase CurrStateBase { get; private set; } + + /// + /// 负责存放状态实例对象 + /// + private readonly Dictionary> _states = new Dictionary>(); + + /// + /// 记录下当前帧是否有改变的状态 + /// + private bool _isChangeState; + + public override void PhysicsProcess(float delta) + { + _isChangeState = false; + if (CurrStateBase != null) + { + CurrStateBase.PhysicsProcess(delta); + //判断当前帧是否有改变的状态, 如果有, 则重新调用 PhysicsProcess() 方法 + if (_isChangeState) + { + PhysicsProcess(delta); + } + } + } + + public override void DebugDraw() + { + if (CurrStateBase != null) + { + CurrStateBase.DebugDraw(); + } + } + + /// + /// 往状态机里注册一个新的状态实例 + /// + public void Register(StateBase stateBase) + { + if (GetStateInstance(stateBase.State) != null) + { + GD.PrintErr("当前状态已经在状态机中注册:", stateBase); + return; + } + + stateBase.Master = ActivityObject as T; + stateBase.StateController = this; + _states.Add(stateBase.State, stateBase); + } + + /// + /// 返回该状态机控制器中是否存在指定的状态实例 + /// + public bool HasState(S state) + { + return _states.ContainsKey(state); + } + + /// + /// 获取指定状态对应的实例对象 + /// + public StateBase GetState(S state) + { + if (_states.ContainsKey(state)) + { + return _states[state]; + } + + return null; + } + + /// + /// 立即切换到下一个指定状态, 并且这一帧会被调用 PhysicsProcess + /// + public void ChangeState(S next, params object[] arg) + { + _changeState(false, next, arg); + } + + /// + /// 切换到下一个指定状态, 下一帧才会调用 PhysicsProcess + /// + public void ChangeStateLate(S next, params object[] arg) + { + _changeState(true, next, arg); + } + + /// + /// 根据状态类型获取相应的状态对象 + /// + private StateBase GetStateInstance(S stateType) + { + _states.TryGetValue(stateType, out var v); + return v; + } + + /// + /// 切换状态 + /// + private void _changeState(bool late, S next, params object[] arg) + { + if (CurrStateBase != null && CurrStateBase.State.Equals(next)) + { + return; + } + + var newState = GetStateInstance(next); + if (newState == null) + { + GD.PrintErr("当前状态机未找到相应状态:" + next); + return; + } + + if (CurrStateBase == null) + { + CurrStateBase = newState; + newState.Enter(default, arg); + } + else if (CurrStateBase.CanChangeState(next)) + { + _isChangeState = !late; + var prev = CurrStateBase.State; + CurrStateBase.Exit(next); + CurrStateBase = newState; + CurrStateBase.Enter(prev, arg); + } + } +} \ No newline at end of file diff --git a/DungeonShooting_Godot/src/framework/generate/GenerateDungeon.cs b/DungeonShooting_Godot/src/framework/generate/GenerateDungeon.cs new file mode 100644 index 0000000..264a35c --- /dev/null +++ b/DungeonShooting_Godot/src/framework/generate/GenerateDungeon.cs @@ -0,0 +1,62 @@ + +using System.Collections.Generic; +using Godot; + +/// +/// 地牢生成器 +/// +public class GenerateDungeon +{ + public readonly TileMap TileMap; + + public GenerateDungeon(TileMap tileMap) + { + TileMap = tileMap; + } + + public void Generate() + { + List roomInfos = new List(); + var x = 0; + var y = 0; + for (int i = 0; i < 10; i++) + { + var roomInfo = GenerateRoom(); + roomInfos.Add(roomInfo); + roomInfo.Position = new Vector2(x + 2, y + 2); + + if (Utils.RandBoolean()) + { + x = x + 2 + (int)roomInfo.Size.x; + } + else + { + y = y + 2 + (int)roomInfo.Size.y; + } + + } + + foreach (var info in roomInfos) + { + //临时铺上地砖 + var id = (int)TileMap.TileSet.GetTilesIds()[0]; + for (int i = 0; i < info.Size.x; i++) + { + for (int j = 0; j < info.Size.y; j++) + { + TileMap.SetCell(i + (int)info.Position.x, j + (int)info.Position.y, id); + } + } + } + } + + public RoomInfo GenerateRoom() + { + var info = new RoomInfo(); + //房间大小 + info.Size = new Vector2(Utils.RandRange(5, 10), Utils.RandRange(5, 10)); + + + return info; + } +} \ No newline at end of file diff --git a/DungeonShooting_Godot/src/framework/generate/RoomInfo.cs b/DungeonShooting_Godot/src/framework/generate/RoomInfo.cs new file mode 100644 index 0000000..603ab08 --- /dev/null +++ b/DungeonShooting_Godot/src/framework/generate/RoomInfo.cs @@ -0,0 +1,21 @@ + +using Godot; + +/// +/// 房间的数据描述 +/// +public class RoomInfo +{ + /// + /// 房间大小 + /// + public Vector2 Size; + + /// + /// 房间位置 + /// + public Vector2 Position; + + public object Doors; + +} \ No newline at end of file diff --git a/DungeonShooting_Godot/src/game/common/Utils.cs b/DungeonShooting_Godot/src/game/common/Utils.cs index 153d6ca..9bfa45e 100644 --- a/DungeonShooting_Godot/src/game/common/Utils.cs +++ b/DungeonShooting_Godot/src/game/common/Utils.cs @@ -5,6 +5,15 @@ /// public static class Utils { + + /// + /// 返回随机 boolean 值 + /// + public static bool RandBoolean() + { + return GD.Randf() >= 0.5f; + } + /// /// 返回一个区间内的随机小数 /// diff --git a/DungeonShooting_Godot/src/game/role/Role.cs b/DungeonShooting_Godot/src/game/role/Role.cs index 90c1cfc..99bc480 100644 --- a/DungeonShooting_Godot/src/game/role/Role.cs +++ b/DungeonShooting_Godot/src/game/role/Role.cs @@ -472,7 +472,7 @@ GameApplication.Instance.Room.GetRoot().AddChild(blood); } - PlayHitAnimation(); + //PlayHitAnimation(); //死亡判定 if (Hp <= 0) diff --git a/DungeonShooting_Godot/src/game/role/StateBase.cs b/DungeonShooting_Godot/src/game/role/StateBase.cs deleted file mode 100644 index c4d2d17..0000000 --- a/DungeonShooting_Godot/src/game/role/StateBase.cs +++ /dev/null @@ -1,92 +0,0 @@ -using System; - -/// -/// 状态基类 -/// -public abstract class StateBase where T : ActivityObject where S : Enum -{ - /// - /// 当前活跃的状态对象实例 - /// - public StateBase CurrStateBase => StateController.CurrStateBase; - - /// - /// 当前对象对应的状态枚举 - /// - public S State { get; } - - /// - /// 当前状态对象挂载的角色对象 - /// - public T Master { get; set; } - - /// - /// 当前状态对象所处的状态机对象 - /// - public StateController StateController { get; set; } - - public StateBase(S state) - { - State = state; - } - - /// - /// 当从其他状态进入到当前状态时调用 - /// - /// 上一个状态类型 - /// 切换当前状态时附带的参数 - public virtual void Enter(S prev, params object[] args) - { - - } - - /// - /// 如果当前状态已被激活, 物理帧每帧更新 - /// - public virtual void PhysicsProcess(float delta) - { - - } - - /// - /// 是否允许切换至下一个状态, 该函数由状态机控制器调用, 不需要手动调用 - /// - /// 下一个状态类型 - public virtual bool CanChangeState(S next) - { - return true; - } - - /// - /// 从当前状态退出时调用 - /// - /// 下一个状态类型 - public virtual void Exit(S next) - { - - } - - /// - /// 当启用 debug 后调用该函数, 调试绘制, 需要调用 Master 身上的绘制函数 - /// - public virtual void DebugDraw() - { - - } - - /// - /// 立即切换到下一个指定状态, 并且这一帧会被调用 PhysicsProcess - /// - public void ChangeState(S next, params object[] args) - { - StateController.ChangeState(next, args); - } - - /// - /// 切换到下一个指定状态, 下一帧才会调用 PhysicsProcess - /// - public void ChangeStateLate(S next, params object[] args) - { - StateController.ChangeStateLate(next, args); - } -} \ No newline at end of file diff --git a/DungeonShooting_Godot/src/game/role/StateController.cs b/DungeonShooting_Godot/src/game/role/StateController.cs deleted file mode 100644 index 969dcdf..0000000 --- a/DungeonShooting_Godot/src/game/role/StateController.cs +++ /dev/null @@ -1,145 +0,0 @@ -using System; -using Godot; -using System.Collections.Generic; - -/// -/// 对象状态机控制器 -/// -public class StateController : Component where T : ActivityObject where S : Enum -{ - /// - /// 获取当前状态 - /// - public S CurrState => CurrStateBase != null ? CurrStateBase.State : default; - - /// - /// 当前活跃的状态对象实例 - /// - public StateBase CurrStateBase { get; private set; } - - /// - /// 负责存放状态实例对象 - /// - private readonly Dictionary> _states = new Dictionary>(); - - /// - /// 记录下当前帧是否有改变的状态 - /// - private bool _isChangeState; - - public override void PhysicsProcess(float delta) - { - _isChangeState = false; - if (CurrStateBase != null) - { - CurrStateBase.PhysicsProcess(delta); - //判断当前帧是否有改变的状态, 如果有, 则重新调用 PhysicsProcess() 方法 - if (_isChangeState) - { - PhysicsProcess(delta); - } - } - } - - public override void DebugDraw() - { - if (CurrStateBase != null) - { - CurrStateBase.DebugDraw(); - } - } - - /// - /// 往状态机里注册一个新的状态实例 - /// - public void Register(StateBase stateBase) - { - if (GetStateInstance(stateBase.State) != null) - { - GD.PrintErr("当前状态已经在状态机中注册:", stateBase); - return; - } - - stateBase.Master = ActivityObject as T; - stateBase.StateController = this; - _states.Add(stateBase.State, stateBase); - } - - /// - /// 返回该状态机控制器中是否存在指定的状态实例 - /// - public bool HasState(S state) - { - return _states.ContainsKey(state); - } - - /// - /// 获取指定状态对应的实例对象 - /// - public StateBase GetState(S state) - { - if (_states.ContainsKey(state)) - { - return _states[state]; - } - - return null; - } - - /// - /// 立即切换到下一个指定状态, 并且这一帧会被调用 PhysicsProcess - /// - public void ChangeState(S next, params object[] arg) - { - _changeState(false, next, arg); - } - - /// - /// 切换到下一个指定状态, 下一帧才会调用 PhysicsProcess - /// - public void ChangeStateLate(S next, params object[] arg) - { - _changeState(true, next, arg); - } - - /// - /// 根据状态类型获取相应的状态对象 - /// - private StateBase GetStateInstance(S stateType) - { - _states.TryGetValue(stateType, out var v); - return v; - } - - /// - /// 切换状态 - /// - private void _changeState(bool late, S next, params object[] arg) - { - if (CurrStateBase != null && CurrStateBase.State.Equals(next)) - { - return; - } - - var newState = GetStateInstance(next); - if (newState == null) - { - GD.PrintErr("当前状态机未找到相应状态:" + next); - return; - } - - if (CurrStateBase == null) - { - CurrStateBase = newState; - newState.Enter(default, arg); - } - else if (CurrStateBase.CanChangeState(next)) - { - _isChangeState = !late; - var prev = CurrStateBase.State; - CurrStateBase.Exit(next); - CurrStateBase = newState; - CurrStateBase.Enter(prev, arg); - } - } -} \ No newline at end of file diff --git a/DungeonShooting_Godot/src/test/TestGenerateDungeon.cs b/DungeonShooting_Godot/src/test/TestGenerateDungeon.cs new file mode 100644 index 0000000..88b1272 --- /dev/null +++ b/DungeonShooting_Godot/src/test/TestGenerateDungeon.cs @@ -0,0 +1,33 @@ +using System; +using Godot; + +public class TestGenerateDungeon : Node2D +{ + [Export] + public NodePath TileMapPath; + + [Export] + public NodePath Camera; + + private TileMap _tileMap; + private Camera2D _camera; + + public override void _Ready() + { + GD.Randomize(); + _tileMap = GetNode(TileMapPath); + _camera = GetNode(Camera); + + var temp = new GenerateDungeon(_tileMap); + temp.Generate(); + } + + public override void _Process(float delta) + { + //移动相机位置 + var dir = Input.GetVector("move_left", "move_right", "move_up", "move_down"); + _camera.Position += dir * 500 * delta; + + + } +} \ No newline at end of file