【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)

文章目录

      • 一、前言
      • 二、插件下载
        • 1、AssetStore下载
        • 2、GitCode下载
      • 三、官方教程
        • 1、在线文档
        • 2、离线文档
      • 四、插件界面
        • 1、打开编辑器
        • 2、界面介绍
      • 五、快速制作一棵行为树
        • 1、创建物体
        • 2、挂BehaviorTree脚本
        • 3、添加Task节点
        • 4、运行测试
        • 5、导出BehaviorTree
        • 6、手动引用BehaviorTree树资源
          • 6.1、设置External Behavior
          • 6.2、使用Behavior Tree Reference
        • 7、动态加载行为树资源并设置External Behavior
      • 六、复合节点:Composities
        • 1、Sequence:顺序节点
          • 1.1、节点介绍
          • 1.2、新发口诀
          • 1.3、案例1:通知开饭了
          • 1.4、案例2:吃几口饭吃一口菜
        • 2、Parallel:并行节点
          • 2.1、节点介绍
          • 2.2、新发口诀
          • 2.3、案例:边跑步边听歌
        • 3、Selector:选择节点
          • 3.1、节点介绍
          • 3.2、新发口诀
          • 3.3、案例:诈骗举报概率
        • 4、Parallel Selector:并行选择节点
          • 4.1、节点介绍
          • 4.2、新发口诀
          • 4.3、案例:考研和找工作
        • 5、Priority Selector:优先级选择节点
          • 5.1、节点介绍
          • 5.2、新发口诀
          • 5.3、案例:先吵架还是先道歉
        • 6、Random Selector:随机选择节点
          • 6.1、节点介绍
          • 6.2、新发口诀
          • 6.3、案例:吃米饭、面条、饺子
        • 7、Random Sequence:随机顺序节点
          • 7.1、节点介绍
          • 7.2、新发口诀
          • 7.3、案例:番茄炒蛋
        • 8、Parallel Complete:并行竞争节点
          • 8.1、节点介绍
          • 8.2、新发口诀
        • 9、Selector Evaluator:评估选择节点
          • 9.1、节点介绍
          • 9.2、新发口诀
      • 七、中断
        • 1、Self中断:老妈喊你回家吃饭
        • 2、Lower Priority中断:睡觉时地震
        • 3、Both中断:两者都中断
      • 八、Variables:行为树成员变量
        • 1、添加变量
        • 2、读取变量
        • 3、修改变量
        • 4、拓展变量类型
        • 5、代码读写变量
      • 九、行为树事件
          • 1、Send Event节点
            • 1.1、Target Game Object参数
            • 1.2、Event Name参数
            • 1.3、Group参数
            • 1.4、Argument参数
          • 2、Has Receive Event节点
            • 2.1、Event Name参数
            • 2.2、Stored Value参数
          • 3、代码中注册和注销事件
      • 十、拓展行为树节点
        • 1、继承
        • 2、案例:MoveTo
        • 3、官方Sample包
      • 十一、完毕

一、前言

嗨,大家好,我是新发。之前用过Behavior Designer行为树插件,最近又需要用到,我发现网上的教程很多写得不够好,今天我就来写写Behavior Designer行为树的教程吧,希望可以帮到大家。

二、插件下载

1、AssetStore下载

插件可以在AssetStore下载到,
地址:https://assetstore.unity.com/packages/tools/visual-scripting/behavior-designer-behavior-trees-for-everyone-15277
在这里插入图片描述
目前最新的版本是1.7.2
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第1张图片
可以在官网查看每个版本的迭代内容:
https://opsive.com/news/category/release-notes/behavior-designer-release-notes/
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第2张图片

2、GitCode下载

我放了1.7.1版本的到GitCode上,地址:https://gitcode.net/linxinfa/unitybehaviordesigner
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第3张图片

下载下来后,放入你的工程即可,
在这里插入图片描述

其中我加了一个FixGUIStyle脚本,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第4张图片

因为在Unity专业版上,打开Behavior Designer编辑器是这个鬼样,

注:如果你使用的是个人版,则不会有这个问题

【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第5张图片

它的GUIStyleUnity专业版本有问题,插件编辑器是个dll文件,我们无法修改编辑器源码,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第6张图片

然后我进行了反编译,找到了它的封装各种GUIStyle的类:BehaviorDesignerUtility
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第7张图片
通过反射,修改这个类的私有静态成员对象,代码如下:

using UnityEngine;
using UnityEditor;
using System.Reflection;
using BehaviorDesigner.Editor;


/// 
/// 修复BehaviorDesigner编辑器的GUIStyle问题
/// 
public class FixGUIStyle
{

    [MenuItem("Tools/Behavior Designer/修复界面GUIStyle #b", false, 0)]
    [RuntimeInitializeOnLoadMethod(RuntimeInitializeLoadType.BeforeSceneLoad)]
    public static void ShowWindow()
    {

        var guiStyle = new GUIStyle();
        guiStyle.alignment = TextAnchor.UpperCenter;
        guiStyle.fontSize = 12;
        guiStyle.wordWrap = true;
        guiStyle.normal.textColor = Color.white;
        guiStyle.active.textColor = Color.white;
        guiStyle.hover.textColor = Color.white;
        guiStyle.focused.textColor = Color.white;

        Texture2D tex2D = new Texture2D(1, 1, TextureFormat.RGB24, false);
        tex2D.SetPixel(1, 1, new Color(0.1f, 0.1f, 0.1f, 1f));
        tex2D.hideFlags = HideFlags.HideAndDontSave;
        tex2D.Apply();
        guiStyle.normal.background = tex2D;

        // 反射动态修改私有静态成员,修改GUIStyle
        var t = typeof(BehaviorDesignerUtility);
        var graphBackgroundGUIStyle = t.GetField("graphBackgroundGUIStyle", BindingFlags.Static | BindingFlags.NonPublic);
        graphBackgroundGUIStyle.SetValue(null, guiStyle);


        var taskCommentGUIStyle = t.GetField("taskCommentGUIStyle", BindingFlags.Static | BindingFlags.NonPublic);
        taskCommentGUIStyle.SetValue(null, guiStyle);


        var selectedBackgroundGUIStyle = t.GetField("selectedBackgroundGUIStyle", BindingFlags.Static | BindingFlags.NonPublic);
        selectedBackgroundGUIStyle.SetValue(null, guiStyle);


        var preferencesPaneGUIStyle = t.GetField("preferencesPaneGUIStyle", BindingFlags.Static | BindingFlags.NonPublic);
        preferencesPaneGUIStyle.SetValue(null, guiStyle);

    }
}

点击菜单Tools/Behavior Designer/修复界面GUIStyle,或者按一下Shift+B快捷键,即可修复GUIStyle问题,

【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第8张图片

效果如下
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第9张图片

三、官方教程

学习插件的时候,建议先看下官方文档。

1、在线文档

官方在线文档: https://opsive.com/support/documentation/behavior-designer/overview/
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第10张图片

2、离线文档

插件的Behavior Designer目录中有个Documentation.pdf文档,不过可能很多同学都没去看这份文档,建议还是看一看,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第11张图片

四、插件界面

1、打开编辑器

点击菜单Tools/Behavior Designer/Editor即可打开编辑器窗口,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第12张图片

如下
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第13张图片

2、界面介绍

界面可以划分为3个区域,如下
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第14张图片

1个区域是行为树的组织区域,我们的行为树节点就是在这个区域上进行连线的;
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第15张图片

2个区域顶部是四个标签页:BehaviorTasksVariablesInspector,默认是Tasks标签页,显示的是节点列表;
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第16张图片

标签页 说明
Behavior 对整个行为树的设置,比如行为树名称、是否激活时立即执行、执行完毕后是否重新执行等设置
Tasks 任务节点列表,比如Composities(符合节点)、Decorators(装饰节点)、Actions(行为节点)等等
Variables 行为树变量,可以设置全局变量,也可以设置行为树自身的变量
Inspector 查看节点详细信息,设置节点参数

3个区域按钮功能如下
在这里插入图片描述

【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第17张图片

五、快速制作一棵行为树

在讲解节点之前,我先演示一遍如何快速制作一棵行为树,让大家对整个流程有个概念。

1、创建物体

首先在场景中创建一个物体,可以是任何物体,比如你想控制角色,那么这个物体就可以是你的角色模型,这里我创建一个空物体,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第18张图片

重命名为BehaviorTreeObj
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第19张图片

2、挂BehaviorTree脚本

打开Behavior Designer编辑器,先选中刚刚的BehaviorTreeObj物体,然后在编辑器网格空白处右键鼠标,点击菜单Add Behavior Tree
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第20张图片

这一步其实就是给物体挂上BehaviorTree组件,我们也可以通过Add Component手动添加BehaviorTree组件,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第21张图片

3、添加Task节点

我以最简单的Log节点为例,它的功能就是输出日志,在空白处点击鼠标左键,按键盘的空格键即可弹出节点搜索框,搜索log,可以看到Log节点,点击即可创建出Log任务节点,它会自动帮我添加一个Entry入口节点,Entry连向Log,如下
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第22张图片

