diff --git a/Content/Blueprints/Weapon/BP_AssaultRifle.uasset b/Content/Blueprints/Weapon/BP_AssaultRifle.uasset index a76ea7f..f356d0d 100644 Binary files a/Content/Blueprints/Weapon/BP_AssaultRifle.uasset and b/Content/Blueprints/Weapon/BP_AssaultRifle.uasset differ diff --git a/Content/Blueprints/Weapon/Projectiles/BP_Projectile.uasset b/Content/Blueprints/Weapon/Projectiles/BP_Projectile.uasset new file mode 100644 index 0000000..8328e96 Binary files /dev/null and b/Content/Blueprints/Weapon/Projectiles/BP_Projectile.uasset differ diff --git a/Source/Blaster/Components/CombatComponent.cpp b/Source/Blaster/Components/CombatComponent.cpp index 432e7b5..97f315f 100644 --- a/Source/Blaster/Components/CombatComponent.cpp +++ b/Source/Blaster/Components/CombatComponent.cpp @@ -106,9 +106,11 @@ void UCombatComponent::TraceUnderCrosshairs(FHitResult& TraceHitResult) if (!TraceHitResult.bBlockingHit) { TraceHitResult.ImpactPoint = End; + HitTarget = End; } else { + HitTarget = TraceHitResult.ImpactPoint; DrawDebugSphere( GetWorld(), TraceHitResult.ImpactPoint, @@ -131,7 +133,7 @@ void UCombatComponent::MulticastFire_Implementation() if (Character) { Character->PlayFireMontage(bAiming); - EquippedWeapon->Fire(); + EquippedWeapon->Fire(HitTarget); } } diff --git a/Source/Blaster/Components/CombatComponent.h b/Source/Blaster/Components/CombatComponent.h index 764dda3..f667313 100644 --- a/Source/Blaster/Components/CombatComponent.h +++ b/Source/Blaster/Components/CombatComponent.h @@ -58,4 +58,6 @@ private: float AimWalkSpeed; bool bFireButtonPressed; + + FVector HitTarget; }; diff --git a/Source/Blaster/Weapon/ProjectileWeapon.cpp b/Source/Blaster/Weapon/ProjectileWeapon.cpp index c2a9878..1bfcb8d 100644 --- a/Source/Blaster/Weapon/ProjectileWeapon.cpp +++ b/Source/Blaster/Weapon/ProjectileWeapon.cpp @@ -3,3 +3,38 @@ #include "ProjectileWeapon.h" +#include "Projectile.h" +#include "Engine/SkeletalMeshSocket.h" + +void AProjectileWeapon::Fire(const FVector& HitTarget) +{ + Super::Fire(HitTarget); + + APawn* InstigatorPawn = Cast(GetOwner()); + const USkeletalMeshSocket* MuzzleFlashSocket = GetWeaponMesh()->GetSocketByName(FName("MuzzleFlash")); + if (MuzzleFlashSocket) + { + FTransform SocketTransform = MuzzleFlashSocket->GetSocketTransform(GetWeaponMesh()); + // From muzzle flash socket to hit location from TraceUnderCrosshairs + FVector ToTarget = HitTarget - SocketTransform.GetLocation(); + FRotator TargetRotation = ToTarget.Rotation(); + + if (ProjectileClass && InstigatorPawn) + { + FActorSpawnParameters SpawnParams; + SpawnParams.Owner = GetOwner(); + SpawnParams.Instigator = InstigatorPawn; + + UWorld* World = GetWorld(); + if (World) + { + World->SpawnActor( + ProjectileClass, + SocketTransform.GetLocation(), + TargetRotation, + SpawnParams + ); + } + } + } +} diff --git a/Source/Blaster/Weapon/ProjectileWeapon.h b/Source/Blaster/Weapon/ProjectileWeapon.h index f8e62b8..7437f09 100644 --- a/Source/Blaster/Weapon/ProjectileWeapon.h +++ b/Source/Blaster/Weapon/ProjectileWeapon.h @@ -13,7 +13,11 @@ UCLASS() class BLASTER_API AProjectileWeapon : public AWeapon { GENERATED_BODY() + virtual void Fire(const FVector& HitTarget) override; - +private: + + UPROPERTY(EditAnywhere) + TSubclassOf ProjectileClass; }; diff --git a/Source/Blaster/Weapon/Weapon.cpp b/Source/Blaster/Weapon/Weapon.cpp index 7dc73f3..e456805 100644 --- a/Source/Blaster/Weapon/Weapon.cpp +++ b/Source/Blaster/Weapon/Weapon.cpp @@ -109,7 +109,7 @@ void AWeapon::ShowPickupWidget(bool bShowWidget) } } -void AWeapon::Fire() +void AWeapon::Fire(const FVector& HitTarget) { if (FireAnimation) { diff --git a/Source/Blaster/Weapon/Weapon.h b/Source/Blaster/Weapon/Weapon.h index ba0bb6c..31dc2af 100644 --- a/Source/Blaster/Weapon/Weapon.h +++ b/Source/Blaster/Weapon/Weapon.h @@ -25,7 +25,7 @@ public: AWeapon(); virtual void GetLifetimeReplicatedProps(TArray& OutLifetimeProps) const override; void ShowPickupWidget(bool bShowWidget); - void Fire(); + virtual void Fire(const FVector& HitTarget); protected: virtual void BeginPlay() override;