From 9c27aa5927c5fd6861a982fccfb4aa4d03c5433b Mon Sep 17 00:00:00 2001
From: GeWuYou <95328647+GeWuYou@users.noreply.github.com>
Date: Mon, 19 Jan 2026 22:00:00 +0800
Subject: [PATCH] =?UTF-8?q?feat(ui):=20=E6=B7=BB=E5=8A=A0=E5=AF=B9?=
=?UTF-8?q?=E5=B7=B2=E5=AD=98=E5=9C=A8UI=E9=A1=B5=E9=9D=A2=E7=9A=84?=
=?UTF-8?q?=E8=B7=AF=E7=94=B1=E6=8E=A8=E9=80=81=E6=94=AF=E6=8C=81?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
- 在UiRouterBase中新增Push方法重载,支持直接推送已创建的IUiPageBehavior实例
- 统一页面推送逻辑到DoPushPageInternal方法,同时处理工厂创建和现有页面
- 更新Replace方法使用新的页面推送逻辑
- 优化日志输出,统一使用View.GetType().Name获取页面类型名称
- 为新功能添加完整的XML文档注释
- 在IUiRouter接口中定义新的Push方法重载签名
---
GFramework.Game.Abstractions/ui/IUiRouter.cs | 9 +++
GFramework.Game/ui/UiRouterBase.cs | 64 +++++++++++++++++---
2 files changed, 63 insertions(+), 10 deletions(-)
diff --git a/GFramework.Game.Abstractions/ui/IUiRouter.cs b/GFramework.Game.Abstractions/ui/IUiRouter.cs
index e311bad..c942344 100644
--- a/GFramework.Game.Abstractions/ui/IUiRouter.cs
+++ b/GFramework.Game.Abstractions/ui/IUiRouter.cs
@@ -27,6 +27,15 @@ public interface IUiRouter : ISystem
/// 界面切换策略,默认为Exclusive(独占)
void Push(string uiKey, IUiPageEnterParam? param = null, UiTransitionPolicy policy = UiTransitionPolicy.Exclusive);
+ ///
+ /// 将已存在的UI页面压入路由栈
+ /// 用于预挂载节点或调试场景
+ ///
+ /// 已创建的UI页面行为实例
+ /// 进入界面的参数,可为空
+ /// 界面切换策略,默认为Exclusive(独占)
+ void Push(IUiPageBehavior page, IUiPageEnterParam? param = null,
+ UiTransitionPolicy policy = UiTransitionPolicy.Exclusive);
///
/// 弹出路由栈顶的UI界面,返回到上一个界面
diff --git a/GFramework.Game/ui/UiRouterBase.cs b/GFramework.Game/ui/UiRouterBase.cs
index d776a2e..6733713 100644
--- a/GFramework.Game/ui/UiRouterBase.cs
+++ b/GFramework.Game/ui/UiRouterBase.cs
@@ -85,10 +85,47 @@ public abstract class UiRouterBase : AbstractSystem, IUiRouter
);
BeforeChange(@event);
- DoPushInternal(uiKey, param, policy);
+
+ // 先创建页面,然后使用统一的Push逻辑
+ var page = _factory.Create(uiKey);
+ Log.Debug("Create UI Page instance: {0}", page.GetType().Name);
+
+ DoPushPageInternal(page, param, policy);
+
AfterChange(@event);
}
+ ///
+ /// 将已存在的UI页面压入栈顶并显示
+ ///
+ /// 已创建的UI页面行为实例
+ /// 页面进入参数,可为空
+ /// 页面切换策略
+ public void Push(
+ IUiPageBehavior page,
+ IUiPageEnterParam? param = null,
+ UiTransitionPolicy policy = UiTransitionPolicy.Exclusive
+ )
+ {
+ var uiKey = page.View.GetType().Name;
+
+ if (IsTop(uiKey))
+ {
+ Log.Warn("Push ignored: UI already on top: {0}", uiKey);
+ return;
+ }
+
+ var @event = CreateEvent(uiKey, UiTransitionType.Push, policy, param);
+
+ Log.Debug(
+ "Push existing UI Page: key={0}, policy={1}, stackBefore={2}",
+ uiKey, policy, _stack.Count
+ );
+
+ BeforeChange(@event);
+ DoPushPageInternal(page, param, policy);
+ AfterChange(@event);
+ }
///
/// 弹出栈顶页面并根据策略处理页面
@@ -139,7 +176,10 @@ public abstract class UiRouterBase : AbstractSystem, IUiRouter
// 使用内部方法,避免触发额外的Pipeline
DoClearInternal(popPolicy);
- DoPushInternal(uiKey, param, pushPolicy);
+
+ var page = _factory.Create(uiKey);
+ Log.Debug("Create UI Page instance for Replace: {0}", page.GetType().Name);
+ DoPushPageInternal(page, param, pushPolicy);
AfterChange(@event);
}
@@ -264,32 +304,36 @@ public abstract class UiRouterBase : AbstractSystem, IUiRouter
}
///
- /// 执行Push的核心逻辑(不触发Pipeline)
+ /// 执行Push页面的核心逻辑(统一处理)
+ /// 这个方法同时服务于工厂创建和已存在页面两种情况
///
- private void DoPushInternal(string uiKey, IUiPageEnterParam? param, UiTransitionPolicy policy)
+ private void DoPushPageInternal(IUiPageBehavior page, IUiPageEnterParam? param, UiTransitionPolicy policy)
{
+ // 1. 处理当前栈顶页面
if (_stack.Count > 0)
{
var current = _stack.Peek();
- Log.Debug("Pause current page: {0}", current.GetType().Name);
+ Log.Debug("Pause current page: {0}", current.View.GetType().Name);
current.OnPause();
if (policy == UiTransitionPolicy.Exclusive)
{
- Log.Debug("Hide current page (Exclusive): {0}", current.GetType().Name);
+ Log.Debug("Hide current page (Exclusive): {0}", current.View.GetType().Name);
current.OnHide();
}
}
- var page = _factory.Create(uiKey);
- Log.Debug("Create UI Page instance: {0}", page.GetType().Name);
-
+ // 2. 将新页面添加到UiRoot
+ Log.Debug("Add page to UiRoot: {0}", page.View.GetType().Name);
_uiRoot.AddUiPage(page);
+
+ // 3. 压入栈
_stack.Push(page);
+ // 4. 触发页面生命周期
Log.Debug(
"Enter & Show page: {0}, stackAfter={1}",
- page.GetType().Name, _stack.Count
+ page.View.GetType().Name, _stack.Count
);
page.OnEnter(param);