我们给Log节点设置Text字段的值为Hello World,并添加注释,如下
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第23张图片

4、运行测试

运行Unity,可以看到Log节点被执行了,显示了一个绿色的勾,日志窗口也输出了HelloWorld
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第24张图片

5、导出BehaviorTree

点击Export按钮,将行为树导出保存为资源文件,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第25张图片

如下,这样子就可以复用行为树资源了,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第26张图片

6、手动引用BehaviorTree树资源

6.1、设置External Behavior

我们把上面导出的行为树资源赋值给BehaviorTree组件的External Behavior成员,如下
在这里插入图片描述
运行时,就会根据这个External Behavior的行为树来执行了。

6.2、使用Behavior Tree Reference

另外,我们还可以通过Behavior Tree Reference节点来引用行为树资源,
先创建一个Behavior Tree Reference节点,点击Inspector,设置它引用的外部行为树资源即可,
在这里插入图片描述

一般我们会做一个通用的行为树保存为资源文件,然后对特殊的怪物另外做行为树,并让其引用通用行为树资源,像这样子
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第27张图片

7、动态加载行为树资源并设置External Behavior

我们也可以通过代码动态设置External Behavior,我这里使用Addressables插件来做资源加载,

注:关于Addressables的使用,可以参见我之前写的这篇文章:【游戏开发探究】Unity Addressables资源管理方式用起来太爽了,资源打包、加载、热更变得如此轻松(Addressable Asset System | 简称AA)

首先给行为树资源文件添加Addressable管理,分配到一个Addressable索引名,如下

注:勾上Addressable就会自动分配一个索引名了

【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第28张图片

接着我们可以使用代码加载行为树资源,动态赋值给BehaviorTree组件的ExternalBehavior 对象,
创建一个AddBehaviorTree.cs脚本,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第29张图片

代码如下

using System.Collections;
using UnityEngine;
using BehaviorDesigner.Runtime;
using UnityEngine.AddressableAssets;

public class AddBehaviorTree : MonoBehaviour
{
    IEnumerator Start()
    {
        // 初始化Addressables
        yield return Addressables.InitializeAsync();
        // 添加BehaviorTree
        var bt = gameObject.AddComponent<BehaviorTree>();
        // 设置不立即执行
        bt.StartWhenEnabled = false;
        // 加载行为树资源
        var loader = Addressables.LoadAssetAsync<ExternalBehaviorTree>("Assets/BtRes/Behavior.asset");
        yield return loader;
        // 设置ExternalBehavior
        bt.ExternalBehavior = loader.Result;
        // 执行行为树
        bt.EnableBehavior();
    }
}

我们创建一个空物体,重命名BtObj,并给它挂上AddBehaviorTree脚本,如下
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第30张图片

我们运行Unity,可以看到BtObj物体动态挂了BehaviorTree组件,并且动态设置了ExternalBehavior对象,行为树也被执行了,输出了Hello World,如下
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第31张图片

我们可以点击BehaviorTree组件上的Open按钮,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第32张图片

可以看到行为树已经执行完毕,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第33张图片

如果我们想让行为树执行完毕后重复执行,可以设置RestartWhenCompletetrue
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第34张图片

我们串一个Wait节点,方便观察,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第35张图片

执行效果如下,可以看到行为树可以重复执行了,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第36张图片

上面我们用到了Squence顺序节点,它是一个复合节点,下文我会进行节点的详细介绍。

六、复合节点:Composities

行为树任务节点中最重要的节点就是复合节点了,它决定了行为树的执行流,也就是Tasks列表中Composities分组的这些节点,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第37张图片
我先简单做个日常生活的行为树给大家看看,如下
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第38张图片

上面的行为树的执行过程是怎么样的呢?想要搞清楚就得先知道行为树的执行顺序:从左到右,并且深度优先
另外,复合节点又控制着子节点的执行规则,是顺序执行还是并行执行,亦或者随机执行,是遇到成功就立即返回成功还是遇到失败就立即返回失败,亦或者遇到成功继续执行下一个,或者遇到失败继续执行下一个呢?
这些都是复合节点来控制的,这里头的逻辑需要大家好好琢磨,下面我带大家挨个过一遍复合节点,讲解过程中我会穿插顺带讲解一下用到的其他任务节点,并举一些实际的应用场景,方便大家学以致用,也希望大家能够触类旁通。

1、Sequence:顺序节点

1.1、节点介绍

