diff --git a/Assets/_Game/Scripts/Enemies/AIBrain/Modules/IDeathModule.cs b/Assets/_Game/Scripts/Enemies/AIBrain/Modules/IDeathModule.cs new file mode 100644 index 00000000..10a758a8 --- /dev/null +++ b/Assets/_Game/Scripts/Enemies/AIBrain/Modules/IDeathModule.cs @@ -0,0 +1,16 @@ +using BaseGames.AI; + +namespace BaseGames.Enemies +{ + /// + /// 死亡层:单态终结(演出交给物理状态机)/ 单段死亡能力 / 两段演出(可带生成物)。 + /// 骨架只挂一条 Global → EntryState 的 Died 事件边,链条内容全归本模块。 + /// + public interface IDeathModule + { + void Build(BrainBuilder b); + + /// 骨架全局死亡边指向的态。 + string EntryState { get; } + } +} diff --git a/Assets/_Game/Scripts/Enemies/AIBrain/Modules/IDeathModule.cs.meta b/Assets/_Game/Scripts/Enemies/AIBrain/Modules/IDeathModule.cs.meta new file mode 100644 index 00000000..449f7816 --- /dev/null +++ b/Assets/_Game/Scripts/Enemies/AIBrain/Modules/IDeathModule.cs.meta @@ -0,0 +1,11 @@ +fileFormatVersion: 2 +guid: ca95968c577c65244bfb6c5a9a908ef4 +MonoImporter: + externalObjects: {} + serializedVersion: 2 + defaultReferences: [] + executionOrder: 0 + icon: {instanceID: 0} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/_Game/Scripts/Enemies/AIBrain/Modules/IEngagementModule.cs b/Assets/_Game/Scripts/Enemies/AIBrain/Modules/IEngagementModule.cs new file mode 100644 index 00000000..b2139d00 --- /dev/null +++ b/Assets/_Game/Scripts/Enemies/AIBrain/Modules/IEngagementModule.cs @@ -0,0 +1,31 @@ +using System; +using BaseGames.AI; + +namespace BaseGames.Enemies +{ + /// + /// 交战层:发现玩家之后怎么打。骨架只认这四件事——从哪个态进、什么条件进、 + /// 边标签是什么、内部怎么打。新增一种打法 = 新增一个实现,骨架与其他模块不受影响。 + /// + /// CanEngage 归本模块所有是关键:像"冲锋冷却门"这种只对某一种打法有意义的条件, + /// 若留在骨架上就会变成骨架的开关字段,并与其他开关互相耦合。 + /// + /// 实现注意:模块会经 [SerializeReference] 反序列化,构造函数不保证被调用。 + /// 不要在构造函数里预计算缓存或做参数校验——缓存用惰性属性,校验放 Build()。 + /// + public interface IEngagementModule + { + /// 声明交战态与脱战边。 + /// 脱战后回到的未发现态,由骨架传入。 + void Build(BrainBuilder b, string rest); + + /// 骨架从未发现态 / 警觉态连过来的目标。 + string EntryState { get; } + + /// 进入交战的条件。惰性构建并缓存。 + Func CanEngage { get; } + + /// CanEngage 的可读标签(trace / 图导出用)。 + string EngageLabel { get; } + } +} diff --git a/Assets/_Game/Scripts/Enemies/AIBrain/Modules/IEngagementModule.cs.meta b/Assets/_Game/Scripts/Enemies/AIBrain/Modules/IEngagementModule.cs.meta new file mode 100644 index 00000000..c7640663 --- /dev/null +++ b/Assets/_Game/Scripts/Enemies/AIBrain/Modules/IEngagementModule.cs.meta @@ -0,0 +1,11 @@ +fileFormatVersion: 2 +guid: 0941f7f7a28a5374fbfd2971bde2ef54 +MonoImporter: + externalObjects: {} + serializedVersion: 2 + defaultReferences: [] + executionOrder: 0 + icon: {instanceID: 0} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/_Game/Scripts/Enemies/AIBrain/Modules/IUnawareModule.cs b/Assets/_Game/Scripts/Enemies/AIBrain/Modules/IUnawareModule.cs new file mode 100644 index 00000000..eda45fe4 --- /dev/null +++ b/Assets/_Game/Scripts/Enemies/AIBrain/Modules/IUnawareModule.cs @@ -0,0 +1,30 @@ +using System.Collections.Generic; +using BaseGames.AI; + +namespace BaseGames.Enemies +{ + /// + /// 未发现层:玩家尚未被发现时的行为形状(单一站桩 / 单向降级 / 定时交替 …)。 + /// + /// 刻意拆成两阶段:AiRuntime 按声明顺序评估条件边,若本模块的内部边(如巡逻计时) + /// 早于骨架的升级边声明,玩家进入追逐区那一帧若恰好计时到点,敌人会切去另一个待机态 + /// 而不是扑上来。骨架的调用顺序固定为 Declare → 挂升级边 → Link。 + /// + public interface IUnawareModule + { + /// 只声明状态与行为回调,不挂任何转换。 + void Declare(BrainBuilder b); + + /// 挂内部转换(如站立 ⇄ 巡逻的计时边)。没有内部边的模块留空实现。 + void Link(BrainBuilder b); + + /// 图入口(出生态)。 + string Entry { get; } + + /// 脱战 / 警觉丢失后回到的态。必须属于 States。 + string Rest { get; } + + /// 需要挂升级边的所有未发现态。 + IReadOnlyList States { get; } + } +} diff --git a/Assets/_Game/Scripts/Enemies/AIBrain/Modules/IUnawareModule.cs.meta b/Assets/_Game/Scripts/Enemies/AIBrain/Modules/IUnawareModule.cs.meta new file mode 100644 index 00000000..fa7be118 --- /dev/null +++ b/Assets/_Game/Scripts/Enemies/AIBrain/Modules/IUnawareModule.cs.meta @@ -0,0 +1,11 @@ +fileFormatVersion: 2 +guid: bad88c851589dbe4fa0efbb66331e399 +MonoImporter: + externalObjects: {} + serializedVersion: 2 + defaultReferences: [] + executionOrder: 0 + icon: {instanceID: 0} + userData: + assetBundleName: + assetBundleVariant: