• UE——导航系统(NavigationSystem)


    一、基本导航

    1. 构建导航网格
      拖拽NavMeshBoundsVolume到关卡内。

    自动更新导航网格: 在 编辑器设置(Editor Settings)->Level Editor->Miscellaneous-> 启用自动更新导航(Update Navigation Automatically)。


    1. 可视化导航网格
      关卡中找到RecastNavMesh-Default,并在Detail里勾选Draw Poly EdgesDraw Tile Bounds

    Draw Poly Edges: 绘制组成网格的多边形。
    Draw Tile Bounds: 可视化单个Navigation Tiles

    在这里插入图片描述

    二、修改导航网格

    1.使用Navigation Modifier Volumes

    AreaClass应用于导航网格,用于更改体积空间内多边形的属性以修改其通过成本。
    在这里插入图片描述

    Area Class描述
    NavArea_Default默认情况下,将相同的导航成本分配给体积内的区域和导航网格。
    NavArea_LowHeight代表一个区域符合低高度通过条件,防止Agent通过它。导航网格不会在该体积内生成导航数据。
    NavArea_Null表示体积内的空白区域。 导航网格不会在该体积内生成导航数据。
    NavArea_Obstacle为体积内的区域分配高导航成本。如果有通路走通路,没通路才会走这条路

    2.使用Nav Link Proxy

    2.1 连接两个导航区域

    Nav Link Proxy连接导航网格中两个不相连的导航区域。 在搜索路径时,Nav Link Proxy用作Agent到达其目的地的额外连接。指示代理在没有可用的连续导航路径时可以从平台跌落或跳向目标。
    在这里插入图片描述

    Note: 如果 Nav Link Proxy 未与 Navigation Mesh 的表面连接,黑色箭头将消失。(在UE4里是绿色箭头)
    黑色箭头是实际AI的导航路径


    2.2 修改连接方向

    SimpleLink里,可以修改连接方向。
    在这里插入图片描述

    2.3 使用SmartLink

    使用SmartLink,让Agent跳到高处
    在这里插入图片描述
    逻辑:
    在这里插入图片描述
    在这里插入图片描述

    Warning: Nav Link Proxy只能连接相邻的导航网格Tile Bounds。您可以通过选择“WorldOutliner”–>“RecastNavMesh-Default”–>启用“Draw Tile Bounds”来可视化Tile Bounds。


    3 实时生成导航模型

    Generation Mode描述
    Static导航网格离线生成,并与关卡一起保存。 在运行时加载,无法更改。
    Dynamic离线生成并与关卡一起保存或在运行时构建。 在运行时,可以实时更新并生成导航相关数据。
    Dynamic Modifiers Only导航网格是离线生成的,并与关卡一起保存。 在运行时,只有 Navigation Modifiers(如 Navigation Areas、Navigation Links 和动态对象)可以通过更改成本或块区域来修改现有 Navigation Mesh。 运行时不会生成新的导航网格表面。
    这种方法允许导航网格缓存碰撞数据,并且可以使受影响图块的处理成本降低 50%。
    高级用户应在仔细考虑其优点和限制后使用此模式。

    Dynamic Modifiers Only

    设置实时生成方式。项目设置–>NavigationMesh–>Runtime Generation。
    在这里插入图片描述
    只有当Actor拥有NavModifier组件时有效。
    在这里插入图片描述

    注意关卡中没有生成新的导航网格(正在生成的图块显示为红色)。 导航修改器只是更改现有的导航网格。

    示例中,目前同时加RotatingMovement组件有效,单加NavModifier无效,原因未知。


    Dynamic

    设置实时生成方式。项目设置–>NavigationMesh–>Runtime Generation。
    在这里插入图片描述
    在这里插入图片描述

    Note: 强制生成具有高计算成本的导航网格。


    三、自定义导航区域和查询筛选器

    1. 自定义区域类(Nav Area)

    NavModifierVolume拖动到关卡中。创建蓝图继承NavArea,命名为BP_Area_Neutral。打开BP_Area_Neutral,修改默认成本乘数和固定区域输入成本。选择颜色,编译并保存。
    将创建好的NavArea添加到NavModifierVolume中的AreaClass里。
    在这里插入图片描述


    2. 创建导航查询筛选器(Navigation Query Filter)

    创建蓝图继承NavigationQueryFilter,命名为BP_QueryFilter1。打开BP_QueryFilter1,添加并修改Areas数组,加入上一步创建的AreaClass,重写通过成本,
    在这里插入图片描述

    由于BP_QueryFilter1 BP_Area_Lane2是最便宜的路线,因此Agent使用它来到达球体。
    在这里插入图片描述

    四、在导航系统中使用回避

    方法描述局限性
    Reciprocal Velocity Obstacles (RVO)
    相互速度障碍
    - 代理通过在指定半径内使用速度矢量来避开障碍物。
    -包含在角色类的角色移动组件中。
    - 与绕行人群管理器相比,配置较少。
    - 仅限于角色类。
    - 不使用导航网格进行回避,因此代理可能会“越界”。
    Detour Crowd Manager
    人群绕行
    - 代理通过使用路径优化以及指定半径内的速度矢量来避开障碍物。
    - 包含在绕道拥挤的AI控制器类中
    具有在项目设置中定义的固定最大代理数。

    1. 使用RVO避免(Reciprocal Velocity Obstacles)

    打开角色蓝图,选择Character Movement Component,导航到“角色移动:回避”部分,启用“UseRVOAvoidance”复选框,并将“回避考虑半径”设置为 100。
    在这里插入图片描述
    效果如下
    在这里插入图片描述


    2. 使用人群绕行避免(Detour Crowd Manager)

    打开角色蓝图,将AIController替换为Detour Crowd AI Controller,运行即可。
    也可以调整绕行人群管理器系统的多个设置,例如系统使用的最大代理数和用于避免计算的最大代理半径。
    在这里插入图片描述

    五、使用Navigation Invokers

    概述

    • 这是一种仅围绕特定目标本地构建导航的方法。
      在Actor上添加Navigation Invoker组件,用于在运行时围绕代理生成导航网格。此方法不再需要在编辑器中构建导航网格,还可以限制在运行时生成的切片数。

    非常适合在编辑器中构建导航网格不切实际的大型关卡


    设置

    1. 向关卡中拖入导航网格。
    2. 项目设置–>NavigationSystem—>启用 Generate Navigation Only Around Navigation Invokers
    3. 项目设置–>NavigationMesh—>Runtime Generation—>Dynamic。
      在这里插入图片描述
      4.添加组件Navigation Invoker。打开细节面板,根据需求更改切片生成半径(用于生成导航网格切片的参与者周围的半径)和切片删除半径(用于删除导航网格切片的参与者的半径)。
      在这里插入图片描述
      效果如下:
      在这里插入图片描述

    六、优化导航网格生成速度

    Note: 最新版本可在引擎中找到。目录如下:Engine\Source\Runtime\NavigationSystem\DevDocs\How To Optimize Navmesh Generation.md

    导航系统提供了各种设置,高级用户可以使用这些设置来修改关卡中导航的计算方式。


    1. 建议

    1.1 尽可能使用最高Cell Size和Cell Height

    Cell SizeCell Height定义了用于生成导航切片的体素大小(Cells)。体素越小,获得的精度就越高,障碍物周围的导航就越准确。但是,体素越小,在运行时重新构建导航网格时需要的处理就越多。

    Cell Size=19
    在这里插入图片描述

    Cell Size=64在这里插入图片描述

    因此,在Agent所需的精度下,CellSize尽可能调大。


    1.2 限制Tile Size

    导航网格分为多个tiles,由于每个tiles都是从cells构建的,因此重新构建导航tiles将导致使用新的碰撞信息重新创建其所有cells。
    较大的tiles包含更多的cells,重建成本高于较小的tiles。但是,在处理tiles时,系统还会处理其边缘上的连续cells。在设置切片大小时,应考虑此开销成本,因为在某些情况下,处理许多较小tiles的开销成本可能大于重建单个大型tiles的成本。

    建议:tiles大小应设置为每侧 32128 个cells之间。这将在运行时重建tiles时提供最佳性能。
    即Cell Size=64时,TileSizeUU>2048 (6432),且TileSizeUU<8192 (64128)。
    在这里插入图片描述


    1.3 对网格使用简化碰撞

    导航系统使用每个对象的碰撞数据来生成导航网格。
    因此, 碰撞网格中使用的三角形计数越低,生成速度就越快。

    1.4 减少影响导航网格的对象数

    默认情况下,关卡中的蓝图Actor和静态网格体会影响导航。影响导航tiles的对象数对生成该tiles的成本有直接影响。
    因此, 选择任何不应影响导航网格的Actor,在细节面板中,禁用Can Ever Affect Navigation
    如果可能,应避免同时影响大型tiles区域或多个tiles。

    2. 用于管理导航生成的有用开发人员工具

    在战略时期锁定和解锁导航网格生成
    可以手动控制在所有资源完成加载后解锁导航网格生成。此方法可防止导航系统多次重建同一tiles。

    • 锁定导航网格生成,设置bInitialBuildingLocked=true;
    • 解锁生成,调用ReleaseInitialBuildingLock()。解锁后,导航网格将重建所有被加载的资源标记为脏的tiles。
    • 为了防止这种情况,可以在解锁之前,调用DefaultDirtyAreasController.Reset()。

    启用多线程导航网格生成
    您可以通过在"项目设置"–>NavigationSystem中的MaxSimultaneousTileGenerationJobsCount来控制多线程导航网格的生成。请注意,这受到 FRecastNavMeshGenerator::Init()中工作线程总数的限制。

    将动态障碍物与全动态导航网格生成结合使用
    您可以将关卡中的Actor标记为动态障碍物,Actor需要有Collision组件。动态障碍物标记需要重建生成的导航网格表面。这可以防止重新生成整个导航tiles。

    使用此方法比生成完整的导航tiles成本更低,当移动障碍物顶部不需要导航网格表面时,应使用此方法。
    在这里插入图片描述

    用法猜测,当Actor顶部有导航网格,却不想用时,添加Collision组件,将AreaClass改成NavArea_Null,再启用DynamicObstacle。这样Actor顶部的导航网格就去掉了。


    将数据块流用于在子关卡中加载的静态导航网格体
    如果对导航网格体的唯一更改来自加载和卸载子关卡,则可以将导航网格体生成方法设置为静态并使用 NavMesh 数据块流式处理,而不是使用动态导航网格体。

    使用此方法,导航网格将在编辑器中完全构建,并且只有相关部分将在运行时loaded in and out。

    七、世界分区静态导航网格体

    世界分区静态导航网格体(官方链接)

  • 相关阅读:
    餐饮行业软文怎么写吸引人?怎么打动人心
    隐藏idea中的文件
    PGL图学习之图神经网络GNN模型GCN、GAT[系列六]
    点分治学习笔记 / 洛谷 P3806【点分治】
    C++程序结束
    python运算函数
    python+java+springboot快递物流之家管理系统
    CSS进阶语法
    智能算力方向分析
    第一届全国高校将计算机技能大赛知识点整理
  • 原文地址:https://blog.csdn.net/linglongbayinhe/article/details/126877979