mirror of
https://github.com/GeWuYou/GFramework.git
synced 2026-03-22 10:34:30 +08:00
feat(GFramework.Godot): 增强架构生命周期管理与扩展支持
- 将 `Architecture.Destroy` 方法标记为 `virtual`,允许子类重写销毁逻辑 - 在 `AbstractArchitecture` 中引入 Godot 生命周期绑定机制,通过锚点节点自动管理架构销毁 - 新增 `IGodotArchitectureExtension` 接口,支持模块化的扩展组件安装与卸载 - 实现 `InstallGodotExtension` 方法,用于异步加载并挂载扩展节点至架构根节点 - 改进 `ArchitectureAnchorNode` 的回调绑定逻辑,增加重复绑定警告提示 - 优化注释内容,提升代码可读性与维护性
This commit is contained in:
parent
f990f8d2c1
commit
86053f2aee
@ -177,7 +177,7 @@ public abstract class Architecture<T> : IArchitecture where T : Architecture<T>,
|
||||
/// 此函数负责有序地销毁架构中的所有系统组件,并发送相应的生命周期事件。
|
||||
/// 函数会确保只执行一次销毁操作,避免重复销毁。
|
||||
/// </remarks>
|
||||
public void Destroy()
|
||||
public virtual void Destroy()
|
||||
{
|
||||
// 检查当前阶段,如果已经处于销毁或已销毁状态则直接返回
|
||||
if (CurrentPhase >= ArchitecturePhase.Destroying)
|
||||
|
||||
@ -1,33 +1,66 @@
|
||||
using GFramework.Core.architecture;
|
||||
using GFramework.Godot.extensions;
|
||||
using Godot;
|
||||
|
||||
namespace GFramework.Godot.architecture;
|
||||
|
||||
/// <summary>
|
||||
/// 抽象架构类,为特定类型的架构提供基础实现框架
|
||||
/// 抽象架构类,为特定类型的架构提供基础实现框架。
|
||||
/// 此类负责管理架构的初始化、生命周期绑定以及扩展模块的安装与销毁。
|
||||
/// </summary>
|
||||
/// <typeparam name="T">架构的具体类型,必须继承自Architecture且能被实例化</typeparam>
|
||||
/// <typeparam name="T">架构的具体类型,必须继承自Architecture且能被实例化。</typeparam>
|
||||
public abstract class AbstractArchitecture<T> : Architecture<T> where T : Architecture<T>, new()
|
||||
{
|
||||
/// <summary>
|
||||
/// 架构锚点节点的唯一标识名称
|
||||
/// 用于在Godot场景树中创建和查找架构锚点节点
|
||||
/// </summary>
|
||||
private const string ArchitectureName = "__GFramework__Architecture__Anchor";
|
||||
|
||||
/// <summary>
|
||||
/// 初始化架构,按顺序注册模型、系统和工具
|
||||
/// 存储所有已安装的Godot架构扩展组件列表
|
||||
/// 用于在架构销毁时正确清理所有扩展资源
|
||||
/// </summary>
|
||||
private readonly List<IGodotArchitectureExtension<T>> _extensions = [];
|
||||
|
||||
/// <summary>
|
||||
/// 架构锚点节点引用
|
||||
/// 用于将架构绑定到Godot生命周期并作为扩展节点的父节点
|
||||
/// </summary>
|
||||
private ArchitectureAnchorNode? _anchor;
|
||||
|
||||
/// <summary>
|
||||
/// 获取架构根节点。如果尚未初始化或已被销毁,则抛出异常。
|
||||
/// </summary>
|
||||
/// <exception cref="InvalidOperationException">当架构未准备就绪时抛出。</exception>
|
||||
protected Node ArchitectureRoot => _anchor ?? throw new InvalidOperationException("Architecture root not ready");
|
||||
|
||||
/// <summary>
|
||||
/// 标记架构是否已被销毁的状态标志
|
||||
/// 用于防止架构被重复销毁,确保资源清理只执行一次
|
||||
/// </summary>
|
||||
private bool _destroyed;
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// 初始化架构,按顺序注册模型、系统和工具。
|
||||
/// 包括将架构绑定到Godot生命周期并调用模块安装逻辑。
|
||||
/// </summary>
|
||||
protected override void Init()
|
||||
{
|
||||
AttachToGodotLifecycle();
|
||||
InstallModules();
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// 安装模块抽象方法,由子类实现具体的模块注册逻辑
|
||||
/// 安装模块抽象方法,由子类实现具体的模块注册逻辑。
|
||||
/// 子类应在此方法中完成所有模型、系统及工具的注册工作。
|
||||
/// </summary>
|
||||
protected abstract void InstallModules();
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// 将架构绑定到Godot生命周期中,确保在场景树销毁时能够正确清理资源
|
||||
/// 通过创建一个锚节点来监听场景树的销毁事件
|
||||
/// 将架构绑定到Godot生命周期中,确保在场景树销毁时能够正确清理资源。
|
||||
/// 通过创建一个锚节点来监听场景树的销毁事件。
|
||||
/// </summary>
|
||||
private void AttachToGodotLifecycle()
|
||||
{
|
||||
@ -38,14 +71,58 @@ public abstract class AbstractArchitecture<T> : Architecture<T> where T : Archit
|
||||
if (tree.Root.GetNodeOrNull(ArchitectureName) != null)
|
||||
return;
|
||||
|
||||
var anchor = new ArchitectureAnchorNode
|
||||
_anchor = new ArchitectureAnchorNode
|
||||
{
|
||||
Name = ArchitectureName
|
||||
};
|
||||
|
||||
anchor.Bind(Destroy);
|
||||
_anchor.Bind(Destroy);
|
||||
|
||||
tree.Root.CallDeferred(Node.MethodName.AddChild, anchor);
|
||||
tree.Root.CallDeferred(Node.MethodName.AddChild, _anchor);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// 安装Godot架构扩展组件
|
||||
/// </summary>
|
||||
/// <param name="extension">要安装的Godot架构扩展实例,必须实现IGodotArchitectureExtension接口</param>
|
||||
/// <returns>异步任务,表示扩展安装过程</returns>
|
||||
protected async Task InstallGodotExtension(IGodotArchitectureExtension<T> extension)
|
||||
{
|
||||
// 检查锚点是否已初始化,未初始化则抛出异常
|
||||
if (_anchor == null)
|
||||
throw new InvalidOperationException("Anchor not initialized");
|
||||
|
||||
// 等待锚点准备就绪
|
||||
await _anchor.WaitUntilReady();
|
||||
|
||||
// 延迟调用将扩展节点添加为锚点的子节点
|
||||
_anchor.CallDeferred(Node.MethodName.AddChild, extension.Node);
|
||||
|
||||
// 调用扩展的附加回调方法
|
||||
extension.OnAttach(this);
|
||||
|
||||
// 将扩展添加到扩展集合中
|
||||
_extensions.Add(extension);
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// 销毁架构及其相关资源。
|
||||
/// 调用所有已安装扩展的OnDetach方法,并清空扩展列表。
|
||||
/// 若已被销毁则直接返回。
|
||||
/// </summary>
|
||||
public override void Destroy()
|
||||
{
|
||||
if (_destroyed)
|
||||
return;
|
||||
|
||||
_destroyed = true;
|
||||
foreach (var ext in _extensions)
|
||||
ext.OnDetach();
|
||||
|
||||
_extensions.Clear();
|
||||
|
||||
base.Destroy();
|
||||
}
|
||||
}
|
||||
@ -9,13 +9,17 @@ namespace GFramework.Godot.architecture;
|
||||
public partial class ArchitectureAnchorNode : Node
|
||||
{
|
||||
private Action? _onExit;
|
||||
|
||||
/// <summary>
|
||||
/// 绑定节点退出时的回调动作
|
||||
/// </summary>
|
||||
/// <param name="onExit">当节点从场景树退出时要执行的动作</param>
|
||||
public void Bind(Action onExit)
|
||||
{
|
||||
if (_onExit != null)
|
||||
{
|
||||
GD.PushWarning(
|
||||
$"{nameof(ArchitectureAnchorNode)} already bound. Rebinding will override previous callback.");
|
||||
}
|
||||
_onExit = onExit;
|
||||
}
|
||||
|
||||
@ -25,10 +29,9 @@ public partial class ArchitectureAnchorNode : Node
|
||||
/// </summary>
|
||||
public override void _ExitTree()
|
||||
{
|
||||
// 执行退出回调
|
||||
_onExit?.Invoke();
|
||||
// 清理引用
|
||||
var callback = _onExit;
|
||||
_onExit = null;
|
||||
callback?.Invoke();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
11
GFramework.Godot/architecture/IGodotArchitectureExtension.cs
Normal file
11
GFramework.Godot/architecture/IGodotArchitectureExtension.cs
Normal file
@ -0,0 +1,11 @@
|
||||
using GFramework.Core.architecture;
|
||||
using Godot;
|
||||
|
||||
namespace GFramework.Godot.architecture;
|
||||
|
||||
public interface IGodotArchitectureExtension<T> where T : Architecture<T>, new()
|
||||
{
|
||||
Node Node { get; }
|
||||
void OnAttach(Architecture<T> architecture);
|
||||
void OnDetach();
|
||||
}
|
||||
Loading…
x
Reference in New Issue
Block a user