欢迎光临散文网 会员登陆 & 注册

斯坦福UE4C++课程P42-P45自定义任务和EQS的中级AI

2022-11-03 20:01 作者:_Hide-on-bush_  | 我要投稿

这一章我们

  • 在C++中给行为树添加范围攻击Task

  • 在行为树中创建攻击行为

  • 用EQS让AI前往接近玩家的地点(不是正好是玩家的位置)

    • EQS Query:找到TargetActor周围位置,让AI走的最短距离,并且包含对TargetActor的line-of-sight

    • 学会使用Gameplay Debugger,Visual Logger(记录了AI行为,并反映到编辑器viewboard)

  • 添加PawnSensing(主要是视觉sight上的感知,替代用TargetActor来追寻玩家)

首先我们添加一个BTTask继承的C++类SBTTask_RangedAttack,包含范围内攻击角色的逻辑

然后把它添加到行为树中。

现在AI首先看玩家是否在攻击范围内,如果在,先cooldown5秒,然后发起RangedAttack任务。

我们接下来修改行为树如下:

within attack range节点设置低优先级观察者中止。因为如果设置观察者中止为None,AI若判断玩家在范围外,将走到范围上,且还需要等5秒才攻击,这很怪异,所以设置该节点为低优先级观察者中止,表示一旦AI判断玩家在范围内,将立即执行自己及子节点。

我们还设置了让AI看向玩家的Focus的service(右键add service,选focus)。

现在如果我们多加几个AI,它们可能会堆成一列,这降低了游戏难度。

我们学习使用环境查询EQS来改进AI的运动,让其更智能。

我们首先新建一个EnvQueryContext_BlueprintBase继承的蓝图类QueryContext_TargetActor

重载Provide Single Actor函数:

表示我们会获取到AI黑板的TargetActor,把它作为返回值。

内容浏览器右键选择Environment Query命名为Query_FindNearbyLocation,弹出的界面和行为树差不多。从root拖出donut节点,右键点击该节点,添加distance的test,filter type选最小值,最小值定为500,(把donut节点的center选为刚新建的EnvQueryContext_BlueprintBase类)表示让AI随机找的位置范围最小为500。

在AI行为树添加EQS节点:

现在AI发现玩家在攻击范围外时,将找到玩家位置以500为下限的范围的点(而非径直前往玩家所在位置),并前往该点。

tip:我们可以打开VisualLogger,来看之前一段时间发生的事情(window->developer tool下)

接下来我们给AI添加PawnSensing(不同于AI Perception,比AI Perception老)

在AICharacter类中:

.h文件添加

.cpp文件:

现在在蓝图中打开AI角色蓝图,多了PawnSensing组件,可以看到许多关于AI感知的内容。调整Peripheral Vision Angle为45°,缩小AI视锥。我们发现视锥在AI头上方,所以选中左侧self,调整Base Eye Height为40,让视锥下移到模型眼睛位置。

另外,我们之前做的是让AI获取到TargetActor,前往TargetActor周围的点;但现在没有看见玩家之前,TargetActor一直为空。而QueryContext蓝图在Cast失败时直接返回空节点,这导致AI无法触发OnSeePawn事件,我们直接简单地添加GetPlayerPawn即可,让AI始终能够获取到TargetActor:

最后我们改进一下AI动画和C++资产。

AI动画有两个问题:没有旋转动画(瞬间转向)、从wait到移动的动画混合过程AI有一段滑动过程。

勾选AI角色移动组件的:

取消勾选Self->Pawn下的:

表示我们使用移动组件的Rotation Rate(每秒):

现在AI一秒可绕Z轴旋转360°。

下面牵扯到动画蓝图的混合空间Blend Space概念。

我们打开AI角色使用的动画蓝图,包含事件图表Event Graph和动画图表Anim Graph,我们打开后者,找到IdleToRun节点,双击打开混合空间。移动下方的绿色点可以查看二维混合空间下的任一点的运动状态动画。

我们可以通过调节左侧Target Weight Interpolation Speed Per Sec的大小来控制一个点到另一个点的过渡速率,从1改成8,过渡就快8倍。

速率为1时有个滑行过程:

速率为8时正常:

最后我们在AIControllerC++类的BeginPlay函数中添加:

确保行为树不空。现在我们在AI控制器蓝图设置行为树为空,运行游戏发现输出日志中有报错信息。

斯坦福UE4C++课程P42-P45自定义任务和EQS的中级AI的评论 (共 条)

分享到微博请遵守国家法律