From ca23fd129e1c09e7be6d43b77974c9efcfef078b Mon Sep 17 00:00:00 2001 From: aicorr Date: Tue, 15 Apr 2025 14:51:25 +0530 Subject: [PATCH] Modify movement implementation for more arcade feel and add strafing --- Content/Blueprints/BP_SpaceshipPawn.uasset | 4 +- Content/Input/IA_Fire.uasset | 3 - Content/Input/IA_MouseControl.uasset | 3 - Content/Input/IA_Movement.uasset | 3 - Content/Input/IA_Strafe.uasset | 3 + Content/Input/IMC_Spaceship.uasset | 4 +- Content/Main.umap | 2 +- Source/MyProject3/SpaceshipPawn.cpp | 249 +++++++++++++-------- Source/MyProject3/SpaceshipPawn.h | 62 +++-- 9 files changed, 209 insertions(+), 124 deletions(-) delete mode 100644 Content/Input/IA_Fire.uasset delete mode 100644 Content/Input/IA_MouseControl.uasset delete mode 100644 Content/Input/IA_Movement.uasset create mode 100644 Content/Input/IA_Strafe.uasset diff --git a/Content/Blueprints/BP_SpaceshipPawn.uasset b/Content/Blueprints/BP_SpaceshipPawn.uasset index f8298f2..1e016f0 100644 --- a/Content/Blueprints/BP_SpaceshipPawn.uasset +++ b/Content/Blueprints/BP_SpaceshipPawn.uasset @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:6e6f3deee01a0b19b9c895fbe7016d28aece167815e6a162920bda72d78b13ce -size 34050 +oid sha256:893e409859f0f7be4ae3671727ed2c0a6f69187d59f6273f281059d39d6147b7 +size 34023 diff --git a/Content/Input/IA_Fire.uasset b/Content/Input/IA_Fire.uasset deleted file mode 100644 index 2c38c54..0000000 --- a/Content/Input/IA_Fire.uasset +++ /dev/null @@ -1,3 +0,0 @@ -version https://git-lfs.github.com/spec/v1 -oid sha256:ae605926b5b53716d40570253d37a1840bac73432d9ac462349277ec939a9226 -size 1886 diff --git a/Content/Input/IA_MouseControl.uasset b/Content/Input/IA_MouseControl.uasset deleted file mode 100644 index 6704ae7..0000000 --- a/Content/Input/IA_MouseControl.uasset +++ /dev/null @@ -1,3 +0,0 @@ -version https://git-lfs.github.com/spec/v1 -oid sha256:622501565ea35f90e1771712aa99273c84b3db2b83d0f2c081845cf2c952174b -size 2121 diff --git a/Content/Input/IA_Movement.uasset b/Content/Input/IA_Movement.uasset deleted file mode 100644 index 30c3d47..0000000 --- a/Content/Input/IA_Movement.uasset +++ /dev/null @@ -1,3 +0,0 @@ -version https://git-lfs.github.com/spec/v1 -oid sha256:e6487004cf0390897bb5d1cb21e0a449aaae32e25464fadeec8c97addd052be3 -size 2064 diff --git a/Content/Input/IA_Strafe.uasset b/Content/Input/IA_Strafe.uasset new file mode 100644 index 0000000..bf170a2 --- /dev/null +++ b/Content/Input/IA_Strafe.uasset @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:3a096c2cddf7c6518c4fc963d5bb28dcf48bc82a3bdaaa77d6b4073a31008934 +size 2231 diff --git a/Content/Input/IMC_Spaceship.uasset b/Content/Input/IMC_Spaceship.uasset index 6c487b2..ff6cdb0 100644 --- a/Content/Input/IMC_Spaceship.uasset +++ b/Content/Input/IMC_Spaceship.uasset @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:7835df7e64bc032143d479af01dc03b4d39585eec741c69310ccd7a0e6da5678 -size 5521 +oid sha256:3c44c65a25ea333f5b62374427b038201f0d2f16de9580c743958f4190c13d5e +size 6983 diff --git a/Content/Main.umap b/Content/Main.umap index 56495fb..23a8717 100644 --- a/Content/Main.umap +++ b/Content/Main.umap @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:87546dfde9836da19f987e46383c1a97ac03c48a765968adf11f80f7c9e8eada +oid sha256:9d9747ae79aa7a7c0c33443fea565a73bf3d5d7e3fdbfc80b1d5fd8144a59743 size 70812 diff --git a/Source/MyProject3/SpaceshipPawn.cpp b/Source/MyProject3/SpaceshipPawn.cpp index 9690b11..26d775f 100644 --- a/Source/MyProject3/SpaceshipPawn.cpp +++ b/Source/MyProject3/SpaceshipPawn.cpp @@ -32,19 +32,19 @@ ASpaceshipPawn::ASpaceshipPawn() CameraSpringArm->CameraLagSpeed = 10.0f; CameraSpringArm->bEnableCameraRotationLag = true; CameraSpringArm->CameraRotationLagSpeed = 10.0f; - CameraSpringArm->CameraLagMaxDistance = 7.0f; - CameraSpringArm->bUsePawnControlRotation = false; // Add this line - CameraSpringArm->bInheritPitch = true; // Add this line - CameraSpringArm->bInheritYaw = true; // Add this line - CameraSpringArm->bInheritRoll = false; // Add this line + CameraSpringArm->CameraLagMaxDistance = 7.0f; + CameraSpringArm->bUsePawnControlRotation = false; + CameraSpringArm->bInheritPitch = true; + CameraSpringArm->bInheritYaw = true; + CameraSpringArm->bInheritRoll = false; // Create camera Camera = CreateDefaultSubobject(TEXT("Camera")); Camera->SetupAttachment(CameraSpringArm, USpringArmComponent::SocketName); // Initialize movement variables - CurrentThrust = 0.0f; - TargetThrust = 0.0f; + CurrentThrottleInput = 0.0f; + CurrentStrafeInput = 0.0f; bThrottlePressed = false; CurrentVelocity = FVector::ZeroVector; CurrentPitch = 0.0f; @@ -110,15 +110,49 @@ void ASpaceshipPawn::Tick(float DeltaTime) { Super::Tick(DeltaTime); + // Update ship rotation first (common to all movement modes) + UpdateShipRotation(DeltaTime); + + // Handle movement based on the selected movement mode + switch (MovementMode) + { + case EShipMovementMode::Arcade: + UpdateArcadeMovement(DeltaTime); + break; + + case EShipMovementMode::Assisted: + UpdateAssistedMovement(DeltaTime); + break; + + case EShipMovementMode::Realistic: + UpdateRealisticMovement(DeltaTime); + break; + } + + // Update position + FVector NewLocation = GetActorLocation() + (CurrentVelocity * DeltaTime); + SetActorLocation(NewLocation, true); + + // Reset mouse delta for next frame + LastMouseDelta = FVector2D::ZeroVector; + // Debug info if (GEngine) { GEngine->AddOnScreenDebugMessage(-1, 0.0f, FColor::Yellow, - FString::Printf(TEXT("Thrust: %.2f"), CurrentThrust)); - GEngine->AddOnScreenDebugMessage(-1, 0.0f, FColor::Green, - FString::Printf(TEXT("Velocity: %.2f"), CurrentVelocity.Size())); - } + FString::Printf(TEXT("Mode: %s | Speed: %.1f"), + MovementMode == EShipMovementMode::Arcade ? TEXT("Arcade") : + MovementMode == EShipMovementMode::Assisted ? TEXT("Assisted") : TEXT("Realistic"), + CurrentVelocity.Size())); + GEngine->AddOnScreenDebugMessage(-1, 0.0f, FColor::Green, + FString::Printf(TEXT("Throttle: %.2f | Strafe: %.2f"), + CurrentThrottleInput, CurrentStrafeInput)); + } +} + +void ASpaceshipPawn::UpdateShipRotation(float DeltaTime) +{ // Smooth mouse movement MouseDeltaSmoothed = FMath::Vector2DInterpTo( MouseDeltaSmoothed, @@ -128,7 +162,7 @@ void ASpaceshipPawn::Tick(float DeltaTime) ); // Update rotation based on smoothed mouse movement - CurrentYaw += MouseDeltaSmoothed.X * MouseSensitivity * DeltaTime * 60.0f; // Multiply by 60 to normalize for frame rate + CurrentYaw += MouseDeltaSmoothed.X * MouseSensitivity * DeltaTime * 60.0f; CurrentPitch = FMath::ClampAngle( CurrentPitch + (MouseDeltaSmoothed.Y * MouseSensitivity * DeltaTime * 60.0f), -85.0f, @@ -144,67 +178,6 @@ void ASpaceshipPawn::Tick(float DeltaTime) FQuat NewQuat = FQuat::Slerp(CurrentQuat, TargetQuat, RotationSpeed * DeltaTime); SetActorRotation(NewQuat); - // Get the current forward vector - FVector CurrentDirection = GetActorForwardVector(); - float CurrentSpeed = CurrentVelocity.Size(); - - // Handle thrust and velocity direction - if (!bThrottlePressed) - { - // Decelerate when not thrusting - CurrentThrust = FMath::FInterpTo(CurrentThrust, 0.0f, DeltaTime, ThrustDeceleration); - bWasThrottlePressed = false; - - // Maintain current velocity direction when not thrusting - DesiredVelocityDirection = CurrentVelocity.GetSafeNormal(); - } - else - { - // Accelerate when thrusting - CurrentThrust = FMath::FInterpConstantTo(CurrentThrust, TargetThrust, DeltaTime, ThrustAcceleration); - - if (!bWasThrottlePressed) - { - // Just started thrusting - blend between current and new direction - if (!CurrentVelocity.IsNearlyZero()) - { - // Blend between current velocity direction and new direction - FVector CurrentDir = CurrentVelocity.GetSafeNormal(); - DesiredVelocityDirection = FMath::Lerp(CurrentDir, CurrentDirection, 1.0f - DirectionalInertia); - DesiredVelocityDirection.Normalize(); - } - else - { - // If nearly stationary, use new direction - DesiredVelocityDirection = CurrentDirection; - } - } - else - { - // Continuously blend towards current facing direction while thrusting - DesiredVelocityDirection = FMath::VInterpNormalRotationTo( - DesiredVelocityDirection, - CurrentDirection, - DeltaTime, - VelocityAlignmentSpeed - ); - } - bWasThrottlePressed = true; - } - - // Calculate thrust force - FVector ThrustForce = CurrentDirection * CurrentThrust; - - // Apply drag - FVector DragForce = -CurrentVelocity * DragCoefficient; - - // Update velocity with forces - CurrentVelocity += (ThrustForce + DragForce) * DeltaTime; - - // Update position - FVector NewLocation = GetActorLocation() + (CurrentVelocity * DeltaTime); - SetActorLocation(NewLocation, true); - // Update spring arm rotation to match ship with smooth interpolation if (CameraSpringArm) { @@ -218,17 +191,106 @@ void ASpaceshipPawn::Tick(float DeltaTime) ); CameraSpringArm->SetWorldRotation(NewSpringArmRotation); } +} - // Reset mouse delta for next frame - LastMouseDelta = FVector2D::ZeroVector; +void ASpaceshipPawn::UpdateArcadeMovement(float DeltaTime) +{ + // In arcade mode, the ship moves exactly where it's pointed with minimal inertia + FVector ForwardVector = GetActorForwardVector(); + FVector RightVector = GetActorRightVector(); - // Debug info - if (GEngine) + // Calculate desired velocity (forward/back + strafe) + FVector DesiredVelocity = (ForwardVector * CurrentThrottleInput * MaxSpeed) + + (RightVector * CurrentStrafeInput * (MaxSpeed * 0.7f)); // Strafe is slightly slower + + // Smoothly interpolate current velocity to desired velocity + if (!FMath::IsNearlyZero(CurrentThrottleInput) || !FMath::IsNearlyZero(CurrentStrafeInput)) { - GEngine->AddOnScreenDebugMessage(-1, 0.0f, FColor::Yellow, - FString::Printf(TEXT("Smoothed Mouse Delta: X=%.2f Y=%.2f"), MouseDeltaSmoothed.X, MouseDeltaSmoothed.Y)); - GEngine->AddOnScreenDebugMessage(-1, 0.0f, FColor::Green, - FString::Printf(TEXT("Current Rotation: P=%.2f Y=%.2f"), CurrentPitch, CurrentYaw)); + // Accelerating + CurrentVelocity = FMath::VInterpTo( + CurrentVelocity, + DesiredVelocity, + DeltaTime, + Acceleration / MaxSpeed + ); + } + else if (bAutoBrakeEnabled) + { + // Auto-braking when no input + CurrentVelocity = FMath::VInterpTo( + CurrentVelocity, + FVector::ZeroVector, + DeltaTime, + AutoBrakeStrength + ); + } + else + { + // Gradual deceleration + float Speed = CurrentVelocity.Size(); + if (Speed > 0) + { + Speed = FMath::FInterpTo(Speed, 0, DeltaTime, Deceleration / MaxSpeed); + CurrentVelocity = CurrentVelocity.GetSafeNormal() * Speed; + } + } +} + +void ASpaceshipPawn::UpdateAssistedMovement(float DeltaTime) +{ + // Assisted mode - a middle ground with some inertia but stabilization assistance + FVector ForwardVector = GetActorForwardVector(); + FVector RightVector = GetActorRightVector(); + + // Calculate thrust force + FVector ThrustForce = (ForwardVector * CurrentThrottleInput * Acceleration) + + (RightVector * CurrentStrafeInput * (Acceleration * 0.7f)); + + // Apply thrust to velocity + CurrentVelocity += ThrustForce * DeltaTime; + + // Limit max speed + float CurrentSpeed = CurrentVelocity.Size(); + if (CurrentSpeed > MaxSpeed) + { + CurrentVelocity = CurrentVelocity.GetSafeNormal() * MaxSpeed; + } + + // Apply auto-stabilization (gradual slowdown) when not thrusting + if (FMath::IsNearlyZero(CurrentThrottleInput) && FMath::IsNearlyZero(CurrentStrafeInput) && bAutoBrakeEnabled) + { + CurrentVelocity = FMath::VInterpTo( + CurrentVelocity, + FVector::ZeroVector, + DeltaTime, + StabilizationSpeed + ); + } +} + +void ASpaceshipPawn::UpdateRealisticMovement(float DeltaTime) +{ + // This is the original physics-based movement with momentum + FVector CurrentDirection = GetActorForwardVector(); + FVector RightVector = GetActorRightVector(); + + // Calculate thrust force (forward + strafe) + FVector ThrustForce = (CurrentDirection * CurrentThrottleInput * Acceleration) + + (RightVector * CurrentStrafeInput * (Acceleration * 0.7f)); + + // Apply thrust to velocity + CurrentVelocity += ThrustForce * DeltaTime; + + // Apply drag + float DragCoefficient = 0.05f; + FVector DragForce = -CurrentVelocity * DragCoefficient; + CurrentVelocity += DragForce * DeltaTime; + + // Limit max speed + float CurrentSpeed = CurrentVelocity.Size(); + if (CurrentSpeed > MaxSpeed) + { + CurrentVelocity = CurrentVelocity.GetSafeNormal() * MaxSpeed; } } @@ -238,9 +300,14 @@ void ASpaceshipPawn::SetupPlayerInputComponent(UInputComponent* PlayerInputCompo if (UEnhancedInputComponent* EnhancedInputComponent = CastChecked(PlayerInputComponent)) { - // Bind both Hold and Released events for throttle - EnhancedInputComponent->BindAction(ThrottleAction, ETriggerEvent::Started, this, &ASpaceshipPawn::HandleThrottleStarted); - EnhancedInputComponent->BindAction(ThrottleAction, ETriggerEvent::Completed, this, &ASpaceshipPawn::HandleThrottleReleased); + // Bind throttle input + EnhancedInputComponent->BindAction(ThrottleAction, ETriggerEvent::Triggered, this, &ASpaceshipPawn::HandleThrottleInput); + + // Bind strafe input if available + if (StrafeAction) + { + EnhancedInputComponent->BindAction(StrafeAction, ETriggerEvent::Triggered, this, &ASpaceshipPawn::HandleStrafeInput); + } // Bind mouse control EnhancedInputComponent->BindAction(MouseLookAction, ETriggerEvent::Triggered, this, &ASpaceshipPawn::HandleMouseLook); @@ -250,24 +317,20 @@ void ASpaceshipPawn::SetupPlayerInputComponent(UInputComponent* PlayerInputCompo } } -// Split the throttle handling into two functions -void ASpaceshipPawn::HandleThrottleStarted(const FInputActionValue& Value) +void ASpaceshipPawn::HandleThrottleInput(const FInputActionValue& Value) { - const float ThrottleValue = Value.Get(); - bThrottlePressed = true; - TargetThrust = ThrottleValue * MaxThrust; + CurrentThrottleInput = Value.Get(); + bThrottlePressed = !FMath::IsNearlyZero(CurrentThrottleInput); } -void ASpaceshipPawn::HandleThrottleReleased(const FInputActionValue& Value) +void ASpaceshipPawn::HandleStrafeInput(const FInputActionValue& Value) { - bThrottlePressed = false; + CurrentStrafeInput = Value.Get(); } void ASpaceshipPawn::HandleMouseLook(const FInputActionValue& Value) { const FVector2D MouseDelta = Value.Get(); - - // Smoothly interpolate mouse delta LastMouseDelta = MouseDelta; } diff --git a/Source/MyProject3/SpaceshipPawn.h b/Source/MyProject3/SpaceshipPawn.h index 6922c78..49abce6 100644 --- a/Source/MyProject3/SpaceshipPawn.h +++ b/Source/MyProject3/SpaceshipPawn.h @@ -6,6 +6,15 @@ #include "Blueprint/UserWidget.h" #include "SpaceshipPawn.generated.h" +// Movement mode enum to allow switching between different control schemes +UENUM(BlueprintType) +enum class EShipMovementMode : uint8 +{ + Arcade, // Direct control, minimal inertia + Assisted, // Some inertia with auto-stabilization + Realistic // Full physics with momentum (original) +}; + UCLASS() class MYPROJECT3_API ASpaceshipPawn : public APawn { @@ -41,29 +50,45 @@ protected: // Movement Parameters UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Movement") - float MaxThrust = 2000.0f; + EShipMovementMode MovementMode = EShipMovementMode::Arcade; UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Movement") - float ThrustAcceleration = 500.0f; + float MaxSpeed = 2000.0f; UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Movement") - float ThrustDeceleration = 500.0f; + float Acceleration = 2000.0f; UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Movement") - float RotationSpeed = 100.0f; + float Deceleration = 1500.0f; + + UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Movement") + float RotationSpeed = 5.0f; UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Movement") float MouseSensitivity = 2.0f; - UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Movement") - float DragCoefficient = 0.05f; + // Auto-stabilization for assisted mode + UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Movement", meta = (ClampMin = "0.0", ClampMax = "10.0")) + float StabilizationSpeed = 3.0f; - // How quickly velocity aligns with new direction + // How much momentum to preserve when changing direction (0 = none, 1 = full) + UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Movement", meta = (ClampMin = "0.0", ClampMax = "1.0")) + float DirectionalInertia = 0.1f; + + // How quickly the ship aligns with its movement direction UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Movement", meta = (ClampMin = "0.0", ClampMax = "10.0")) float VelocityAlignmentSpeed = 4.0f; - UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Movement", meta = (ClampMin = "0.0", ClampMax = "1.0", ToolTip = "How much of the current velocity is maintained when changing direction (0 = none, 1 = full)")) - float DirectionalInertia = 0.3f; + // Auto-braking when not thrusting in Arcade mode + UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Movement") + bool bAutoBrakeEnabled = true; + + UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Movement") + float AutoBrakeStrength = 3.0f; + + // Add a strafe input to allow lateral movement + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Input") + class UInputAction* StrafeAction; // Shooting properties UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Combat") @@ -86,14 +111,14 @@ protected: UUserWidget* CrosshairWidget; // Input functions - void HandleThrottleStarted(const FInputActionValue& Value); - void HandleThrottleReleased(const FInputActionValue& Value); + void HandleThrottleInput(const FInputActionValue& Value); + void HandleStrafeInput(const FInputActionValue& Value); void HandleMouseLook(const FInputActionValue& Value); private: // Movement state - float CurrentThrust; - float TargetThrust; + float CurrentThrottleInput; + float CurrentStrafeInput; bool bThrottlePressed; FVector CurrentVelocity; FRotator TargetRotation; @@ -104,10 +129,7 @@ private: FVector2D MouseDeltaSmoothed; FVector2D LastMouseDelta; - float MouseSmoothingSpeed = 10.0f; - - bool bWasThrottlePressed; - FVector DesiredVelocityDirection; + float MouseSmoothingSpeed = 10.0f; FTimerHandle FireTimerHandle; bool bCanFire = true; @@ -115,4 +137,10 @@ private: void HandleShoot(const FInputActionValue& Value); void Fire(); void ResetFire(); + + // Movement helper functions + void UpdateArcadeMovement(float DeltaTime); + void UpdateAssistedMovement(float DeltaTime); + void UpdateRealisticMovement(float DeltaTime); + void UpdateShipRotation(float DeltaTime); }; \ No newline at end of file