Search Unity

  1. Good news ✨ We have more Unite Now videos available for you to watch on-demand! Come check them out and ask our experts any questions!
    Dismiss Notice

Help Wanted timeScale is messing up movement script.

Discussion in 'Physics' started by darthgameroff, Sep 16, 2020 at 4:38 AM.

  1. darthgameroff

    darthgameroff

    Joined:
    Wednesday
    Posts:
    1
    So I am using a wall run script provided by Dave / Gamedevelopment that he has created by using the fps movement script by Dani. I am super new to unity so this may be a simple fix but whenever I try to use Time.timeScale it slows the whole movement down to a crawl. When Time.timeScale is used it also seems to make gravity stronger and slows down the mouse sensitivity. For the time manger script I have followed the Brackeys tutorial cause as stated earlier, I am very new to all this. Any help would be greatly appreciated.

    Code (CSharp):
    1. using UnityEngine;
    2.  
    3. public class TimeManager : MonoBehaviour
    4. {
    5.     public float slowdownFactor = 0.05f;
    6.     public float slowdownLenght = 2f;
    7.  
    8.     void Update()
    9.     {
    10.         Time.timeScale += (1f / slowdownLenght) * Time.unscaledDeltaTime;
    11.         Time.timeScale = Mathf.Clamp(Time.timeScale, 0f, 1f);
    12.     }
    13.  
    14.     public void DoSlowmotion()
    15.     {
    16.         Time.timeScale = slowdownFactor;
    17.         Time.fixedDeltaTime = Time.timeScale * .02f;
    18.     }
    19.  
    20.    
    21. }

    Code (CSharp):
    1. using System;
    2. using UnityEngine;
    3.  
    4. public class WallRunTutorial : MonoBehaviour
    5. {
    6.     /// <summary>
    7.     /// Wall run Tutorial stuff, scroll down for full movement
    8.     /// </summary>
    9.  
    10.     //Wallrunning
    11.     public LayerMask whatIsWall;
    12.     public float wallrunForce, maxWallrunTime, maxWallSpeed;
    13.     bool isWallRight, isWallLeft;
    14.     bool isWallRunning;
    15.     public float maxWallRunCameraTilt, wallRunCameraTilt;
    16.  
    17.     public void WallRunInput() //make sure to call in void Update
    18.     {
    19.         //Wallrun
    20.         if (Input.GetKey(KeyCode.D) && isWallRight) StartWallrun();
    21.         if (Input.GetKey(KeyCode.A) && isWallLeft) StartWallrun();
    22.     }
    23.     public void StartWallrun()
    24.     {
    25.         rb.useGravity = false;
    26.         isWallRunning = true;
    27.  
    28.         if (rb.velocity.magnitude <= maxWallSpeed)
    29.         {
    30.             rb.AddForce(orientation.forward * wallrunForce * Time.fixedUnscaledDeltaTime);
    31.  
    32.             //Make sure char sticks to wall
    33.             if (isWallRight)
    34.                 rb.AddForce(orientation.right * wallrunForce / 5 * Time.fixedUnscaledDeltaTime);
    35.             else
    36.                 rb.AddForce(-orientation.right * wallrunForce / 5 * Time.fixedUnscaledDeltaTime);
    37.         }
    38.     }
    39.     public void StopWallRun()
    40.     {
    41.         isWallRunning = false;
    42.         rb.useGravity = true;
    43.     }
    44.     public void CheckForWall() //make sure to call in void Update
    45.     {
    46.         isWallRight = Physics.Raycast(transform.position, orientation.right, 1f, whatIsWall);
    47.         isWallLeft = Physics.Raycast(transform.position, -orientation.right, 1f, whatIsWall);
    48.  
    49.         //leave wall run
    50.         if (!isWallLeft && !isWallRight) StopWallRun();
    51.         //reset double jump (if you have one :D)
    52.         if (isWallLeft || isWallRight) doubleJumpsLeft = startDoubleJumps;
    53.     }
    54.  
    55.  
    56.     /// <summary>
    57.     /// Wall run done, here comes the rest of the movement script
    58.     /// </summary>
    59.  
    60.  
    61.     //Assingables
    62.     public Transform playerCam;
    63.     public Transform orientation;
    64.  
    65.     //Other
    66.     public Rigidbody rb;
    67.  
    68.     //Rotation and look
    69.     public float xRotation;
    70.     public float sensitivity = 50f;
    71.     public float sensMultiplier = 1f;
    72.  
    73.     //Movement
    74.     public float moveSpeed = 4500;
    75.     public float maxSpeed = 20;
    76.     public float startMaxSpeed;
    77.     public bool grounded;
    78.     public LayerMask whatIsGround;
    79.  
    80.     public float counterMovement = 0.175f;
    81.     public float threshold = 0.01f;
    82.     public float maxSlopeAngle = 35f;
    83.  
    84.     //Crouch & Slide
    85.     public Vector3 crouchScale = new Vector3(1, 0.5f, 1);
    86.     public Vector3 playerScale;
    87.     public float slideForce = 400;
    88.     public float slideCounterMovement = 0.2f;
    89.     public float crouchGravityMultiplier;
    90.  
    91.     //Jumping
    92.     public bool readyToJump = true;
    93.     public float jumpCooldown = 0.25f;
    94.     public float jumpForce = 550f;
    95.  
    96.     public int startDoubleJumps = 1;
    97.     int doubleJumpsLeft;
    98.  
    99.     //Input
    100.     public float x, y;
    101.     bool jumping, sprinting, crouching;
    102.  
    103.     //Sliding
    104.     public Vector3 normalVector = Vector3.up;
    105.  
    106.     void Awake()
    107.     {
    108.         rb = GetComponent<Rigidbody>();
    109.         startMaxSpeed = maxSpeed;
    110.     }
    111.  
    112.     void Start()
    113.     {
    114.         playerScale = transform.localScale;
    115.         Cursor.lockState = CursorLockMode.Locked;
    116.         Cursor.visible = false;
    117.     }
    118.  
    119.  
    120.     public void FixedUpdate()
    121.     {
    122.         Movement();
    123.     }
    124.  
    125.     public void Update()
    126.     {
    127.         MyInput();
    128.         Look();
    129.         CheckForWall();
    130.         WallRunInput();
    131.     }
    132.  
    133.     /// <summary>
    134.     /// Find user input. Should put this in its own class but im lazy
    135.     /// </summary>
    136.     public void MyInput()
    137.     {
    138.         x = Input.GetAxisRaw("Horizontal");
    139.         y = Input.GetAxisRaw("Vertical");
    140.         jumping = Input.GetButton("Jump");
    141.         crouching = Input.GetKey(KeyCode.LeftShift);
    142.  
    143.         //Crouching
    144.         if (Input.GetKeyDown(KeyCode.LeftShift))
    145.             StartCrouch();
    146.         if (Input.GetKeyUp(KeyCode.LeftShift))
    147.             StopCrouch();
    148.  
    149.         //Double Jumping
    150.         if (Input.GetButtonDown("Jump") && !grounded && doubleJumpsLeft >= 1)
    151.         {
    152.             Jump();
    153.             doubleJumpsLeft--;
    154.         }
    155.     }
    156.  
    157.     public void StartCrouch()
    158.     {
    159.         transform.localScale = crouchScale;
    160.         transform.position = new Vector3(transform.position.x, transform.position.y - 0.5f, transform.position.z);
    161.         if (rb.velocity.magnitude > 0.5f)
    162.         {
    163.             if (grounded)
    164.             {
    165.                 rb.AddForce(orientation.transform.forward * slideForce);
    166.             }
    167.         }
    168.     }
    169.  
    170.     public void StopCrouch()
    171.     {
    172.         transform.localScale = playerScale;
    173.         transform.position = new Vector3(transform.position.x, transform.position.y + 0.5f, transform.position.z);
    174.     }
    175.  
    176.     public void Movement()
    177.     {
    178.         //Extra gravity
    179.         //Needed that the Ground Check works better!
    180.         float gravityMultiplier = 10f;
    181.  
    182.         if (crouching) gravityMultiplier = crouchGravityMultiplier;
    183.  
    184.         rb.AddForce(Vector3.down * Time.fixedUnscaledDeltaTime * gravityMultiplier);
    185.  
    186.         //Find actual velocity relative to where player is looking
    187.         Vector2 mag = FindVelRelativeToLook();
    188.         float xMag = mag.x, yMag = mag.y;
    189.  
    190.         //Counteract sliding and sloppy movement
    191.         CounterMovement(x, y, mag);
    192.  
    193.         //If holding jump && ready to jump, then jump
    194.         if (readyToJump && jumping && grounded) Jump();
    195.  
    196.         //ResetStuff when touching ground
    197.         if (grounded)
    198.         {
    199.             doubleJumpsLeft = startDoubleJumps;
    200.         }
    201.  
    202.         //Set max speed
    203.         float maxSpeed = this.maxSpeed;
    204.  
    205.         //If sliding down a ramp, add force down so player stays grounded and also builds speed
    206.         if (crouching && grounded && readyToJump)
    207.         {
    208.             rb.AddForce(Vector3.down * Time.fixedUnscaledDeltaTime * 3000);
    209.             return;
    210.         }
    211.  
    212.         //If speed is larger than maxspeed, cancel out the input so you don't go over max speed
    213.         if (x > 0 && xMag > maxSpeed) x = 0;
    214.         if (x < 0 && xMag < -maxSpeed) x = 0;
    215.         if (y > 0 && yMag > maxSpeed) y = 0;
    216.         if (y < 0 && yMag < -maxSpeed) y = 0;
    217.  
    218.         //Some multipliers
    219.         float multiplier = 1f, multiplierV = 1f;
    220.  
    221.         // Movement in air
    222.         if (!grounded)
    223.         {
    224.             multiplier = 0.5f;
    225.             multiplierV = 0.5f;
    226.         }
    227.  
    228.         // Movement while sliding
    229.         if (grounded && crouching) multiplierV = 0f;
    230.  
    231.         //Apply forces to move player
    232.         rb.AddForce(orientation.transform.forward * y * moveSpeed * Time.fixedUnscaledDeltaTime * multiplier * multiplierV);
    233.         rb.AddForce(orientation.transform.right * x * moveSpeed * Time.fixedUnscaledDeltaTime * multiplier);
    234.     }
    235.  
    236.     public void Jump()
    237.     {
    238.         if (grounded)
    239.         {
    240.             readyToJump = false;
    241.  
    242.             //Add jump forces
    243.             rb.AddForce(Vector2.up * jumpForce * 1.5f);
    244.             rb.AddForce(normalVector * jumpForce * 0.5f);
    245.  
    246.             //If jumping while falling, reset y velocity.
    247.             Vector3 vel = rb.velocity;
    248.             if (rb.velocity.y < 0.5f)
    249.                 rb.velocity = new Vector3(vel.x, 0, vel.z);
    250.             else if (rb.velocity.y > 0)
    251.                 rb.velocity = new Vector3(vel.x, vel.y / 2, vel.z);
    252.  
    253.             Invoke(nameof(ResetJump), jumpCooldown);
    254.         }
    255.         if (!grounded)
    256.         {
    257.             readyToJump = false;
    258.  
    259.             //Add jump forces
    260.             rb.AddForce(orientation.forward * jumpForce * 1f);
    261.             rb.AddForce(Vector2.up * jumpForce * 1.5f);
    262.             rb.AddForce(normalVector * jumpForce * 0.5f);
    263.  
    264.             //Reset Velocity
    265.             rb.velocity = Vector3.zero;
    266.  
    267.             Invoke(nameof(ResetJump), jumpCooldown);
    268.         }
    269.  
    270.         //Walljump
    271.         if (isWallRunning)
    272.         {
    273.             readyToJump = false;
    274.  
    275.             //normal jump
    276.             if (isWallLeft && !Input.GetKey(KeyCode.D) || isWallRight && !Input.GetKey(KeyCode.A))
    277.             {
    278.                 rb.AddForce(Vector2.up * jumpForce * 1.5f);
    279.                 rb.AddForce(normalVector * jumpForce * 0.5f);
    280.             }
    281.  
    282.             //sidwards wallhop
    283.             if (isWallRight || isWallLeft && Input.GetKey(KeyCode.A) || Input.GetKey(KeyCode.D)) rb.AddForce(-orientation.up * jumpForce * 1f);
    284.             if (isWallRight && Input.GetKey(KeyCode.A)) rb.AddForce(-orientation.right * jumpForce * 3.2f);
    285.             if (isWallLeft && Input.GetKey(KeyCode.D)) rb.AddForce(orientation.right * jumpForce * 3.2f);
    286.  
    287.             //Always add forward force
    288.             rb.AddForce(orientation.forward * jumpForce * 1f);
    289.  
    290.             Invoke(nameof(ResetJump), jumpCooldown);
    291.         }
    292.     }
    293.  
    294.     public void ResetJump()
    295.     {
    296.         readyToJump = true;
    297.     }
    298.  
    299.     public void ActivateGravity()
    300.     {
    301.         rb.useGravity = true;
    302.     }
    303.  
    304.     public float desiredX;
    305.     public void Look()
    306.     {
    307.         float mouseX = Input.GetAxis("Mouse X") * sensitivity * Time.fixedUnscaledDeltaTime * sensMultiplier;
    308.         float mouseY = Input.GetAxis("Mouse Y") * sensitivity * Time.fixedUnscaledDeltaTime * sensMultiplier;
    309.  
    310.         //Find current look rotation
    311.         Vector3 rot = playerCam.transform.localRotation.eulerAngles;
    312.         desiredX = rot.y + mouseX;
    313.  
    314.         //Rotate, and also make sure we dont over- or under-rotate.
    315.         xRotation -= mouseY;
    316.         xRotation = Mathf.Clamp(xRotation, -90f, 90f);
    317.  
    318.         //Perform the rotations
    319.         playerCam.transform.localRotation = Quaternion.Euler(xRotation, desiredX, wallRunCameraTilt);
    320.         orientation.transform.localRotation = Quaternion.Euler(0, desiredX, 0);
    321.  
    322.         //While Wallrunning
    323.         //Tilts camera in .5 second
    324.         if (Math.Abs(wallRunCameraTilt) < maxWallRunCameraTilt && isWallRunning && isWallRight)
    325.             wallRunCameraTilt += Time.fixedUnscaledDeltaTime * maxWallRunCameraTilt * 2;
    326.         if (Math.Abs(wallRunCameraTilt) < maxWallRunCameraTilt && isWallRunning && isWallLeft)
    327.             wallRunCameraTilt -= Time.fixedUnscaledDeltaTime * maxWallRunCameraTilt * 2;
    328.  
    329.         //Tilts camera back again
    330.         if (wallRunCameraTilt > 0 && !isWallRight && !isWallLeft)
    331.             wallRunCameraTilt -= Time.fixedUnscaledDeltaTime * maxWallRunCameraTilt * 2;
    332.         if (wallRunCameraTilt < 0 && !isWallRight && !isWallLeft)
    333.             wallRunCameraTilt += Time.fixedUnscaledDeltaTime * maxWallRunCameraTilt * 2;
    334.     }
    335.     public void CounterMovement(float x, float y, Vector2 mag)
    336.     {
    337.         if (!grounded || jumping) return;
    338.  
    339.         //Slow down sliding
    340.         if (crouching)
    341.         {
    342.             rb.AddForce(moveSpeed * Time.fixedUnscaledDeltaTime * -rb.velocity.normalized * slideCounterMovement);
    343.             return;
    344.         }
    345.  
    346.         //Counter movement
    347.         if (Math.Abs(mag.x) > threshold && Math.Abs(x) < 0.05f || (mag.x < -threshold && x > 0) || (mag.x > threshold && x < 0))
    348.         {
    349.             rb.AddForce(moveSpeed * orientation.transform.right * Time.fixedUnscaledDeltaTime * -mag.x * counterMovement);
    350.         }
    351.         if (Math.Abs(mag.y) > threshold && Math.Abs(y) < 0.05f || (mag.y < -threshold && y > 0) || (mag.y > threshold && y < 0))
    352.         {
    353.             rb.AddForce(moveSpeed * orientation.transform.forward * Time.fixedUnscaledDeltaTime * -mag.y * counterMovement);
    354.         }
    355.  
    356.         //Limit diagonal running. This will also cause a full stop if sliding fast and un-crouching, so not optimal.
    357.         if (Mathf.Sqrt((Mathf.Pow(rb.velocity.x, 2) + Mathf.Pow(rb.velocity.z, 2))) > maxSpeed)
    358.         {
    359.             float fallspeed = rb.velocity.y;
    360.             Vector3 n = rb.velocity.normalized * maxSpeed;
    361.             rb.velocity = new Vector3(n.x, fallspeed, n.z);
    362.         }
    363.     }
    364.  
    365.     /// <summary>
    366.     /// Find the velocity relative to where the player is looking
    367.     /// Useful for vectors calculations regarding movement and limiting movement
    368.     /// </summary>
    369.     public Vector2 FindVelRelativeToLook()
    370.     {
    371.         float lookAngle = orientation.transform.eulerAngles.y;
    372.         float moveAngle = Mathf.Atan2(rb.velocity.x, rb.velocity.z) * Mathf.Rad2Deg;
    373.  
    374.         float u = Mathf.DeltaAngle(lookAngle, moveAngle);
    375.         float v = 90 - u;
    376.  
    377.         float magnitue = rb.velocity.magnitude;
    378.         float yMag = magnitue * Mathf.Cos(u * Mathf.Deg2Rad);
    379.         float xMag = magnitue * Mathf.Cos(v * Mathf.Deg2Rad);
    380.  
    381.         return new Vector2(xMag, yMag);
    382.     }
    383.  
    384.     public bool IsFloor(Vector3 v)
    385.     {
    386.         float angle = Vector3.Angle(Vector3.up, v);
    387.         return angle < maxSlopeAngle;
    388.     }
    389.  
    390.     public bool cancellingGrounded;
    391.  
    392.     /// <summary>
    393.     /// Handle ground detection
    394.     /// </summary>
    395.     public void OnCollisionStay(Collision other)
    396.     {
    397.         //Make sure we are only checking for walkable layers
    398.         int layer = other.gameObject.layer;
    399.         if (whatIsGround != (whatIsGround | (1 << layer))) return;
    400.  
    401.         //Iterate through every collision in a physics update
    402.         for (int i = 0; i < other.contactCount; i++)
    403.         {
    404.             Vector3 normal = other.contacts[i].normal;
    405.             //FLOOR
    406.             if (IsFloor(normal))
    407.             {
    408.                 grounded = true;
    409.                 cancellingGrounded = false;
    410.                 normalVector = normal;
    411.                 CancelInvoke(nameof(StopGrounded));
    412.             }
    413.         }
    414.  
    415.         //Invoke ground/wall cancel, since we can't check normals with CollisionExit
    416.         float delay = 3f;
    417.         if (!cancellingGrounded)
    418.         {
    419.             cancellingGrounded = true;
    420.             Invoke(nameof(StopGrounded), Time.fixedUnscaledDeltaTime * delay);
    421.         }
    422.     }
    423.  
    424.     public void StopGrounded()
    425.     {
    426.         grounded = false;
    427.     }
    428. }
    429.  

    I have already gone into the wall run script and tried to change all the deltaTime to fixedUnscaledDeltaTime as that is all i could think the problem might be.
     
  2. Edy

    Edy

    Joined:
    Jun 3, 2010
    Posts:
    1,852
    I can see quite a few things wrong in these scripts.
    • Time.timeScale being assigned some value related with Time.unscaledDeltaTime. Time.timeScale is a scale: 1 for normal time (no changes), 0.5 to 50% slow, 2 to 200% fast, etc.
    • Calling Rigidbody.AddForce with parameters multiplied by time. Force is a time-independent magnitude. Use ForceMode.Impulse to apply impulses.
    • Mixing stuff in Update and FixedUpdate, yet using Time.fixedUnscaledDeltaTime.
    • Time.fixedUnscaledDeltaTime is, by definition, unscaled. Time.timeScale don't affect it.
    Time.deltaTime should be used when a delta time is required, in both Update and FixedUpdate, unless there's some specific reason to use other delta time value (definitely Rigidbody.AddForce is not a place to use any delta time). When used within FixedUpdate Time.deltaTime returns the fixed delta time.

    If delta times are used properly (not in AddForce, use Time.deltaTime elsewhere) then it would be enough to use Time.deltaTime as described above to slow down or speed up everything.
     
unityunity