Search Unity

Resolved Moving character on slopes with forces

Discussion in 'Scripting' started by Phoenix248, Oct 26, 2022.

  1. Phoenix248

    Phoenix248

    Joined:
    Sep 20, 2019
    Posts:
    52
    Hi everyone!

    I'm having problems with slopes in the movement system I'm currently working on.

    The code uses forces to have a smooth movement with acceleration and deacceleration, as following:

    Code (CSharp):
    1.      public void OnFixedUpdate()
    2.     {
    3.         float targetSpeed = Vector2Int.RoundToInt(inputManager.moveAction.ReadValue<Vector2>()).x * player.playerMoveSpeed;
    4.         float speedDifference = targetSpeed - player.playerRigidbody.velocity.x;
    5.         float accelerationRate = (Mathf.Abs(targetSpeed) > 0.01f) ? player.playerAcceleration : player.playerDeacceleration;
    6.  
    7.         float movementForce = Mathf.Pow(Mathf.Abs(speedDifference) * accelerationRate, player.velocityPower) * Mathf.Sign(speedDifference);
    8.  
    9.         Vector2 moveDirection = -Vector2.Perpendicular(player.GetFloorHighestSensor().normal);
    10.  
    11.         player.playerRigidbody.AddForce(moveDirection * movementForce);
    12.  
    13.     }
    To get the direction of movement, It casts a ray down and calculate the perpendicular from the normal of the point hitted, this way the player able to walk up and down slopes.

    The behaviour I wish to avoid is a bump that happends when the player crosses the top of the slope.
    Example2.PNG

    Any ideas on how to implement this?
     
  2. Kurt-Dekker

    Kurt-Dekker

    Joined:
    Mar 16, 2013
    Posts:
    38,689
    You know that forces are not necessary for smooth movement, right?

    Smoothing movement between any two particular values:

    https://forum.unity.com/threads/beginner-need-help-with-smoothdamp.988959/#post-6430100

    You have currentQuantity and desiredQuantity.
    - only set desiredQuantity
    - the code always moves currentQuantity towards desiredQuantity
    - read currentQuantity for the smoothed value

    Works for floats, Vectors, Colors, Quaternions, anything continuous or lerp-able.

    The code: https://gist.github.com/kurtdekker/fb3c33ec6911a1d9bfcb23e9f62adac4
     
  3. Phoenix248

    Phoenix248

    Joined:
    Sep 20, 2019
    Posts:
    52
    Thanks! managed to find a solution. The code is the following:

    Code (CSharp):
    1.       public void OnFixedUpdate()
    2.     {
    3.        
    4.         Vector2 moveDirection = -Vector2.Perpendicular(player.GetFloorHighestSensor().normal);
    5.  
    6.         float targetSpeed = Vector2Int.RoundToInt(inputManager.moveAction.ReadValue<Vector2>()).x * player.playerMoveSpeed * Time.deltaTime;
    7.         float accelerationRate = player.playerAcceleration;
    8.         float movementForce = Mathf.MoveTowards(Mathf.Abs(player.playerRigidbody.velocity.magnitude) * Mathf.Sign(player.playerRigidbody.velocity.x), targetSpeed, accelerationRate * Time.deltaTime);
    9.  
    10.         player.playerRigidbody.velocity = moveDirection * movementForce;
    11.     }
    For anyone that may take this as a base in the future, be sure to have long raycasts down, to avoid the player getting ungrounded when crossing corners.