在这里插入图片描述

顾名思义,顺序节点就是从左到右挨个顺序执行,当所有子节点都返回Success时,它才返回Success
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第39张图片

当某个子节点返回Failure时,顺序节点就会立刻返回Failure
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第40张图片

1.2、新发口诀

顺序节点,从左到右,为真继续,全真才真,一假即假,一假即停。
类似于逻辑。

1.3、案例1:通知开饭了

我们使用Has Received Event来监听开饭的事件,当它检测收到事件时才会返回Success,此时顺序节点就会去执行下一个子节点,即干饭的逻辑,达到响应事件的功能,如下【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第41张图片

其中Has Received Event节点要设置监听的事件名称,定义一个字符串即可,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第42张图片

抛出事件有两种方式,一种是代码调用行为树的SendEvent接口,如下

public void SendEvent(string name);
public void SendEvent<T>(string name, T arg1);
public void SendEvent<T, U>(string name, T arg1, U arg2);
public void SendEvent<T, U, V>(string name, T arg1, U arg2, V arg3);

示例:

// bt是BehaviorTree对象
bt.SendEvent("EAT_EVENT");

另外一种是使用SendEvent节点,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第43张图片
设置要发送的事件名称即可,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第44张图片

1.4、案例2:吃几口饭吃一口菜

想象一下你吃饭的过程,扒拉吃几口饭,然后吃一口菜,我们可以用顺序节点来组织,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第45张图片

2、Parallel:并行节点

2.1、节点介绍

【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第46张图片

并行节点,顾名思义,它会并行执行所有的子节点,所有的子节点都返回Success,并行节点才会返回Success
请添加图片描述
只要有一个子节点返回Failure,并行节点就会立刻返回Failure。如下图,我们可以看到,等10秒和等20秒的两个节点还没执行完就被停止了,因为中间那个等1秒的节点执行完毕并返回了Failure给并行节点,整个并行以Failure结束,那些被终止的Wait也会直接返回Failure
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第47张图片

2.2、新发口诀

并行节点,并行执行,全真才真,一假即假,一假即停,被停即假。

2.3、案例:边跑步边听歌

比如我们边跑步边听歌,同时还要监听是否有下雨,有下雨的话要中断跑步,如下
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第48张图片
这个例子我用到了Selector节点,并且启用了Self中断,看不懂的同学不要着急,下文我会讲。

3、Selector:选择节点

3.1、节点介绍

在这里插入图片描述
选择节点与顺序节点类似,也是从左到右执行,不同的是,当有子节点返回Success,选择节点就会立刻返回Success不会执行下一个子节点

【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第49张图片

如果子节点返回Failure,会就执行下一个子节点,其实很好理解,就是从左到右遍历选一个Success,有Success就返回Success,否则执行下一个子节点,

【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第50张图片
如果所有子节点都返回Failure,选择节点才返回Failure
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第51张图片

3.2、新发口诀

选择节点,从左到右,一真即真,一真即停,全假才假。

3.3、案例:诈骗举报概率

比如收到诈骗短信后,有99%的概率会执行举报,有1%的概率会上当受骗,如下
在这里插入图片描述

4、Parallel Selector:并行选择节点

4.1、节点介绍

【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第52张图片

顾名思义,就是并行执行选择节点,有一个Success就立即返回Success,并且会终止其他子节点,被终止的子节点会返回Failure,如下
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第53张图片

所有子节点都返回Failure时,并行选择节点才返回Failure

【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第54张图片

4.2、新发口诀

并行选择节点,并行执行,一真即真,一真即停,全假才假。

4.3、案例:考研和找工作

现在人生道路有两条路:考研、找工作,同时进行,其中一件事情成了,就吃一顿好的庆祝一下,如下
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第55张图片

5、Priority Selector:优先级选择节点

5.1、节点介绍

在这里插入图片描述

这个节点和Selector类似,Selector的执行顺序是从左到右,而Priority Selector会先检查子节点的优先级(priority)进行排序,优先级高的优先执行。
问题来了,我们如何设置子节点的优先级呢?节点的优先级默认是0,如果要修改优先级,需要重写TaskGetPriority方法,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第56张图片
这里我封装一个带优先级参数的日志节点吧:PriorityLog,创建一个PriorityLog脚本,代码如下

using UnityEngine;

namespace BehaviorDesigner.Runtime.Tasks
{
    [TaskDescription("带优先级参数的日志节点")]
    [TaskIcon("{SkinColor}LogIcon.png")]
    public class PriorityLog : Action
    {
        [Tooltip("Text to output to the log")]
        public SharedString text;
        [Tooltip("Is this text an error?")]
        public SharedBool logError;
        [Tooltip("Should the time be included in the log message?")]
        public SharedBool logTime;

