虚幻4 ue4 学习笔记pwan篇 1.3b 粒子组件的 切换bug ToggleActive 反应迟钝问题 与之前博客又进步一步加入了 摄像头组件 cameracomponent

时间:2021-06-08 18:57:25
//头文件部分
1
// Fill out your copyright notice in the Description page of Project Settings. 2 3 #pragma once 4 5 #include "CoreMinimal.h" 6 #include "GameFramework/Pawn.h" 7 #include "MyPawn.generated.h" 8 9 UCLASS() 10 class TEST4_API AMyPawn : public APawn 11 { 12 GENERATED_BODY() 13 14 public: 15 // Sets default values for this pawn's properties 16 AMyPawn(); 17 18 protected: 19 // Called when the game starts or when spawned 20 virtual void BeginPlay() override; 21 22 public: 23 // Called every frame 24 virtual void Tick(float DeltaTime) override; 25 26 // Called to bind functionality to input 27 virtual void SetupPlayerInputComponent(class UInputComponent* PlayerInputComponent) override; 28 void fire(); 29 UParticleSystemComponent* OurParticleSystem; 30 private: 31 int32 coutFire = 0;//计数器 禁止其他对象和子对象访问 防止外人更改数据 32 };

cpp部分

 1 // Fill out your copyright notice in the Description page of Project Settings.
 2 
 3 #include "MyPawn.h"
 4 #include "Runtime/Engine/Classes/Components/BoxComponent.h"
 5 #include "Runtime/Engine/Classes/Components/SphereComponent.h"//    USphereComponent 引用
 6 #include "Runtime/CoreUObject/Public/UObject/ConstructorHelpers.h" // ConstructorHelpers 引用
 7 #include "Runtime/Engine/Classes/Particles/ParticleSystemComponent.h"//UParticleSystemComponent 引用
 8 #include "Runtime/Engine/Classes/GameFramework/SpringArmComponent.h"//UStaticMeshComponent 引用
 9 #include "Runtime/Engine/Classes/Camera/CameraComponent.h"//UCameraComponent 引用
10 // Sets default values
11 AMyPawn::AMyPawn()
12 {
13      // Set this pawn to call Tick() every frame.  You can turn this off to improve performance if you don't need it.
14     PrimaryActorTick.bCanEverTick = true;
15     AutoPossessPlayer = EAutoReceiveInput::Player0;//这行代码不加 无法实现用户操作 此时用户视角就是当前pawn视角
16 
17     USphereComponent * SphereComponent = CreateDefaultSubobject<USphereComponent>("RootComponent");
18     RootComponent = SphereComponent;//这里不一定非要用物体组件
19     
20 //    创建静态网格物体
21     UStaticMeshComponent * SphereVisual = CreateDefaultSubobject<UStaticMeshComponent>("VisualRepresentation");
22     SphereVisual->SetupAttachment(RootComponent);
23     
24     //打开素材库
25     static ConstructorHelpers::FObjectFinder<UStaticMesh> SphereVisualAssetWzh(TEXT("/Game/StarterContent/Shapes/Shape_Sphere.Shape_Sphere"));
26     if (SphereVisualAssetWzh.Succeeded()) {
27         SphereVisual->SetStaticMesh(SphereVisualAssetWzh.Object);
28         SphereVisual->SetRelativeLocation(FVector(0.0f, 0.0f, -40.0f));//设置位置0,0,0为初始位置                                               
29         SphereVisual->SetWorldScale3D(FVector(0.8f));//SetWorldScale3D 设置组件在世界空间中的变换倍数。 倍数以原来模型大小为基准
30     }
31 
32     // 创建一个可启用或停用的粒子系统
33     OurParticleSystem = CreateDefaultSubobject<UParticleSystemComponent>(TEXT("MovementParticles"));
34     OurParticleSystem->SetupAttachment(RootComponent);//直接将粒子系统添加到根组件上
35     OurParticleSystem->bAutoActivate = false;//在场景中激活
36 
37     OurParticleSystem->SetRelativeLocation(FVector(-20.0f, 0.0f, 20.0f));
38     OurParticleSystem->SetWorldScale3D(FVector(3.0f));//SetWorldScale3D 设置组件在世界空间中的变换倍数。 倍数以原来模型大小为基准
39     static ConstructorHelpers::FObjectFinder<UParticleSystem> ParticleAsset(TEXT("/Game/StarterContent/Particles/P_Fire.P_Fire"));
40     if (ParticleAsset.Succeeded())
41     {
42         OurParticleSystem->SetTemplate(ParticleAsset.Object);
43     }
44 
45 
46     //加入个摄像头让视角看起来舒服点 当然不加也是可以看到 
47     UCameraComponent* Camera = CreateDefaultSubobject<UCameraComponent>(TEXT("ActualCamera"));
48     Camera->SetupAttachment(RootComponent);
49     Camera->SetRelativeLocation(FVector(-250.f, 0.0f, 400));//设置位置0,0,0为初始位置    
50     Camera->RelativeRotation = FRotator(-45.f, 0.f, 0.f);// y z x顺序旋转  一个旋转信息的容器 所有旋转值都以度数存储。
51 }
52 
53 // Called when the game starts or when spawned
54 void AMyPawn::BeginPlay()
55 {
56     Super::BeginPlay();
57 
58     
59 }
60 
61 // Called every frame
62 void AMyPawn::Tick(float DeltaTime)
63 {
64     Super::Tick(DeltaTime);
65 
66 }
67 
68 // Called to bind functionality to input
69 void AMyPawn::SetupPlayerInputComponent(UInputComponent* PlayerInputComponent)
70 {
71     Super::SetupPlayerInputComponent(PlayerInputComponent);
72     PlayerInputComponent->BindAction("fire", IE_Released, this, &AMyPawn::fire);
73 
74 }
75 
76 
77 void AMyPawn::fire() {
78         coutFire = !coutFire;    
79     if (GEngine)
80     {
81         GEngine->AddOnScreenDebugMessage(-1, 0.2, FColor::Red, TEXT("火焰!"));
82 
83         int32 active32 = OurParticleSystem->bIsActive;
84         //OurParticleSystem->ToggleActive(); //官方使用的ToggleActive()切换粒子状态 我建议不要使用这个函数 因为
85         //在快速按下键盘按键 调用事件函数fire时 无法执行里面的ToggleActive函数 但是可以打印文字“火焰“ 但是慢慢按就没问题
86         //我发现主要是 ToggleActive内部操作 bIsActive的问题 如果快速按下 bIsActive 就不会重新赋值 而是一直为1 并不会赋0 估计是虚幻4官方的bug, 慢慢按 才为0 我自己重新 定义一个外部变量coutFire 计数代替bIsActive 就没问题了不用ToggleActive实现
87         OurParticleSystem->SetActive(coutFire);//通过计数器 切换状态
88     }
89 
90 }