常用组件
uactorcomponent:
actorcomponent 是组件的基础类,定义可被添加到不同类型 actor 的重复使用行为。它们主要用于将几何体与 actor 关联起来,如碰撞几何体或渲染网格体,控制 actor 在世界场景中的移动方式、播放与 actor 相关的声效、使 actor 能投射光影到世界场景等。
uscenecomponent:
scenecomponent 是 actorcomponent 的延伸,拥有一个变形,即位置、旋转和尺寸。附加的一个变形意味着 scenecomponent 可以相互附着。
uprimitivecomponent
uprimitivecomponent
是虚幻引擎(ue)中用于渲染和物理交互的基础组件类。它继承自uscenecomponent
,具有可视化的功能,可作为可视性剔除的粒度和渲染属性规范(如投射阴影等)。
uprimitivecomponent
是ue中用于定义actor几何形状和渲染属性的重要组件类,它为游戏的可视化和物理模拟提供了基础。
ucameracomponent:用于控制相机的组件。
ulightcomponent:用于控制灯光的组件。
静态网格组件(static mesh component)
ustaticmeshcomponent* staticmeshcomponent = createdefaultsubobject<ustaticmeshcomponent>(text("staticmeshcomponent"));
staticmeshcomponent->setstaticmesh(yourstaticmesh);
动画组件(animation component)
uaniminstance* animinstance = createdefaultsubobject<uaniminstance>(text("animationcomponent"));
音频组件(audio component)
uaudiocomponent* audiocomponent = createdefaultsubobject<uaudiocomponent>(text("audiocomponent"));
audiocomponent->setsound(yoursound);
粒子系统组件(particle system component)
uparticlesystemcomponent* particlecomponent = createdefaultsubobject<uparticlesystemcomponent>(text("particlecomponent"));
particlecomponent->settemplate(yourparticlesystem);
动画蒙太奇通知窗口组件
void uplaymontagenotifywindow::branchingpointnotifybegin(fbranchingpointnotifypayload& branchingpointpayload)
{
// 输出 branchingpointpayload 的某些成员变量的值
ue_log(logtemp, display, text("branchingpointpayload value: %f"), branchingpointpayload.payloadvalue);
}
“fbranchingpointnotifypayload”通常是一个自定义的数据结构(结构体或类),用于传递与分支点通知相关的数据。
它包含了各种与动画蒙太奇(montage)中的分支点相关的信息。具体包含哪些成员变量取决于项目的具体需求和设计。
它包含以下类型的信息:
- 分支点的标识或名称,以便识别特定的分支点。
- 与分支点相关的参数或数据,这些参数可能用于控制动画的流程、行为或其他相关逻辑。
- 可能还包含其他与动画状态、条件或事件相关的数据。
常用函数
ugameplaystatics
是一个静态类,提供了许多与游戏玩法相关的静态函数。通过这个类,你可以在不需要拥有该类实例的情况下,直接调用其中的函数来执行各种操作。
spawnobject
:创建一个对象。beginspawningactorfromblueprint
:从蓝图中生成实例,但不会自动执行它的构造脚本。begindeferredactorspawnfromclass
:生成一个actor
类的实例,但是不会自动执行它的构造脚本。finishspawningactor
:结束生成actor
,执行构造脚本。getactorarrayaveragelocation
:获取actor
数组的平均位置。getactorarraybounds
:获取actor
数组的边界。getallactorsofclass
:获取此类的actor
数组。getallactorswithinterface
:获取拥有此接口的actor
数组。getallactorswithtag
:获取此tag
的actor
数组。getgameinstance
:获取ugameinstance
。getplayercontroller
:获取aplayercontroller
。getpawn
:获取apawn
。getcharacter
:获取acharacter
。getplayercameramanager
:获取aplayercameramanager
。openlevel
:加载关卡。loadstreamlevel
:加载streamlevel
。unloadstreamlevel
:卸载streamlevel
。getworld
:获取当前世界。getauthgamemode
:获取当前授权的游戏模式。getgamestatebase
:获取游戏状态。applydamage
:应用伤害。playworldcamerashake
:播放世界相机震动。spawnemitteratlocation
:在目标位置生成粒子。
tsubclassof
是一个提供 uclass 类型安全性的模板类。例如,假设您正在创建一个弹丸类,该类允许设计器指定损坏类型。可以只创建一个 uclass 类型的 uproperty,并希望设计器始终分配派生自 udamagetype 的类,或者可以使用 tsubclassof 模板强制执行该选择。下面的示例代码说明了其中的区别:
/** type of damage */
uproperty(editdefaultsonly, category=damage)
uclass* damagetype;
与
/** type of damage */
uproperty(editdefaultsonly, category=damage)
tsubclassof<udamagetype> damagetype;
在第二个声明中,模板类告诉编辑器的属性窗口仅列出派生自 udamagetype 的类作为属性的选项。在第一个声明中,可以选择任何 uclass。下图说明了这一点。
strategygame的弹丸蓝图示例
除了这种 uproperty 安全性之外,您还可以获得 c++ 级别的类型安全性。如果尝试将不兼容的 tsubclassof 类型相互分配,则会出现编译错误。如果尝试分配泛型 uclass,它将执行运行时检查以验证它是否可以执行分配。如果运行时检查失败,则结果值为 nullptr。
uclass* classa = udamagetype::staticclass();
tsubclassof<udamagetype> classb;
classb = classa; // performs a runtime check
tsubclassof<udamagetype_lava> classc;
classb = classc; // performs a compile time check
getworldtimermanager()
是ue4中用于获取全局定时器管理器的函数。全局定时器管理器用于管理游戏中的定时器,它存在于游戏实例对象上以及每个场景中。
通过调用getworldtimermanager()
,可以获取到全局定时器管理器的引用,然后可以使用该管理器来设置、暂停、恢复、清除定时器等操作。
以下是一个使用getworldtimermanager()
的示例代码:
ftimerhandle timerhandle;
getworldtimermanager().settimer(timerhandle, this, &yourclass::yourfunction, 5.0f, true);
在上述代码中,首先创建了一个ftimerhandle
类型的变量timerhandle
,用于保存定时器的句柄。然后,使用getworldtimermanager().settimer()
函数来设置一个定时器。该函数的参数包括:
timerhandle
:定时器句柄的引用,用于保存设置的定时器。this
:指定定时器所属的对象。&yourclass::yourfunction
:定时器到期时要执行的函数指针。5.0f
:定时器的时间间隔,单位为秒。true
:表示定时器是否循环执行。
这样,就设置了一个每隔5秒执行一次yourfunction
函数的定时器。
获取自身自带的组件
目标类型* 变量名= cast<目标类型>(this->getcomponentbyclass(目标类型::staticclass()));
//用于根据指定的组件类来获取该类的组件实例。
//staticclass() 是一个用于获取类的静态信息的函数。
需要注意的是,getcomponentbyclass
返回的是 uactorcomponent*
类型的指针,需要使用 cast
函数进行类型转换以获取特定类型的组件指针。如果转换失败(即组件不是指定的类型),则转换后的指针为 nullptr
,可以通过判断指针是否为空来处理这种情况。
角色运动绑定函数
“bindaction”通常用于在 unreal engine 4(ue4)中绑定输入动作到特定的函数或方法。它是一种将用户输入(例如按下键盘按键、点击鼠标等)与游戏中的操作或事件关联起来的方式。
playerinputcomponent->bindaction("discardweapon", ie_pressed, this, &amycharacter::discardweapon);
在上述代码中,通过playerinputcomponent->bindaction
将名为“discardweapon”的动作与amycharacter
类中的discardweapon
函数进行绑定,当该动作被触发(例如按下对应的按键)时,将调用amycharacter::discardweapon
函数。
除了ie_pressed
,还有其他的触发条件可用于bindaction
,它们定义在einputevent
枚举中,具体包括:
ie_released
:表示当按键被松开时触发。ie_repeat
:用于连续触发的情况,例如按住按键时会不断重复触发相关操作。ie_doubleclick
:表示双击按键时触发。ie_axis
:轴事件类型,通常用于处理类似摇杆或鼠标移动等持续性的输入,并会返回一个值。ie_max
:枚举的最大值,一般不用于实际的绑定操作。
调整鼠标灵敏度
“addcontrolleryawinput”是 unreal engine 4(ue4)中 pawn 类的一个函数,用于给控制器的控制旋转添加输入(影响偏航),前提是该控制器是本地玩家控制器。
此函数的值会乘以玩家控制器的“inputyawscale”值。通常用于实现角色或 pawn 根据输入(例如鼠标移动)来进行左右方向的旋转。
playerinputcomponent->bindaxis("turn", this, &amonsterplayer::yawcamera);
playerinputcomponent->bindaxis("lookup", this, &amonsterplayer::pitchcamera);
void amonsterplayer::yawcamera(float axisvalue)
{
addcontrolleryawinput(axisvalue * mousespeed);
}
通过改变自己定义的mousespeed的值来更改鼠标移动速度
延迟函数
首先,创建一个 flatentactioninfo
结构体,用于存储异步操作的相关信息,例如延迟后要执行的函数、函数的归属者以及异步操作的 id 等。然后,通过 ukismetsystemlibrary::delay
函数来设置延迟。
#include "kismet/gameplaystatics.h"
#include "engine/world.h"
uclass()
class yourclass : public aactor
{
public:
// 延迟结束后的回调函数,声明处必须加 ufunction,否则反射系统找不到这个函数
ufunction()
void delayfinish();
void beginplay() override
{
super::beginplay();
// 创建一个 latentinfo,用不到 linkage 直接传 0(不能是-1),uuid 随机生成,指定延迟后要执行的函数 executionfunction,以及 executionfunction 的归属者 this
const flatentactioninfo latentinfo(0, fmath::rand(), text("delayfinish"), this);
ukismetsystemlibrary::delay(this, 3.0f, latentinfo);
}
};
// 定义延迟结束后的回调函数
void yourclass::delayfinish()
{
// 在这里添加延迟结束后要执行的具体操作
ue_log(logtemp, log, text("delay 结束!"));
}
定义了一个 delayfinish
函数作为延迟结束后的回调函数。在 beginplay
函数中,创建了 flatentactioninfo
结构体实例 latentinfo
,设置了 linkage
为 0(虽然资料较少,但一般直接传 0 即可),使用 fmath::rand
生成随机的 uuid
,指定延迟结束后要执行的函数为 delayfinish
,并将 this
作为 executionfunction
的归属者(即表明 delayfinish
是当前类的成员函数)。最后,通过 ukismetsystemlibrary::delay
函数传入当前对象 this
、延迟时间 3.0f
和 latentinfo
来启动延迟操作。
flatentactioninfo
是一个结构体,用于存储异步操作的相关信息。它包含了以下几个成员:
linkage
:执行函数中的恢复点,是一个整数。一般情况下,如果用不到可以直接传 0,但不能是-1。uuid
:本次异步操作的 id,用于标识此次操作。通常可以使用fmath::rand()
生成一个随机数,或者通过其他方式生成一个唯一的标识。executionfunction
:要执行的函数名,类型为fname
。需要使用text()
宏进行转换。callbacktarget
:执行函数的归属者,即表明executionfunction
是callbacktarget
的成员函数。它是一个tobjectptr<uobject>
类型的弱指针。
ukismetsystemlibrary
ukismetsystemlibrary
是虚幻引擎(unreal engine)中的一个类,它包含了许多有用的函数,可用于各种不同的操作,例如打印调试信息、进行射线检测、移动组件、加载资产、获取游戏相关信息等。
以下是ukismetsystemlibrary
中一些常见函数的介绍:
stacktrace
:打印一个堆栈跟踪到日志,以便查看蓝图是如何到达某个节点的。isvalid
:判断一个对象是否可用(非空且未被标记为待删除)。getobjectname
:返回指定对象的实际对象名称。getpathname
:返回指定对象的完整路径名。getdisplayname
:返回对象的显示名称(在编辑器构建中是 actor 标签,在非编辑器构建中是实际对象名称),主要用于调试辅助显示,不应被用于唯一标识 actor,也不适合用于向游戏的最终用户显示,因为它没有被本地化。getclassdisplayname
:返回一个类的显示名称。getengineversion
:获取引擎的版本号,用于向最终用户显示。getgamename
:获取当前游戏的名称。getplatformusername
:获取操作系统中的当前用户名。getgametimeinseconds
:获取当前游戏时间(以秒为单位),当游戏暂停时它会停止,并且会受到慢动作的影响。此函数需要传入一个worldcontextobject
参数,表示世界上下文。isserver
:根据提供的世界上下文对象,判断该对象所在的世界是否为主机。isdedicatedserver
:判断是否运行在专用服务器上。ispackagedfordistribution
:判断是否是为了分发而打包的构建。getuniquedeviceid
/getdeviceid
:获取平台特定的唯一设备 id。makeliteralint
/makeliteralfloat
/makeliteralbool
:分别创建一个指定值的整型、浮点型或布尔型的字面值。delay
:用于实现延迟操作。可以创建一个flatentactioninfo
结构体来设置延迟的相关信息,例如延迟后要执行的函数、函数的归属者以及异步操作的 id 等,然后通过该函数来启动延迟。linetracesinglebyprofile
:进行基于配置文件的单次射线检测。
射线检测
虚幻引擎中的射线检测主要分为单通道和多通道检测,根据检测目标还可分为通道检测和目标物体类型检测。常见的射线检测类型包括:
单通道射线检测:通过指定通道类型(如ecc_visibility
)进行检测。定义射线的起始位置、方向和碰撞返回数据(fhitresult
)。需注意被检测对象在该通道的“visibility”需设置为阻挡状态,否则可能检测不到。例如:
fhitresult hitresult;
bool btemphit = ukismetsystemlibrary::linetracesinglebyprofile(getworld(),hitresult, startlocation, endlocation, ecc_visibility);
单通道根据目标物体类型进行检测:首先定义fcollisionobjectqueryparams
的参数,然后使用addobjecttypestoquery
方法添加目标通道。例如:
fcollisionobjectqueryparams tempobjecttype;
tempobjecttype.addobjecttypestoquery(ecc_worlddynamic);
bool btemphit2 = ukismetsystemlibrary::linetracesinglebyprofile(getworld(),hitresult, startlocation, endlocation, tempobjecttype);
根据 profile 的名称进行检测:可以根据在项目设置-碰撞-preset 中新建的碰撞预设的名字进行检测,例如“cpptest”。也可以通过fcollisionqueryparams
类型参数添加忽略检测的 actor。例如:
bool btemphit5 = ukismetsystemlibrary::linetracesinglebyprofile(getworld(),hitresult, startlocation, endlocation, "cpptest");
// 或添加忽略检测的 actor
fcollisionqueryparams tempqueryparams;
tempqueryparams.addignoredactor(this->getuniqueid());
bool btemphit5 = getworld()->linetracesinglebyprofile(hitresult, startlocation, endlocation, "cpptest", tempqueryparams);
多通道射线检测:
- 根据通道直接使用
linetracemultibychannel
,与单通道使用类似,但可返回多个结果。 - 多对象类型检测使用
linetracemultibyobjecttype
,通过fcollisionobjectqueryparams
的addobjecttypestoquery
添加多个目标通道。 - 根据碰撞预设名进行多通道检测的方式可参考单通道根据 profile 名称检测的使用方式。
float seekradius = 100.0f;
tarray<fhitresult> hitresults;
fvector beginlocation = followcamera->getcomponentlocation(); // 起点位置
fvector endlocation = beginlocation + followcamera->getforwardvector() * 1000; // 终点位置
tarray<tenumasbyte<eobjecttypequery>> objecttypes;
objecttypes.add(eobjecttypequery::objecttypequery2); // 添加要检测的对象类型,例如 pawn
tarray<aactor*> ignoreactors; // 忽略的 actor 数组
bool bishit = ukismetsystemlibrary::spheretracemultiforobjects(getworld(), beginlocation, endlocation, seekradius, objecttypes, true, ignoreactors, edrawdebugtrace::forduration, hitresults, true);
if (bishit) {
for (fhitresult hitresult : hitresults) {
if (hitresult.getactor()!= null) {
// 对检测到的 actor 进行相应的处理
}
}
}
spheretracemultiforobjects
是 unreal engine 中用于进行球形碰撞检测的函数。它可以检测从起始点到结束点形成的球体范围内的多个对象。
以下是该函数的参数说明:
worldcontextobject
:提供世界上下文的对象指针,通常是getworld()
。start
:球体检测的起始位置向量。end
:球体检测的结束位置向量(用于确定球体的方向和范围)。radius
:球体的半径。objecttypes
:要检测的对象类型数组。通过tenumasbyte<eobjecttypequery>
枚举指定对象类型。btracecomplex
:是否追踪复杂碰撞。ignoreactors
:要忽略的actor数组。drawdebugtype
:调试绘制类型,例如edrawdebugtrace::forduration
表示在一段时间内显示调试痕迹。outhits
:用于存储碰撞结果的fhitresult
数组。bignoreself
(可选):是否忽略自身。
该函数返回一个布尔值,表示是否检测到碰撞。如果检测到碰撞,碰撞结果将存储在 outhits
数组中
另外,还有其他形状的扫描射线检测,如sweepsinglebychannel
,需提前定义扫描形状,可通过大小、类型、方向决定扫描形状效果。其相关函数sweepmultibyobjecttype
、sweepmultibyprofile
的使用方式类似。
在进行射线检测时,需定义起始位置坐标和方向,同时设置相关变量的值,通常会与摄像机进行绑定。结束位置一般设置得足够远,以确保射线能够检测到目标物体。
发表评论