        [Tooltip("优先级")]
        public SharedFloat priority;

        /// 
        /// 重写获取优先级的方法
        /// 
        /// 
        public override float GetPriority()
        {
            return priority.Value;
        }
        public override TaskStatus OnUpdate()
        {
            // Log the text and return success
            if (logError.Value) {
                Debug.LogError(logTime.Value ? string.Format("{0}: {1}", Time.time, text) : text);
            } else {
                Debug.Log(logTime.Value ? string.Format("{0}: {1}",Time.time, text) : text);
            }
            return TaskStatus.Success;
        }

        public override void OnReset()
        {
            // Reset the properties back to their original values
            text = "";
            logError = false;
            logTime = false;
        }
    }
}

现在我们就可以在Tasks列表中看到我们新封装的PriorityLog节点了,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第57张图片
使用它连个简单的行为树,如下
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第58张图片
我们可以选中节点,在Inspector中设置节点的Priority
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第59张图片
由于右边的节点优先级我们设置为了1,比左边的节点优先级高,所以会优先执行右边的节点,因为右边的节点执行返回了Success,此时Priority Selector就会直接返回Success,不会去执行左边的节点了,如下
请添加图片描述

5.2、新发口诀

优先级选择节点,优先级排序,一真即真,一真即停,全假才假。

5.3、案例:先吵架还是先道歉

我先给行为树创建一Foat类型的变量:SorryPriority,如下
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第60张图片
以它作为道歉优先级变量,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第61张图片
接着制作如下的行为树,当按下A键的时候,设置SorryPriority变量,提高道歉的优先级,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第62张图片
其中Set Shared Float节点的设置如下,让它去修改SorryPriority变量为1

【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第63张图片
道歉节点的Priority参数设置为SorryPriority变量,如下
请添加图片描述
我们运行,如果我没有按下A键,则道歉优先级是02秒情绪酝酿完毕后,会默认先执行吵架,

【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第64张图片
如果我在2秒情绪酝酿期间按下了A键,则会设置道歉优先级变量为1,情绪酝酿完毕后就会优先执行道歉,就不会吵架了,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第65张图片

6、Random Selector:随机选择节点

6.1、节点介绍

【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第66张图片

这个很好理解,按选择节点的规则,只是不是从左到右执行,而是随机顺序执行。
如果有子节点返回Success,则立即返回Success,否则继续执行下一个节点,

请添加图片描述
只有所有的子节点都返回Failure时,Random Selector才返回Failure

【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第67张图片

6.2、新发口诀

随机选择节点,随机执行,一真即真,一真即停,全假才假。

6.3、案例:吃米饭、面条、饺子

中午吃什么好呢?随机选一个吧,好的,吃面条~
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第68张图片

7、Random Sequence:随机顺序节点

7.1、节点介绍

在这里插入图片描述

这个也很好理解,就是顺序节点的规则,但不是从左到右执行,而是随机顺序执行。

当所有子节点都返回Success时,它才返回Success
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第69张图片

当某个子节点返回Failure时,顺序节点就会立刻返回Failure
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第70张图片

7.2、新发口诀

随机顺序节点,随机顺序,为真继续,全真才真,一假即假,一假即停。

7.3、案例:番茄炒蛋

我现在要做一道番茄炒蛋,有的人先炒番茄,有的人先炒鸡蛋,这里我们就可以使用随机顺序节点了,如果炒鸡蛋或者炒番茄失败,那么我们就吃不到番茄炒蛋了,只有两个都成功了,才能吃到番茄炒蛋,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第71张图片

8、Parallel Complete:并行竞争节点

8.1、节点介绍

【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第72张图片
这个节点其实就是并行执行所有的子节点,只要有一个子节点返回了结果,它就结束,并以这个子节点的结果为结果,
请添加图片描述
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第73张图片

8.2、新发口诀

并行竞争节点,并行执行,最速之子,以子为果。

9、Selector Evaluator:评估选择节点

9.1、节点介绍

【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第74张图片
这个节点不是很好理解,它的逻辑是这样的,从左到右顺序执行,如果遇到子节点返回Success,则立即结束,并返回Success,否则继续执行下一个子节点。

