Help with projectiles and aiming

So I am working on a simple 3rd person shooter and I am a total noob.

When firing projectiles, everything works fine except when aiming up or down, the projectiles still just go straight. They work fine when aiming side to side, but not up or down. I have tried to do my own research on this but everything I’ve found is either in Blueprints, for a FPS or just never had a solution. I will share my code below and hopefully someone can tell me what I am missing/doing wrong. On top of being a 3rd person shooter the camera is also at a 30 degree angle, making it just slightly top down, since I am sure that info matters. I hope I am making sense, and thanks to anyone and everyone in advance.

AGun::AGun()
{
// 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;

Root = CreateDefaultSubobject<USceneComponent>(TEXT("Root"));
SetRootComponent(Root);

Mesh = CreateDefaultSubobject<USkeletalMeshComponent>(TEXT("Mesh"));
Mesh->SetupAttachment(Root);

ProjectileSpawnPoint = CreateDefaultSubobject<USceneComponent>(TEXT("Spawn Point"));
ProjectileSpawnPoint->SetupAttachment(Mesh);

}

// Called when the game starts or when spawned
void AGun::BeginPlay()
{
Super::BeginPlay();
}

// Called every frame
void AGun::Tick(float DeltaTime)
{
Super::Tick(DeltaTime);

}

void AGun::PullTrigger()
{
UGameplayStatics::SpawnEmitterAttached(MuzzleFlash, Mesh, TEXT(“MuzzleFlashSocket”));

FVector ProjectileLocation = ProjectileSpawnPoint->GetComponentLocation();
const FRotator ProjectileRotation =  GetOwner()->GetActorRotation();
AProjectile* Projectile = GetWorld()->SpawnActor<AProjectile>(ProjectileClass, ProjectileLocation, ProjectileRotation);		Projectile->SetOwner(this);
UGameplayStatics::SpawnEmitterAttached(ProjectileBeam, ProjectileSpawnPoint, TEXT("ProjectileBeamSocket"));

FHitResult Hit;
FVector ShotDirection;
bool bSuccess = GunTrace(Hit, ShotDirection);
if(bSuccess)
{
//	UGameplayStatics::SpawnEmitterAtLocation(GetWorld(), ImpactEffect, Hit.Location, ShotDirection.Rotation());
//	UGameplayStatics::PlaySoundAtLocation(GetWorld(), ImpactSound, Hit.Location);
	
	AActor* HitActor = Hit.GetActor();
	if (HitActor != nullptr)
	{
		FPointDamageEvent DamageEvent(Damage, Hit, ShotDirection, nullptr);
		AController* OwnerController = GetOwnerController();
		HitActor->TakeDamage(DamageAmount, DamageEvent, OwnerController, this);
	}
}

}

bool AGun::GunTrace(FHitResult& Hit, FVector& ShotDirection)
{
AController* OwnerController = GetOwnerController();
if (OwnerController == nullptr) return false;

FVector Location;
FRotator Rotation;
OwnerController->GetPlayerViewPoint(Location, Rotation);
ShotDirection = -Rotation.Vector();

FVector End = Location + Rotation.Vector() * MaxRange;
FCollisionQueryParams Params;
Params.AddIgnoredActor(this);
Params.AddIgnoredActor(GetOwner());
return GetWorld()->LineTraceSingleByChannel(Hit, Location, End, ECC_GameTraceChannel1, Params);

}

AController* AGun::GetOwnerController() const
{
APawn* OwnerPawn = Cast(GetOwner());
if (OwnerPawn == nullptr) return false;
return OwnerPawn->GetController();
}

Above this is all of the code used for the gun, below will be for the projectile:

AProjectile::AProjectile()
{
// 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;

ProjectileMesh = CreateDefaultSubobject<UStaticMeshComponent>(TEXT("Projectile Mesh"));
RootComponent = ProjectileMesh;

ProjectileMovementComponent = CreateDefaultSubobject<UProjectileMovementComponent>(TEXT("Projectile Movement Component"));	
ProjectileMovementComponent->MaxSpeed = 10000;
ProjectileMovementComponent->InitialSpeed = 5000;

}

// Called when the game starts or when spawned
void AProjectile::BeginPlay()
{
Super::BeginPlay();

ProjectileMesh->OnComponentHit.AddDynamic(this, &AProjectile::OnHit);

}

// Called every frame
void AProjectile::Tick(float DeltaTime)
{
Super::Tick(DeltaTime);

}

