climbing mode polished
This commit is contained in:
@@ -20,68 +20,7 @@ void UCustomCharacterMovementComponent::PhysCustom(float DeltaTime, int32 Iterat
|
||||
{
|
||||
case 0:
|
||||
{
|
||||
if (DeltaTime < MIN_TICK_TIME)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
RestorePreAdditiveRootMotionVelocity();
|
||||
|
||||
if (!HasAnimRootMotion() && !CurrentRootMotion.HasOverrideVelocity())
|
||||
{
|
||||
if (bCheatFlying && Acceleration.IsZero())
|
||||
{
|
||||
Velocity = FVector::ZeroVector;
|
||||
}
|
||||
//const float Friction = 0.5f * GetPhysicsVolume()->FluidFriction;
|
||||
constexpr float Friction = 5.f;
|
||||
CalcVelocity(DeltaTime, Friction, true, GetMaxBrakingDeceleration());
|
||||
}
|
||||
|
||||
ApplyRootMotionToVelocity(DeltaTime);
|
||||
|
||||
bJustTeleported = false;
|
||||
|
||||
FVector OldLocation = UpdatedComponent->GetComponentLocation();
|
||||
const FVector Adjusted = Velocity * DeltaTime;
|
||||
FHitResult Hit(1.f);
|
||||
SafeMoveUpdatedComponent(Adjusted, UpdatedComponent->GetComponentQuat(), true, Hit);
|
||||
|
||||
if (Hit.Time < 1.f)
|
||||
{
|
||||
SlideAlongSurface(Velocity * DeltaTime, 1.f - Hit.Time, Hit.Normal, Hit, true);
|
||||
}
|
||||
|
||||
const ACharacter* Character = Cast<ACharacter>(GetOwner());
|
||||
FHitResult WallHit;
|
||||
const bool bWallFound = SweepForwardForWall(Character, WallHit);
|
||||
if (bWallFound)
|
||||
{
|
||||
const FVector SurfaceNormal = WallHit.Normal;
|
||||
|
||||
// Update Location
|
||||
const FVector TargetLocation = WallHit.Location + (SurfaceNormal * 0.1f);
|
||||
const FVector NewLocation = FMath::VInterpTo(UpdatedComponent->GetComponentLocation(), TargetLocation, DeltaTime, 2.f);
|
||||
UpdatedComponent->SetWorldLocation(NewLocation);
|
||||
|
||||
// Update Rotation
|
||||
const FRotator TargetRotation = FRotationMatrix::MakeFromXZ(-SurfaceNormal, FVector::UpVector).Rotator();
|
||||
const FRotator NewRotation = FMath::RInterpTo(UpdatedComponent->GetComponentRotation(), TargetRotation, DeltaTime, 2.f);
|
||||
UpdatedComponent->SetWorldRotation(NewRotation);
|
||||
}
|
||||
else
|
||||
{
|
||||
// Reset Rotation and set MovementMode to Falling
|
||||
const FRotator NewRotation = FRotator(0.0f, UpdatedComponent->GetComponentRotation().Yaw, 0.0f);
|
||||
UpdatedComponent->SetWorldRotation(NewRotation);
|
||||
SetMovementMode(MOVE_Falling);
|
||||
}
|
||||
|
||||
if (!bJustTeleported && !HasAnimRootMotion() && !CurrentRootMotion.HasOverrideVelocity())
|
||||
{
|
||||
Velocity = (UpdatedComponent->GetComponentLocation() - OldLocation) / DeltaTime;
|
||||
}
|
||||
|
||||
PhysClimbing(DeltaTime, Iterations);
|
||||
break;
|
||||
}
|
||||
|
||||
@@ -93,6 +32,81 @@ void UCustomCharacterMovementComponent::PhysCustom(float DeltaTime, int32 Iterat
|
||||
}
|
||||
}
|
||||
|
||||
void UCustomCharacterMovementComponent::PhysClimbing(float DeltaTime, int32 Iterations)
|
||||
{
|
||||
if (DeltaTime < MIN_TICK_TIME)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
RestorePreAdditiveRootMotionVelocity();
|
||||
|
||||
if (!HasAnimRootMotion() && !CurrentRootMotion.HasOverrideVelocity())
|
||||
{
|
||||
if (bCheatFlying && Acceleration.IsZero())
|
||||
{
|
||||
Velocity = FVector::ZeroVector;
|
||||
}
|
||||
//const float Friction = 0.5f * GetPhysicsVolume()->FluidFriction;
|
||||
constexpr float Friction = 5.f;
|
||||
CalcVelocity(DeltaTime, Friction, true, GetMaxBrakingDeceleration());
|
||||
}
|
||||
|
||||
ApplyRootMotionToVelocity(DeltaTime);
|
||||
|
||||
bJustTeleported = false;
|
||||
|
||||
FVector OldLocation = UpdatedComponent->GetComponentLocation();
|
||||
const FVector Adjusted = Velocity * DeltaTime;
|
||||
FHitResult Hit(1.f);
|
||||
SafeMoveUpdatedComponent(Adjusted, UpdatedComponent->GetComponentQuat(), true, Hit);
|
||||
|
||||
if (Hit.Time < 1.f)
|
||||
{
|
||||
SlideAlongSurface(Velocity * DeltaTime, 1.f - Hit.Time, Hit.Normal, Hit, true);
|
||||
}
|
||||
|
||||
const ACharacter* Character = Cast<ACharacter>(GetOwner());
|
||||
FHitResult WallHit;
|
||||
const bool bWallFound = SweepForwardForWall(Character, WallHit);
|
||||
if (bWallFound)
|
||||
{
|
||||
const FVector SurfaceNormal = WallHit.Normal;
|
||||
|
||||
// Update Location
|
||||
const FVector TargetLocation = WallHit.Location + (SurfaceNormal * 0.1f);
|
||||
const FVector NewLocation = FMath::VInterpTo(UpdatedComponent->GetComponentLocation(), TargetLocation, DeltaTime, 2.f);
|
||||
UpdatedComponent->SetWorldLocation(NewLocation);
|
||||
|
||||
// Update Rotation
|
||||
FRotator TargetRotation = FRotationMatrix::MakeFromXZ(-SurfaceNormal, FVector::UpVector).Rotator();
|
||||
if (TargetRotation.Pitch < -70.0f)
|
||||
{
|
||||
TargetRotation = FRotator(0.0f, UpdatedComponent->GetComponentRotation().Yaw, 0.0f);
|
||||
UpdatedComponent->SetWorldRotation(TargetRotation);
|
||||
SetMovementMode(MOVE_Falling);
|
||||
GEngine->AddOnScreenDebugMessage(-1, 5.0f, FColor::Blue, TEXT("Standing up"));
|
||||
}
|
||||
else
|
||||
{
|
||||
const FRotator NewRotation = FMath::RInterpTo(UpdatedComponent->GetComponentRotation(), TargetRotation, DeltaTime, 2.f);
|
||||
UpdatedComponent->SetWorldRotation(NewRotation);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
// Reset Rotation and set MovementMode to Falling
|
||||
const FRotator NewRotation = FRotator(0.0f, UpdatedComponent->GetComponentRotation().Yaw, 0.0f);
|
||||
UpdatedComponent->SetWorldRotation(NewRotation);
|
||||
SetMovementMode(MOVE_Falling);
|
||||
}
|
||||
|
||||
if (!bJustTeleported && !HasAnimRootMotion() && !CurrentRootMotion.HasOverrideVelocity())
|
||||
{
|
||||
Velocity = (UpdatedComponent->GetComponentLocation() - OldLocation) / DeltaTime;
|
||||
}
|
||||
}
|
||||
|
||||
void UCustomCharacterMovementComponent::OnMovementModeChanged(EMovementMode PreviousMovementMode, uint8 PreviousCustomMode)
|
||||
{
|
||||
Super::OnMovementModeChanged(PreviousMovementMode, PreviousCustomMode);
|
||||
|
||||
@@ -21,6 +21,7 @@ public:
|
||||
protected:
|
||||
// Override PhysCustom to handle custom movement mode behaviors
|
||||
virtual void PhysCustom(float DeltaTime, int32 Iterations) override;
|
||||
void PhysClimbing(float DeltaTime, int32 Iterations);
|
||||
virtual void OnMovementModeChanged(EMovementMode PreviousMovementMode, uint8 PreviousCustomMode) override;
|
||||
static bool SweepForwardForWall(const ACharacter* Character, FHitResult& OutHit, float SweepDistance = 100.f);
|
||||
};
|
||||
|
||||
Reference in New Issue
Block a user