【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第75张图片
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第76张图片
有同学会问了,那它与Selector节点有啥区别?
上面我用的是Log节点,会立即返回结果,如果是用Wait节点,则会有Running状态,这个Selector Evaluator节点是个固执的强迫症节点,它认为子节点应该给它返回Success,如果子节点返回了Failure,它会硬着头皮执行下一子节点,但是,一旦下一个子节点处于Running状态,它就会像个渣男一样毫不犹豫地打断并返回第一个子节点,重新执行,只要有机会它就想要一个Success结果,如果后续的子节点都是立即返回成功或失败,而没有Running状态,则它会接受后续子节点的Success,也就是说,它也不是非得第一个子节点不娶,后面的子节点只要立刻Success,它就不打断去重新找第一个子节点了,相当地渣男啊!

看,第二任只要考虑一下(Running状态),它就会立即打断回去执行初恋,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第77张图片
如果第二任立即答应了,它就会接受第二任的结果,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第78张图片
如果第二任直接给个Failure,那么这个渣男会去骚扰路人甲,如果路人甲给它Success,它就会爱上路人甲,

【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第79张图片
如果路人甲立即给它Failure,这个渣男才会死心,
请添加图片描述

9.2、新发口诀

评估选择节点,渣男一个,从左到右,遇真即真,遇假继续,Runing时机打断,从头来过。

七、中断

复合节点有中断的权利,我们可以选中某个复合节点,然后点击Inspector,设置它的中断模式,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第80张图片
默认为None,即无中断,另外三个中断模式,下文我会挨个进行演示。
这里我先解释一下什么是中断,比如你正在睡觉,突然地震了,这个时候睡觉就要被中断,执行逃跑的逻辑,命要紧。
复合节点的中断控制是由谁来调度的呢?细心的同学应该会发现,执行行为树的时候,会自动创建一个Behavior Manager对象,上面挂着BehaviorManager脚本,我们的行为树的执行都是由这个BehaviorManager来调度的,它就是最高司令,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第81张图片
感兴趣的同学可以反编译BehaviorDesigner.Runtime.dll,查看BehaviorManager的源码,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第82张图片

1、Self中断:老妈喊你回家吃饭

一个复合节点下可以有多个子节点,假设现在有两个子节点,假设此时正在执行第二个子节点(Running状态),突然来了一个事件,需要中断第二个子节点,立即执行第一个子节点,这里就可以使用Self中断,Self其实是站在复合节点的角度的,就是中断复合节点自己。

假设你去朋友家打游戏,你决定打完游戏就回家,如果打游戏过程中,老妈打电话喊你回家吃饭,那么就中断打游戏,回家。

行为树如下
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第83张图片

没有按下A键的执行效果如下,打完游戏开开心心回家,

【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第84张图片
打游戏过程中,按下A键,中断打游戏,回家,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第85张图片

2、Lower Priority中断:睡觉时地震

我们以睡觉的时候发生地震为例,演示一下Lower Priority中断。
睡觉的时候如果发生地震,需要中断睡觉,执行逃命逻辑。
如下,睡觉节点与Sequence节点是平级关系,并且睡觉节点在右边,属于低优先级,当正在执行睡觉节点时,左边的Sequence节点想要中断右边的睡觉节点,设置Lower Priority中断即可,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第86张图片
我们从中断的图标也可以看出,它指向右边,表示中断右边的节点的意思,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第87张图片

3、Both中断:两者都中断

Both中断其实就是SelfLower Priority都中断。如下
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第88张图片

八、Variables:行为树成员变量

我们点击Variables,可以给行为树添加成员变量,也可以查看已添加的成员变量,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第89张图片

1、添加变量

先起一个变量名,然后选择变量的数据类型,我们也可以添加自定义的数据类型,需要进行变量类型拓展,下文会讲解拓展变量类型的步骤,这里我们先选一个String好了,最后点击Add按钮即可,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第90张图片
我们可以修改变量名,给变量设置初始值,如下
在这里插入图片描述

2、读取变量

现在我们想通过Log节点把myName这个变量输出出来。
先选中Log节点,切到Inspector页,点击Text值最右边的小点点,如下
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第91张图片
此时会出现红色的感叹号
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第92张图片
我们点击下拉框,选中myName变量即可,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第93张图片
我们运行行为树,可以看到日志输出了变量值,如下
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第94张图片

3、修改变量

我们在Log节点左边串一个Set String节点,

注:如果你的变量类型是Bool,则这里要使用Set Bool节点,其他类型同理,选择对应的Set节点,如果是自定义的数据类型,则要自己拓展一个Set变量值的节点才行。

【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第95张图片
此时带有一个红色感叹号,我们需要给它设置要修改的变量,如下
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第96张图片
我们运行行为树,可以看到输出的变量值是皮皮猫了,
在这里插入图片描述