void AProjectile::OnHit(UPrimitiveComponent* HitComp, AActor* OtherActor, UPrimitiveComponent* OtherComp, FVector NormalImpulse, const FHitResult& Hit)
{
AActor* MyOwner = GetOwner();
if (MyOwner == nullptr)
{
return;
}

AController* MyOwnerInstigator = MyOwner->GetInstigatorController();
UClass* DamageTypeClass = UDamageType::StaticClass();

if (OtherActor && OtherActor != this && OtherActor != MyOwner)
{
	UGameplayStatics::ApplyDamage(OtherActor, Damage, MyOwnerInstigator, this, DamageTypeClass);
	Destroy();
}

}

This is for the character:

AMainCharacter::AMainCharacter()
{
// Set this character to call Tick() every frame. You can turn this off to improve performance if you don’t need it.
PrimaryActorTick.bCanEverTick = true;

GetCharacterMovement()->bOrientRotationToMovement = true;

bUseControllerRotationYaw = true;
bUseControllerRotationPitch = true;
this->bUseControllerRotationPitch = false;

}

// Called when the game starts or when spawned
void AMainCharacter::BeginPlay()
{
Super::BeginPlay();

MainCharacterController = Cast<APlayerController>(GetController());

Health = MaxHealth;

Gun = GetWorld()->SpawnActor<AGun>(GunClass);

Gun->AttachToComponent(GetMesh(), FAttachmentTransformRules::KeepRelativeTransform, TEXT("WeaponSocket"));
Gun->SetOwner(this);

}
// Called every frame
void AMainCharacter::Tick(float DeltaTime)
{
Super::Tick(DeltaTime);

}

// Called to bind functionality to input
void AMainCharacter::SetupPlayerInputComponent(UInputComponent* PlayerInputComponent)
{
Super::SetupPlayerInputComponent(PlayerInputComponent);

PlayerInputComponent->BindAxis(TEXT("MoveForward"), this, &AMainCharacter::MoveForward);
PlayerInputComponent->BindAxis(TEXT("MoveRight"), this, &AMainCharacter::MoveRight);
PlayerInputComponent->BindAxis(TEXT("Turn"), this, &APawn::AddControllerYawInput);
PlayerInputComponent->BindAxis("LookUp", this, &AMainCharacter::LookUp);

PlayerInputComponent->BindAction(TEXT("Jump"), IE_Pressed, this, &ACharacter::Jump);
PlayerInputComponent->BindAction(TEXT("Fire"), IE_Pressed, this, &AMainCharacter::Fire);

}

void AMainCharacter::MoveForward(float Value)
{
AddMovementInput(GetActorForwardVector() * Value);
}

void AMainCharacter::MoveRight(float Value)
{
AddMovementInput(GetActorRightVector() * Value);
}

float CurrentPitch = 0.0f;

void AMainCharacter::LookUp(float Value)
{

if (Controller != nullptr && Value != 0.0f)
{
    // Get the current control rotation
    FRotator Rotation = Controller->GetControlRotation();

    // Manually track the current pitch and clamp the new pitch
    CurrentPitch = FMath::Clamp(CurrentPitch + Value, MinPitch, MaxPitch);

    // Apply the clamped pitch, keeping yaw and roll unchanged
    Rotation.Pitch = CurrentPitch;
    Controller->SetControlRotation(Rotation);
}

}

void AMainCharacter::Fire()
{
Gun->PullTrigger();
}

float AMainCharacter::TakeDamage(float DamageAmount, struct FDamageEvent const& DamageEvent, class AController* EventInstigator, AActor* DamageCauser)
{
float DamageApplied = Super::TakeDamage(DamageAmount, DamageEvent, EventInstigator, DamageCauser);
DamageApplied = FMath::Min(Health, DamageApplied);
Health -= DamageApplied;
UE_LOG(LogTemp, Warning, TEXT(“Health Left %f”), Health);

if (IsDead())
{
    DetachFromControllerPendingDestroy();
    GetCapsuleComponent()->SetCollisionEnabled(ECollisionEnabled::NoCollision);

    ACowboyBeepBoopGameModeBase* GameMode = GetWorld()->GetAuthGameMode<ACowboyBeepBoopGameModeBase>();
    if (GameMode != nullptr)
    {
        GameMode->CharacterKilled(this);
    }
}
return DamageApplied;

}

bool AMainCharacter::IsDead() const
{
return Health <= 0;
}

Hope this helps someone help me lol.

Thanks, again