• 20uec++多人游戏【小球与玩家互动】


    为小球添加生命值组件和伤害处理函数

    1. //生命值组件
    2. UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Components")
    3. class USHealthComponent * HealthComp;
    4. //伤害处理函数
    5. UFUNCTION()
    6. void HandleTakeAnyDamage(USHealthComponent * OwnerHealthComp, float Health, float HealthDelta, const UDamageType * DamageType, AController * InstigatedBy, AActor * DamageCauser);

    创建组件并定义函数

    HealthComp = CreateDefaultSubobject(TEXT("HealthComp"));
    1. void AASTrackerBot::HandleTakeAnyDamage(USHealthComponent * OwnerHealthComp, float Health, float HealthDelta, const UDamageType * DamageType, AController * InstigatedBy, AActor * DamageCauser)
    2. {
    3. UKismetSystemLibrary::PrintString(this, FString::SanitizeFloat(HealthComp->Health));
    4. }

    添加与爆炸相关的成员变量和函数

    1. //自爆函数
    2. void SelfDestruct();
    3. //爆炸特效
    4. UPROPERTY(EditDefaultsOnly, Category = "TracerBot")
    5. class UParticleSystem * ExplorEffect;
    6. //是否已经爆炸
    7. bool bExplored;
    8. //爆炸半径
    9. UPROPERTY(EditDefaultsOnly, Category = "TracerBot")
    10. float ExplorRadius;
    11. //爆炸伤害
    12. UPROPERTY(EditDefaultsOnly, Category = "TracerBot")
    13. float ExplorDamage;

    在构造函数中初始化一下

    1. bExplored = false;
    2. ExplorRadius = 200;
    3. ExplorDamage = 100;

    定义自爆函数

    1. void AASTrackerBot::SelfDestruct()
    2. {
    3. //检查是否已经爆炸了
    4. if (bExplored)
    5. {
    6. return;
    7. }
    8. bExplored = true;
    9. //发生爆炸
    10. UGameplayStatics::SpawnEmitterAtLocation(GetWorld(), ExplorEffect, GetActorLocation());
    11. //设置要忽略的actor
    12. TArray IgnoredActors;
    13. IgnoredActors.Add(this);
    14. //对自身进行伤害
    15. UGameplayStatics::ApplyRadialDamage(this, ExplorDamage, GetActorLocation(), ExplorRadius, nullptr, IgnoredActors, this, GetInstigatorController(), true);
    16. //画出伤害范围
    17. DrawDebugSphere(GetWorld(), GetActorLocation(), ExplorRadius, 12, FColor::Green, false, 2.0f, 0, 1.0f);
    18. //自毁
    19. Destroy();
    20. }

    在伤害处理中,调用该函数

    1. void AASTrackerBot::HandleTakeAnyDamage(USHealthComponent * OwnerHealthComp, float Health, float HealthDelta, const UDamageType * DamageType, AController * InstigatedBy, AActor * DamageCauser)
    2. {
    3. UKismetSystemLibrary::PrintString(this, FString::SanitizeFloat(HealthComp->Health));
    4. if (HealthComp->Health <= 0)
    5. {
    6. SelfDestruct();
    7. }
    8. }

    ===========================================

    现在实现靠近玩家定时自爆功能

    创建相关的变量和函数

    1. //球形碰撞组件
    2. UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Components")
    3. class USphereComponent* CollisionComponent;
    4. //自爆倒计时句柄
    5. FTimerHandle TimerHandle_SelfDamage;
    6. //倒计时自爆函数
    7. void DamageSelf();
    8. //是否已经开始自毁倒计时
    9. bool bStartSelfDamge;
    10. //游戏重叠函数
    11. virtual void NotifyActorBeginOverlap(AActor * OtherActor) override;

    在构造函数中创建球形组件,并设置相关参数

    1. CollisionComponent = CreateDefaultSubobject(TEXT("SphereComponent"));
    2. CollisionComponent->SetSphereRadius(200);
    3. CollisionComponent->SetCollisionEnabled(ECollisionEnabled::QueryOnly);
    4. CollisionComponent->SetCollisionResponseToAllChannels(ECR_Ignore);
    5. CollisionComponent->SetCollisionResponseToChannel(ECC_Pawn, ECR_Overlap);
    6. CollisionComponent->SetupAttachment(RootComponent);

    定义倒计时自爆函数

    1. void AASTrackerBot::DamageSelf()
    2. {
    3. UGameplayStatics::ApplyDamage(this, 20, GetInstigatorController(), this, nullptr);
    4. }

    定义重叠函数

    1. void AASTrackerBot::NotifyActorBeginOverlap(AActor * OtherActor)
    2. {
    3. if (!bStartSelfDamge)
    4. {
    5. ASCharacter * PlayerPawn = Cast(OtherActor);
    6. if (PlayerPawn)
    7. {
    8. GetWorld()->GetTimerManager().SetTimer(TimerHandle_SelfDamage, this, &AASTrackerBot::DamageSelf, 0.5f, true , 0.0f);
    9. bStartSelfDamge = true;
    10. }
    11. }
    12. }

    编译,然后打开小球的蓝图,选择特效

    编译,测试,发现小球不会爆炸。

    将构造函数的事件绑定函数放到游戏开始函数。就可以了

    1. // Called when the game starts or when spawned
    2. void AASTrackerBot::BeginPlay()
    3. {
    4. Super::BeginPlay();
    5. NextPathPoint = GetNextPathPoint();
    6. //伤害事件绑定函数
    7. HealthComp->OnHealthChanged.AddDynamic(this, &AASTrackerBot::HandleTakeAnyDamage);
    8. }

     我也不知道为啥。

    同时也可以炸死人。

    ========================================

    现在我们为小球完善一下材质

     按住T,点击鼠标左键

    然后选择一个材质

     

    按U,然后点击鼠标左键

     

    将这两个设成4

     

    这样可以让材质变得密集 

     

    按住M,然后点击鼠标左键,得到乘节点,然后连线

     

    按住1,然后点击鼠标左键,生成常数节点,然后连接到自发光上面

     这是将值设为0.5的效果

    添加一个Time节点

     

     

    然后按住s,点击鼠标左键,生成参数节点 

     我们用(时间-参数)*4,然后约束一下乘积。

     然后1-上述结果

    然后再得到一个指数

    然后将其赋予到自发光上面

     回到小球类,我们添加一个小球材质的变量

    1. //动态材质
    2. class UMaterialInstanceDynamic * MatInst;
    #include "Materials/MaterialInstanceDynamic.h"

    完善伤害处理函数

    1. void AASTrackerBot::HandleTakeAnyDamage(USHealthComponent * OwnerHealthComp, float Health, float HealthDelta, const UDamageType * DamageType, AController * InstigatedBy, AActor * DamageCauser)
    2. {
    3. //UKismetSystemLibrary::PrintString(this, FString::SanitizeFloat(HealthComp->Health));
    4. //得到MeshComponent组件的材质
    5. if (MatInst == nullptr)
    6. {
    7. MatInst = MeshComponent->CreateAndSetMaterialInstanceDynamicFromMaterial(0, MeshComponent->GetMaterial(0));
    8. UKismetSystemLibrary::PrintString(this, FString::SanitizeFloat(HealthComp->Health));
    9. }
    10. //将参数设为当前时间,让材质发光
    11. if (MatInst)
    12. {
    13. MatInst->SetScalarParameterValue("LastTimeDamageTaken", GetWorld()->TimeSeconds);
    14. }
    15. //自爆
    16. if (HealthComp->Health <= 0)
    17. {
    18. SelfDestruct();
    19. }
    20. }

    ==========================================

    现在加一下声音特效

    添加两个成员变量

    1. //自爆中声音特效
    2. UPROPERTY(EditDefaultsOnly, Category = "TracerBot")
    3. class USoundCue * SelfDestructSound;
    4. //爆炸特效
    5. UPROPERTY(EditDefaultsOnly, Category = "TracerBot")
    6. class USoundCue * ExploedSound;
    #include "Sound/SoundCue.h"

    更新一下SelfDestruct函数和NotifyActorBeginOverlap函数

    1. void AASTrackerBot::SelfDestruct()
    2. {
    3. //检查是否已经爆炸了
    4. if (bExplored)
    5. {
    6. return;
    7. }
    8. bExplored = true;
    9. //发生爆炸
    10. UGameplayStatics::SpawnEmitterAtLocation(GetWorld(), ExplorEffect, GetActorLocation());
    11. //设置要忽略的actor
    12. TArray IgnoredActors;
    13. IgnoredActors.Add(this);
    14. // UKismetSystemLibrary::PrintString(this, FString::SanitizeFloat(222.0f));
    15. //对自身进行伤害
    16. UGameplayStatics::ApplyRadialDamage(this, ExplorDamage, GetActorLocation(), ExplorRadius, nullptr, IgnoredActors, this, GetInstigatorController(), true);
    17. //画出伤害范围
    18. DrawDebugSphere(GetWorld(), GetActorLocation(), ExplorRadius, 12, FColor::Green, false, 2.0f, 0, 1.0f);
    19. //发生爆炸声,在actor的位置
    20. UGameplayStatics::PlaySoundAtLocation(this, ExploedSound, GetActorLocation());
    21. //自毁
    22. Destroy();
    23. }
    1. void AASTrackerBot::NotifyActorBeginOverlap(AActor * OtherActor)
    2. {
    3. if (!bStartSelfDamge)
    4. {
    5. ASCharacter * PlayerPawn = Cast(OtherActor);
    6. if (PlayerPawn)
    7. {
    8. GetWorld()->GetTimerManager().SetTimer(TimerHandle_SelfDamage, this, &AASTrackerBot::DamageSelf, 0.5f, true , 0.0f);
    9. bStartSelfDamge = true;
    10. }
    11. //将自爆警告声音绑定到根组件
    12. UGameplayStatics::SpawnSoundAttached(SelfDestructSound, RootComponent);
    13. }
    14. }

    删掉这些成品,我们自己做一个

    创建cue, cue实际上就是声音文件的子类

     

     

    设置声音衰减

     

    我们还可以做一个音效衰减

     

    创建之后打开,设为自然音

    这里选择衰减 

     

     

    在蓝图中选择声音

     

    然后添加一个声音组件,选择滚动声效

     

     

     编译测试成功  

  • 相关阅读:
    微信公众号模板消息api
    API接口开发采集淘宝商品详情页数据优惠券sku价格销量信息等可支持高并发接入演示
    Java关键字说明
    Java基于SpringBoot的校园博客系统
    JavaWeb开发了解
    一文了解 Java 中的构造器
    vue.js前端框架应用案例
    c语言 编程及答案
    Python - 全局变量小记
    B. Decode String
  • 原文地址:https://blog.csdn.net/zhang2362167998/article/details/128097328