4、拓展变量类型

实际项目中,我们大概率是要拓展行为树的变量类型的,比如我现在有个Blog类,

/// 
/// 博客
/// 
public class Blog
{
    /// 
    /// 作者
    /// 
    public string author;
    
    /// 
    /// 博客地址
    /// 
    public string url;

    public override string ToString()
    {
        return $"author: {author}, url: {url}";
    }
}

我想让他出现行为树Variables的变量类型列表中,我们需要给它包装一层SharedBlog
新建一个SharedBlog脚本,
在这里插入图片描述
按照下面这个格式写即可:

namespace BehaviorDesigner.Runtime
{
    [System.Serializable]
    public class SharedT : SharedVariable<T>
    {
        public static implicit operator SharedT(T value)
        {
            return new SharedT { mValue = value };
        }
    }
}

SharedBlog代码如下:


namespace BehaviorDesigner.Runtime
{
    [System.Serializable]
    public class SharedBlog : SharedVariable<Blog>
    {
        public static implicit operator SharedBlog(Blog value)
        {
            return new SharedBlog { mValue = value };
        }
    }
}

此时,我们就可以在变量类型列表中看到我们拓展的Blog变量类型了,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第97张图片
我们给行为树添加一个Blog变量吧,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第98张图片

5、代码读写变量

上面我们拓展了一个Blog变量类型,并给行为树添加了一个Blog变量,现在我们想在代码中对这个变量进行访问和修改,我们可以通过BehaviorTreeGetVariable方法和SetVariable方法,

public SharedVariable GetVariable(string name);
public void SetVariable(string name, SharedVariable item);

例:

// 获取行为树对象
var bt = GetComponent<BehaviorTree>();

// 访问成员变量-----------------------------------------
var sharedBlog = (SharedBlog)bt.GetVariable("myBlog");
Debug.Log(sharedBlog.Value.ToString());

// 修改变量值-----------------------------------------
sharedBlog.Value.author = "Unity3D技术博主:林新发";
bt.SetVariable("myBlog", sharedBlog);


// 构建新的成员对象-----------------------------------------
SharedBlog newSharedBlog  = new SharedBlog();
Blog newBlog = new Blog();
newBlog.author = "博客技术专家:林新发";
newBlog.url = "https://blog.csdn.net/linxinfa";
newSharedBlog.SetValue(newBlog);
// 赋值成员变量
bt.SetVariable("myBlog", newSharedBlog);

九、行为树事件

上文讲Sequence节点的时候已经举例讲了行为树事件,不过有些细节没有讲到,这里我进行补充。
与事件相关的节点是Send EventHas Received Event
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第99张图片
另外,我们也可以通过代码来发出事件和监听事件,下面给大家演示一遍。

1、Send Event节点

我们首先看Send Event节点,可以在Inspector面板看到它的参数,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第100张图片

1.1、Target Game Object参数

行为树之间的事件是可以跨物体发送的,比如A物体上的行为树给B物体上的行为树发送事件。
默认为None,事件会发给自身的行为树。
我们可以查看SendEvent节点的源码,它调用了GetDefaultGameObject方法去获取目标物体,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第101张图片
这个方法的源码如下:
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第102张图片
意思就是如果为空,就返回自身的gameObject,也就是行为树自身的物体。
如果我们想要设置这个SendEvent节点的Target Game Object参数,可以通过行为树变量来传递,比如在Variables中定义一个targetObj
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第103张图片
然后SendEventTarget Game Object引用这个targetObj变量,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第104张图片
而这个targetObj变量的赋值,我们可以通过代码来赋值,例:

// go是目标物体GameObject对象,bt是自身行为树对象
SharedGameObject targetObj = new SharedGameObject();
targetObj.Value = go;
bt.SetVariable("targetObj", targetObj);
1.2、Event Name参数

Event Name就是事件名称,自己定义一个字符串即可,建议为XXX_EVENT

1.3、Group参数

【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第105张图片
这个Group参数又是干啥用的呢?因为一个物体可以挂多个BehaviorTree组件,假设挂了3BehaviorTree组件,我只想给其中的两个BehaviorTree发送事件,这个时候就要用到Group了。
我们可以在BehaviorTree组件上看到有一个Group参数,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第106张图片
我们可以给这些BehaviorTree分组,默认Group0
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第107张图片
如果SendEventGroup也是0,那么这个物体下所有Group0BehaviorTree都会收到事件。

1.4、Argument参数

