Gameplay对象

先说游戏引擎对象,描述如下
image.png

组件

游戏对象绑定着不同的组件
image.png

产生问题

tick时序问题,并相互存在冲突,为了避免这种发声的存在,利用委托暂存事件tickimage.png

委托定义

是一种泛型但类型安全的方式,可在C++对象上调用成员函数。可使用委托动态绑定到任意对象的成员函数,之后在该对象上调用函数,即使调用程序不知对象类型也可进行操作。复制委托对象很安全。(——Unreal官方文档)
这和C#委托处理有相似之处。
image.png

视频教学

委托的概念和用法

https://www.bilibili.com/video/BV1Ar4y1K7AK?p=13&spm_id_from=333.788.top_right_bar_window_history.content.click

委托•语法篇

https://www.bilibili.com/video/BV1Bk4y1B7DN/?spm_id_from=333.788.recommend_more_video.-1

声明和使用

在C#中声明委托

  1. 修饰符 delegate 返回值类型 委托名 ( 参数列表 );
  1. public delegate void MyDelegate();//例如

在定义好委托后就到了实例化委托的步骤,命名方法委托在实例化委托时必须带入方法的具体名称。
实例化委托的语法形式如下。

  1. 委托名 委托对象名 = new 委托名 ( 方法名 );

委托中传递的方法名既可以是静态方法的名称,也可以是实例方法的名称。
需要注意的是,在委托中所写的方法名必须与委托定义时的返回值类型和参数列表相同。
在实例化委托后即可调用委托,语法形式如下。

  1. 委托对象名 ( 参数列表 );
  1. using System;
  2. class Program
  3. {
  4. public delegate void mydelegate();
  5. static void testfuna()
  6. {
  7. Console.WriteLine("testfuna");
  8. }
  9. static void testfunb()
  10. {
  11. Console.WriteLine("testfunb");
  12. }
  13. static void Main(string[] args)
  14. {
  15. mydelegate mydelegate1 = new mydelegate(testfuna);
  16. mydelegate mydelegate2=new mydelegate(testfunb);
  17. mydelegate1.Invoke();//调用testfuna
  18. mydelegate1 -=mydelegate1;//通过重载运算符灵活调用多波代理
  19. mydelegate1+=mydelegate2;
  20. mydelegate1.Invoke();
  21. }
  22. }

系统库提供的委托类

不用再声明委托,在system库中就声明好了。

  1. Fun<T>//泛型委托,最多支持16个参数
  2. Action//无返回,无参数值委托
  1. using System;
  2. class Program
  3. {
  4. static void testfuna()
  5. {
  6. Console.WriteLine("testfuna");
  7. }
  8. static void testfunb()
  9. {
  10. Console.WriteLine("testfunb");
  11. }
  12. static int testfun() { Console.WriteLine("testfun"); return 0; }
  13. static void Main(string[] args)
  14. {
  15. Action mydelegate3=new Action(testfuna);//直接构造
  16. Func<int> sss= new Func<int>(testfun);//直接构造
  17. }
  18. }

函数指针

和C/C++函数指针语法相似,只是把指针拿掉,换成delegate关键字,这样更好理解委托

image.png

委托和事件分发器

C++中实现委托和事件分发器的实现是等效的,委托能够以一种类型安全的方式调用 Actor蓝图中的方法。委托可以动态绑定,使一个Actor能够触发一个事件,让”监听”该Actor的其他Actor监听事件。
官方参考:https://docs.unrealengine.com/4.27/zh-CN/ProgrammingAndScripting/ProgrammingWithCPP/UnrealArchitecture/Delegates/
https://docs.unrealengine.com/4.27/zh-CN/ProgrammingAndScripting/ActorCommunication/EventDispatcherQuickStart/
UE4代理(委托)概览:https://zhuanlan.zhihu.com/p/419232568
UE4案例进屋同时开灯开门:https://www.bilibili.com/video/BV1jL411t7zN?spm_id_from=333.337.search-card.all.click

整体框架

委托.jpg

UE4使用委托

1、在.h文件中声明委托的宏,我们在官网查表,声明委托的生命宏。

  1. //用宏声明2个参数的委托,返回值int32
  2. DECLARE_DELEGATE_RetVal_TwoParams(int32, FTestDelegateTwoparamsRetVal, float, const FString&);

2、类中声明成员函数和声明成员对象

  1. UFUNCTION(BlueprintCallable)
  2. int32 testDelegatefuction(float a, const FString& s);//声明被委托的函数
  3. FTestDelegateTwoparamsRetVal myDelegate;//声明一个委托对象

3、在实现文件中,实现函数,其他类对象也可以,这里用自己这个类的指针,使用是第六行是this指针,实现绑定,两个参数,分别为类指针和要实现的成员函数。

  1. void UMyObject::myfunction()
  2. {
  3. GEngine->AddOnScreenDebugMessage(-1, 5.0f, FColor::Yellow, FString::Printf(TEXT("value = %d"), value));
  4. //实现绑定,两个参数,分别为类指针和要实现的成员函数
  5. myDelegate.BindUObject(this, &UMyObject::testDelegatefuction);
  6. //判断是否绑定成功,避免崩溃
  7. if (myDelegate.IsBound())
  8. myDelegate.Execute(23, "Hi");
  9. }
  10. int32 UMyObject::testDelegatefuction(float a, const FString& s)
  11. {
  12. return int32(a);
  13. }

蓝图实现:
image.png
如图效果:
image.png