Use timeline for updating pickup position

This commit is contained in:
baz 2024-11-14 22:49:59 +00:00
parent ee0a537621
commit 18702cea0c
12 changed files with 106 additions and 41 deletions

BIN
Content/Pickups/C_Pickup.uasset (Stored with Git LFS) Normal file

Binary file not shown.

Binary file not shown.

Binary file not shown.

BIN
Content/Pickups/EXP/BP_RedEXPPickup.uasset (Stored with Git LFS)

Binary file not shown.

BIN
Content/Pickups/Gold/BP_GoldPickup.uasset (Stored with Git LFS)

Binary file not shown.

View File

@ -16,12 +16,12 @@ void AEXPPickup::Tick(float DeltaSeconds)
Super::Tick(DeltaSeconds);
}
void AEXPPickup::OnBeginOverlap(UPrimitiveComponent* OverlappedComponent, AActor* OtherActor,
void AEXPPickup::OnInnerBeginOverlap(UPrimitiveComponent* OverlappedComponent, AActor* OtherActor,
UPrimitiveComponent* OtherComp, int32 OtherBodyIndex, bool bFromSweep, const FHitResult& SweepResult)
{
if (APlayerCharacter* PlayerCharacter = Cast<APlayerCharacter>(OtherActor))
{
PlayerCharacter->GetEXPComponent()->IncrementEXP(EXP);
Super::OnBeginOverlap(OverlappedComponent, OtherActor, OtherComp, OtherBodyIndex, bFromSweep, SweepResult);
Super::OnInnerBeginOverlap(OverlappedComponent, OtherActor, OtherComp, OtherBodyIndex, bFromSweep, SweepResult);
}
}

View File

@ -25,7 +25,7 @@ protected:
public:
virtual void Tick(float DeltaSeconds) override;
virtual void OnBeginOverlap(UPrimitiveComponent* OverlappedComponent, AActor* OtherActor,
virtual void OnInnerBeginOverlap(UPrimitiveComponent* OverlappedComponent, AActor* OtherActor,
UPrimitiveComponent* OtherComp, int32 OtherBodyIndex, bool bFromSweep,
const FHitResult& SweepResult) override;
};

View File

@ -18,12 +18,12 @@ void AGoldPickup::Tick(float DeltaSeconds)
Super::Tick(DeltaSeconds);
}
void AGoldPickup::OnBeginOverlap(UPrimitiveComponent* OverlappedComponent, AActor* OtherActor,
void AGoldPickup::OnInnerBeginOverlap(UPrimitiveComponent* OverlappedComponent, AActor* OtherActor,
UPrimitiveComponent* OtherComp, int32 OtherBodyIndex, bool bFromSweep, const FHitResult& SweepResult)
{
if (APlayerCharacter* PlayerCharacter = Cast<APlayerCharacter>(OtherActor))
{
PlayerCharacter->GetGoldComponent()->IncrementGold(Gold);
Super::OnBeginOverlap(OverlappedComponent, OtherActor, OtherComp, OtherBodyIndex, bFromSweep, SweepResult);
Super::OnInnerBeginOverlap(OverlappedComponent, OtherActor, OtherComp, OtherBodyIndex, bFromSweep, SweepResult);
}
}

View File

@ -25,7 +25,7 @@ protected:
public:
virtual void Tick(float DeltaSeconds) override;
virtual void OnBeginOverlap(UPrimitiveComponent* OverlappedComponent, AActor* OtherActor,
virtual void OnInnerBeginOverlap(UPrimitiveComponent* OverlappedComponent, AActor* OtherActor,
UPrimitiveComponent* OtherComp, int32 OtherBodyIndex, bool bFromSweep,
const FHitResult& SweepResult) override;
};

View File

@ -2,7 +2,6 @@
#include "Pickup.h"
#include "PlayerCharacter.h"
#include "Components/SphereComponent.h"
#include "Kismet/GameplayStatics.h"
@ -12,46 +11,52 @@
APickup::APickup()
{
// Set this actor to call Tick() every frame. You can turn this off to improve performance if you don't need it.
PrimaryActorTick.bCanEverTick = true;
PrimaryActorTick.bCanEverTick = false;
// Create Sphere Component
SphereComponent = CreateDefaultSubobject<USphereComponent>(TEXT("Sphere Component"));
SetRootComponent(SphereComponent);
SphereComponent->SetSphereRadius(25.0f);
InnerSphereComponent = CreateDefaultSubobject<USphereComponent>(TEXT("Inner Sphere Component"));
SetRootComponent(InnerSphereComponent);
InnerSphereComponent->SetSphereRadius(25.0f);
OuterSphereComponent = CreateDefaultSubobject<USphereComponent>(TEXT("Outer Sphere Component"));
OuterSphereComponent->AttachToComponent(RootComponent, FAttachmentTransformRules::KeepRelativeTransform);
OuterSphereComponent->SetSphereRadius(250.0f);
SpriteComponent = CreateDefaultSubobject<UPaperSpriteComponent>(TEXT("Sprite Component"));
SpriteComponent->SetRelativeRotation(FRotator(0.0f, 90.0f, -90.0f));
SpriteComponent->SetRelativeScale3D(FVector(.5f, .5f, .5f));
SpriteComponent->SetCollisionEnabled(ECollisionEnabled::NoCollision);
SpriteComponent->SetupAttachment(RootComponent);
TimelineComponent = CreateDefaultSubobject<UTimelineComponent>(TEXT("Timeline Component"));
TimelineComponent->SetDirectionPropertyName(FName("TimelineDirection"));
TimelineComponent->SetLooping(false);
TimelineComponent->SetTimelineLength(5.0f);
TimelineComponent->SetTimelineLengthMode(TL_TimelineLength);
TimelineComponent->SetPlaybackPosition(0.0f, false);
onTimelineCallback.BindUFunction(this, FName(TEXT("TimelineCallback")));
onTimelineFinishedCallback.BindUFunction(this, FName(TEXT("TimelineFinishedCallback")));
}
// Called when the game starts or when spawned
void APickup::BeginPlay()
{
Super::BeginPlay();
SphereComponent->OnComponentBeginOverlap.AddDynamic(this, &APickup::OnBeginOverlap);
}
void APickup::Tick(float DeltaSeconds)
{
Super::Tick(DeltaSeconds);
InnerSphereComponent->OnComponentBeginOverlap.AddDynamic(this, &APickup::OnInnerBeginOverlap);
OuterSphereComponent->OnComponentBeginOverlap.AddDynamic(this, &APickup::OnOuterBeginOverlap);
// TODO: Move actor towards player when in range
FVector actorLocation = GetActorLocation();
FVector playerLocation = UGameplayStatics::GetPlayerCharacter(GetWorld(), 0)->GetActorLocation();
double currentDistance = FVector::Distance(actorLocation, playerLocation);
if (currentDistance <= PickupMovementRange)
if (CurveFloat != nullptr)
{
double speed = 400 / currentDistance;
FVector location = FMath::VInterpTo(actorLocation, playerLocation, DeltaSeconds, speed);
SetActorLocation(location);
TimelineComponent->AddInterpFloat(CurveFloat, onTimelineCallback);
TimelineComponent->SetTimelineFinishedFunc(onTimelineFinishedCallback);
}
}
void APickup::OnBeginOverlap(UPrimitiveComponent* OverlappedComponent, AActor* OtherActor,
UPrimitiveComponent* OtherComp, int32 OtherBodyIndex, bool bFromSweep,
const FHitResult& SweepResult)
void APickup::OnInnerBeginOverlap(UPrimitiveComponent* OverlappedComponent, AActor* OtherActor,
UPrimitiveComponent* OtherComp, int32 OtherBodyIndex, bool bFromSweep,
const FHitResult& SweepResult)
{
if (APlayerCharacter* PlayerCharacter = Cast<APlayerCharacter>(OtherActor))
{
@ -64,3 +69,31 @@ void APickup::OnBeginOverlap(UPrimitiveComponent* OverlappedComponent, AActor* O
Destroy();
}
}
void APickup::OnOuterBeginOverlap(UPrimitiveComponent* OverlappedComponent, AActor* OtherActor,
UPrimitiveComponent* OtherComp, int32 OtherBodyIndex, bool bFromSweep,
const FHitResult& SweepResult)
{
if (APlayerCharacter* PlayerCharacter = Cast<APlayerCharacter>(OtherActor))
{
PickupLocation = GetActorLocation();
PlayTimeLine();
}
}
void APickup::TimelineCallback(float val)
{
FVector actorLocation = PickupLocation;
FVector playerLocation = UGameplayStatics::GetPlayerCharacter(GetWorld(), 0)->GetActorLocation();
FVector location = FMath::Lerp(actorLocation, playerLocation, val);
SetActorLocation(location);
}
void APickup::TimelineFinishedCallback()
{
}
void APickup::PlayTimeLine()
{
TimelineComponent->Play();
}

View File

@ -3,9 +3,11 @@
#pragma once
#include "CoreMinimal.h"
#include "Components/TimelineComponent.h"
#include "GameFramework/Actor.h"
#include "Pickup.generated.h"
class UTimelineComponent;
class USphereComponent;
class UPaperSpriteComponent;
@ -23,13 +25,28 @@ public:
double PickupMovementSpeed = 1000;
UPROPERTY(EditDefaultsOnly, BlueprintReadWrite)
USphereComponent* SphereComponent = nullptr;
USphereComponent* InnerSphereComponent = nullptr;
UPROPERTY(EditDefaultsOnly, BlueprintReadWrite)
USphereComponent* OuterSphereComponent = nullptr;
UPROPERTY(EditAnywhere)
UPaperSpriteComponent* SpriteComponent = nullptr;
UPROPERTY(EditDefaultsOnly)
USoundBase* PickupSoundBase = nullptr;
UPROPERTY(EditDefaultsOnly, BlueprintReadOnly, Category = "Timeline")
TObjectPtr<UTimelineComponent> TimelineComponent;
UPROPERTY(EditDefaultsOnly, BlueprintReadOnly, Category = "Timeline")
UCurveFloat* CurveFloat;
private:
FOnTimelineFloat onTimelineCallback;
FOnTimelineEventStatic onTimelineFinishedCallback;
FVector PickupLocation;
public:
// Sets default values for this actor's properties
@ -39,11 +56,22 @@ protected:
// Called when the game starts or when spawned
virtual void BeginPlay() override;
public:
virtual void Tick(float DeltaSeconds) override;
UFUNCTION()
virtual void OnBeginOverlap(UPrimitiveComponent* OverlappedComponent, AActor* OtherActor,
virtual void OnInnerBeginOverlap(UPrimitiveComponent* OverlappedComponent, AActor* OtherActor,
UPrimitiveComponent* OtherComp, int32 OtherBodyIndex, bool bFromSweep,
const FHitResult& SweepResult);
UFUNCTION()
virtual void OnOuterBeginOverlap(UPrimitiveComponent* OverlappedComponent, AActor* OtherActor,
UPrimitiveComponent* OtherComp, int32 OtherBodyIndex, bool bFromSweep,
const FHitResult& SweepResult);
UFUNCTION()
void TimelineCallback(float val);
UFUNCTION()
void TimelineFinishedCallback();
UFUNCTION(BlueprintCallable)
void PlayTimeLine();
};

View File

@ -48,6 +48,7 @@ APlayerCharacter::APlayerCharacter()
HealthBarWidgetComponent->SetRelativeLocation(FVector(0, 0, 90));
HealthBarWidgetComponent->SetTwoSided(true);
HealthBarWidgetComponent->SetBackgroundColor(FLinearColor(1, 1, 1, 0));
HealthBarWidgetComponent->SetCollisionEnabled(ECollisionEnabled::NoCollision);
}
void APlayerCharacter::BeginPlay()