跳到主要内容

在运行时注册和移除事件流程

TinyGiants
Unity Games & Tools Developer

程序生成的房间要等布局确定后,才能把压力板连接到对应陷阱,创建房间后注册连接,由房间管理对象保存句柄,回收房间时按句柄移除

注册独立的 Trigger 分支​

一个事件要发起多个独立反应时,用 Trigger 连接

例如开门后打开灯光并解除警报

下面三个字段都使用无参数的 GameEvent 资产

TriggerHandle lights = onDoorOpened.AddTriggerEvent(
onLightsOn,
delay: 0.5f,
condition: () => isNight);

TriggerHandle alarm = onDoorOpened.AddTriggerEvent(
onAlarmDisabled,
priority: 10);

GES 在源事件派发时检查条件,按优先级从高到低遍历 Trigger

延迟为零的目标立即触发,有延迟的目标在计时结束后触发

图中各条分支分别响应同一个源事件

Trigger 流程图

有参数的事件可以转发或转换参数

这里 onPlayerHit 是 Int32GameEvent,onDamageScale 是接收 float 的 SingleGameEvent

TriggerHandle scale = onPlayerHit.AddTriggerEvent(
onDamageScale,
condition: amount => amount > 0,
passArgument: true,
argumentTransformer: amount => amount / 100f);

把句柄和源事件一起保存

解绑时,将句柄交回注册它的源事件

onDoorOpened.RemoveTriggerEvent(lights);
onDoorOpened.RemoveTriggerEvent(alarm);
onPlayerHit.RemoveTriggerEvent(scale);

把 Chain 步骤注册到同一个源事件​

Chain 按注册顺序执行同一个源事件下的步骤

下面三个事件都是无参数的 GameEvent

onBossPhaseStart 触发后,第一步播放动画并等待 3 秒,第二步再等 0.5 秒后触发召唤

ChainHandle animation = onBossPhaseStart.AddChainEvent(
onPlayBossAnimation,
duration: 3f);

ChainHandle spawn = onBossPhaseStart.AddChainEvent(
onSpawnAdds,
delay: 0.5f);

delay 在触发目标前计时,duration 在触发后计时

条件为假会结束当前链的剩余步骤

waitForCompletion: true 会在步骤后多等一帧

需要等实际动画播放完再召唤时,在动画完成回调中发出另一个事件,并用它作为召唤的源事件

Chain 流程图

把步骤注册到同一个源事件,让它们按同一条链执行

阶段结束时,调用 onBossPhaseStart.RemoveChainEvent(animation) 和 onBossPhaseStart.RemoveChainEvent(spawn) 解绑

生成房间时注册连接​

给房间分配独立的进入事件,再为灯光和准备完成分别注册 Trigger 和 Chain

房间组件保存两条连接的句柄,在禁用时解绑

using TinyGiants.GES.Runtime;
using UnityEngine;

public sealed class DungeonRoomEvents : MonoBehaviour
{
[GameEventDropdown, SerializeField] private GameEvent onRoomEntered;
[GameEventDropdown, SerializeField] private GameEvent onLightsOn;
[GameEventDropdown, SerializeField] private GameEvent onRoomReady;
[SerializeField] private bool isCleared;

private TriggerHandle _lights;
private ChainHandle _ready;

private void OnEnable()
{
_lights = onRoomEntered.AddTriggerEvent(
onLightsOn, condition: () => !isCleared);

_ready = onRoomEntered.AddChainEvent(
onRoomReady, delay: 2f, condition: () => !isCleared);
}

public void EnterRoom() => onRoomEntered.Raise();

private void OnDisable()
{
onRoomEntered.RemoveTriggerEvent(_lights);
onRoomEntered.RemoveChainEvent(_ready);
_lights = null;
_ready = null;
}
}

通关状态由房间保存,条件直接读取它

移除句柄会更新后续派发的连接,已开始的延迟 Trigger 或 Chain 仍可能执行

依赖房间状态的延迟回调应在写入前确认房间仍有效

在 Play Mode 触发房间进入事件,然后到 Game Event Monitor 的 Automation 查看 Trigger 和 Chain 连接

Monitor 的 Automation 树


🚀 全球开发者服务矩阵

🇨🇳 国区开发者社区

🌐 全球开发者社区

📧 支持与合作