BlueprintCallable
在上一篇文章中,我们已经实现了抓取事件的逻辑,是用蓝图实现的。在按键按下时,需要触发扫掠检测,这部分逻辑我们已经在 C++ 侧的 Grabber 场景组件里实现了。所以在本篇文章中,我们学习如何在蓝图里调用自己写的 C++ 函数。
交互的方法非常简单。如代码清单 1 所示,我们只需要对想要暴露的函数添加 UFUNCTION(BlueprintCallable) 宏即可。此处我们新增了两个函数 Grab 和 Release,用于蓝图调用。
- class CRYPTRAIDER_API UGrabber : public USceneComponent
- {
- public:
- UFUNCTION(BlueprintCallable)
- void Grab();
- UFUNCTION(BlueprintCallable)
- void Release();
- };
Grab 和 Release 函数的具体实现,如代码清单 2 所示:Grab 函数里面的逻辑就是复制的之前在 TickComponent 函数里实现的扫掠检测逻辑;Release 函数里面目前仅是日志打印。
- void UGrabber::Grab()
- {
- FVector Start = GetComponentLocation();
- FVector End = Start + GetForwardVector() * MaxGrabDistance;
- DrawDebugLine(GetWorld(), Start, End, FColor::Red);
- FCollisionShape Sphere = FCollisionShape::MakeSphere(GrabRadius);
- FHitResult HitResult;
- bool HasHit = GetWorld()->SweepSingleByChannel(HitResult,
- Start, End,
- FQuat::Identity,
- ECC_GameTraceChannel2,
- Sphere);
- if (HasHit)
- {
- AActor* HitActor = HitResult.GetActor();
- UE_LOG(LogTemp, Display, TEXT("Hit actor: %s"), *HitActor->GetActorNameOrLabel());
- }
- else
- {
- UE_LOG(LogTemp, Display, TEXT("No actor hit"));
- }
- }
- void UGrabber::Release()
- {
- UE_LOG(LogTemp, Display, TEXT("Released grabber"))
- }
在蓝图中的使用方式,如图 1 所示,因为调用的是类成员函数,所以我们需要指定类的“this 指针”。 Grabber 类可以从左侧组件标签卡中拖拽得到。

运行程序。尝试在视线里没有雕塑时按下鼠标左键,以及视线里有雕塑时按下鼠标左键。如图 2 所示,可以看到在控制台中打印了预期的日志。
即时编译后,如果运行报错,可以尝试重新编译蓝图。如果还不行,就退出编辑器,重新编译 C++ 项目。