在这里插入图片描述
我们可以看到有三个Argument参数,一般是用来做跨行为树发送事件时的数据传递用的。
比如A打了BB收到被打事件,但它并不知道是谁打它的,我们可以给它们定义一个playerId成员变量,

注:这里你使用GameObject变量也可以,看具体需要~

【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第108张图片
发事件的时候把playerId传递过去,B在收到事件后会去读取这个参数,B就知道是A打了它了,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第109张图片

2、Has Receive Event节点

Has Receive Event节点参数如下,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第110张图片

2.1、Event Name参数

Event Name参数就是要监听的事件名称,与SendEventEvent Name要对应上。

2.2、Stored Value参数

Stored Value参数用来存储传递过来的数据的,与Send Event的三个Argument顺序对应。注意,这里是把传递过来的参数存储到Stored Value设置的变量中,比如A行为树传递了一个playerId过来,表示打人者的IdB行为树收到事件,把这个plaeyrId存储到fromPlayerId变量中,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第111张图片
然后我们可以在代码中通过B行为树的GetVariable方法读取到这个fromPlayerId

var fromPlayerId = (SharedInt)bt.GetVariable("fromPlayerId");
Debug.Log($"{fromPlayerId} 打了我");
3、代码中注册和注销事件

有时候我们需要在代码中自己注册事件的响应函数,可以调用行为树的RegisterEvent方法,

public void RegisterEvent<T, U, V>(string name, Action<T, U, V> handler);
public void RegisterEvent<T, U>(string name, Action<T, U> handler);
public void RegisterEvent<T>(string name, Action<T> handler);
public void RegisterEvent(string name, System.Action handler);

对应的,要注销事件的响应函数,则调用UnregisterEvent方法,

public void UnregisterEvent<T, U, V>(string name, Action<T, U, V> handler);
public void UnregisterEvent<T, U>(string name, Action<T, U> handler);
public void UnregisterEvent<T>(string name, Action<T> handler);
public void UnregisterEvent(string name, System.Action handler);

可以查阅Has Receive Event节点的源码
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第112张图片

十、拓展行为树节点

1、继承

实际项目开发过程中,我们一般都需要自己拓展一些行为树节点,我们知道,所有的节点都是继承Task的,然后根据节点的功能分类,有细分了一些子类出来,比如复合节点的继承关系如下:
在这里插入图片描述
我们我们想要封装一个新的复合节点,也继承Composite然后进行拓展即可。
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第113张图片

同理,Action类的节点也如此,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第114张图片

我们可以参考Log节点、Wait节点的写法,自行拓展自己的Action节点。

2、案例:MoveTo

举个例子,现在要写一个移动主角到指定Transform位置的Action,首先创建一个MoveTo脚本,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第115张图片
引入BehaviorDesigner的命名空间,然后继承Action

using UnityEngine;
using BehaviorDesigner.Runtime;
using BehaviorDesigner.Runtime.Tasks;

// 移动主角到指定Transform位置
public class MoveTo: Action
{
}

接着定义一些必要的public成员变量,这些变量会在Inspector面板中显示,

using UnityEngine;
using BehaviorDesigner.Runtime;
using BehaviorDesigner.Runtime.Tasks;

// 移动主角到指定Transform位置
public class MoveTo : Action
{
    public float speed = 0;
    public SharedTransform target;

}

再接着,我们重写OnUpdate方法,如下

public override TaskStatus OnUpdate()
{
   if (Vector3.SqrMagnitude(transform.position - target.Value.position) < 0.1f) {
      return TaskStatus.Success;
   }
   transform.position = Vector3.MoveTowards(transform.position, target.Value.position, speed * Time.deltaTime);
   return TaskStatus.Running;
}

这样,我们自己封装的MoveTo节点就完成了,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第116张图片
我们连个行为树,让Cub来回移动,效果如下
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第117张图片

3、官方Sample包

BehaviorDesigner官方自己写了一些拓展包,我们可以把对应的包导入项目中使用,
【游戏开发教程】BehaviorDesigner插件制作AI行为树(Unity | 保姆级教程 | 动态图演示 | Unity2021最新版)_第118张图片
这里分享给大家,
链接:https://pan.baidu.com/s/1mQUkxbeokOh6oyTmEG837w
提取码:oi74

十一、完毕

好了,就先写到这里吧,我是林新发:https://blog.csdn.net/linxinfa
一个在小公司默默奋斗的Unity开发者,希望可以帮助更多想学Unity的人,共勉~

你可能感兴趣的:(Unity3D,unity,Behavior,Designer,行为树,插件)