2

I'm working on a custom character in Unreal Engine 5. I want the player to have his velocity direction based on mouse movement when he is in the air.

For example, when you jump forward and move your mouse right, he should follow the new direction, but if you jump backwards and move your mouse right, it will change direction towards where your back is looking.

allejack
  • 33
  • 5
  • 1
    I am not familiar with unreal-engine, but given the calculation inside your snippet above is probably based on Vectorial Calculus, you should first compute the amplitude (absolute value) of your `Velocity` vector, and then project it in the direction the character is looking at – Giogre Aug 19 '22 at 18:39
  • @Giogre thanks for the hint, I will try to implement it – allejack Aug 19 '22 at 19:15
  • `-UpdatedComponent->GetForwardVector()` should be the same of `UpdatedComponent->GetBackwardVector()`. Same thing for `-GetRightVector()` and `GetLeftVector()`. It is obviously a vectorial problem. You should try to obtain the angle between the direction the character is facing and the current direction of `Velocity`. Then you need to define a vector that points in the direction of this angle, similar to how `GetForwardVector()` is defined for the forward direction. – Giogre Aug 20 '22 at 10:37

1 Answers1

1

I created a custom character movement component and overrode CalcVelocity() method:

// AirControl = 0;
// AirControlBoostMultiplier = 0;
// AirControlBoostVelocityThreshold = 0;

void UCustomCharacterMovementComponent::CalcVelocity(const float DeltaTime, const float Friction, const bool bFluid, const float BrakingDeceleration)
{
    Super::CalcVelocity(DeltaTime, Friction, bFluid, BrakingDeceleration);

    if (IsMovingOnGround() && Velocity.Size() > 0) {
        const FVector NewDirection = UKismetMathLibrary::InverseTransformDirection(GetActorTransform(), Velocity);
        LastYawOnGround = FMath::CeilToInt(FRotationMatrix::MakeFromX(NewDirection).Rotator().Yaw);
    }

    // Air control for mouse movement to change direction mid-air after jumping
    if (!IsMovingOnGround()) {
        FVector VelocityDirection;
        const bool IsMovingForward = UKismetMathLibrary::InRange_IntInt(LastYawOnGround, -22, 0) || UKismetMathLibrary::InRange_IntInt(LastYawOnGround, 0, 22);
        const bool IsMovingForwardRight = UKismetMathLibrary::InRange_IntInt(LastYawOnGround, 23, 67);
        const bool IsMovingRight = UKismetMathLibrary::InRange_IntInt(LastYawOnGround, 68, 112);
        const bool IsMovingBackwardRight = UKismetMathLibrary::InRange_IntInt(LastYawOnGround, 113, 157);
        const bool IsMovingBackward = UKismetMathLibrary::InRange_IntInt(LastYawOnGround, -180, -158) || UKismetMathLibrary::InRange_IntInt(LastYawOnGround, 158, 180);
        const bool IsMovingBackwardLeft = UKismetMathLibrary::InRange_IntInt(LastYawOnGround, -157, -113);
        const bool IsMovingLeft = UKismetMathLibrary::InRange_IntInt(LastYawOnGround, -112, -68);
        const bool IsMovingForwardLeft = UKismetMathLibrary::InRange_IntInt(LastYawOnGround, -67, -23);

        if (IsMovingForward) {
            VelocityDirection = UpdatedComponent->GetForwardVector();
        } else if (IsMovingBackward) {
            VelocityDirection = -UpdatedComponent->GetForwardVector();
        } else if (IsMovingRight) {
            VelocityDirection = UpdatedComponent->GetRightVector();
        } else if (IsMovingLeft) {
            VelocityDirection = -UpdatedComponent->GetRightVector();
        } else {
            if (IsMovingForwardRight) {
                VelocityDirection = UpdatedComponent->GetForwardVector() + UpdatedComponent->GetRightVector();
            } else if (IsMovingForwardLeft) {
                VelocityDirection = UpdatedComponent->GetForwardVector() - UpdatedComponent->GetRightVector();
            } else if (IsMovingBackwardRight) {
                VelocityDirection = UpdatedComponent->GetRightVector() - UpdatedComponent->GetForwardVector();
            } else if (IsMovingBackwardLeft) {
                VelocityDirection = -(UpdatedComponent->GetForwardVector() + UpdatedComponent->GetRightVector());
            }
            
            VelocityDirection = UKismetMathLibrary::Normal(VelocityDirection / 2);
        }

        Velocity -= Velocity - VelocityDirection * Velocity.Size();
    }
}
allejack
  • 33
  • 5