Search Unity

  1. Welcome to the Unity Forums! Please take the time to read our Code of Conduct to familiarize yourself with the forum rules and how to post constructively.
  2. Dismiss Notice

Stop adding force based on height [Solved]

Discussion in 'Scripting' started by Troas, Jul 9, 2014.

  1. Troas

    Troas

    Joined:
    Jan 26, 2013
    Posts:
    157
    So I've made a script that allows my character to jump (by adding force to a rigid body):

    Code (CSharp):
    1. using UnityEngine;
    2. using System.Collections;
    3.  
    4. public class JumpTest : MonoBehaviour {
    5.  
    6.  
    7.     private Vector3 input;
    8.     public float jumpSpeed = 8f;
    9.     private float maxJumpSpeed = 10f;
    10.     public float gravity = 3f;
    11.  
    12.     private float playerHeight;
    13.  
    14.     private Vector3 moveDirection = Vector3.zero;
    15.  
    16.  
    17.     void FixedUpdate () {
    18.  
    19.  
    20.         moveDirection = new Vector3(Input.GetAxis("Horizontal"), 0, Input.GetAxis("Vertical"));
    21.         moveDirection = transform.TransformDirection(moveDirection);
    22.  
    23.  
    24.         // Needs Work
    25.         if (Input.GetButton ("space")) {
    26.             Debug.Log ("I jumped!");
    27.             moveDirection.y = jumpSpeed;
    28.             if (rigidbody.velocity.magnitude < maxJumpSpeed){
    29.                 rigidbody.AddRelativeForce (moveDirection * jumpSpeed);
    30.             }
    31.         }
    32.     }
    33. }

    The problem is it continously adds force so long as the space bar is pressed.

    My idea is to set a maxHeight variable and if the object reaches that height to no longer add force. However, I do not know how to put that in the code. I was thinking something along the lines of this but a friend told me that it wouldn't work since there is an if statement before it.


    Code (CSharp):
    1. if (Input.GetButton ("space")) {
    2.             Debug.Log ("I jumped!");
    3.             moveDirection.y = jumpSpeed;
    4.             if (rigidbody.velocity.magnitude < maxJumpSpeed){
    5.                 rigidbody.AddRelativeForce (moveDirection * jumpSpeed);
    6.             }
    7.             if (transform.position.y > maxHeight) {
    8.                  rigidbody.AddRelativeForce (moveDirction * 0);
    9.             }
    10. }
    Now the second problem I'd run into is once it does hit this height as soon as it falls below the player could press space bar again and essentially keep floating at that height.

    Any ideas on how to solve this? (I don't need code just the logic behind it, I'll figure out the code for myself).
     
  2. Patico

    Patico

    Joined:
    May 21, 2013
    Posts:
    886
    Usually same systems use isGrounded variable to define if player can jump or not. You can also add the same check but with maxHeight and isGrounded variables. I recomend you to put it in separate method for clarify.
    Code (csharp):
    1. if (IsPlayerCanJump()) {
    2.     rigidbody.AddRelativeForce (moveDirction * 0);
    3. }
    4. ...
    5.  
    6. bool IsPlayerCanJump()
    7. {
    8.     return transform.position.y > maxHeight & isGrounded;
    9. }
     
  3. IsGreen

    IsGreen

    Joined:
    Jan 17, 2014
    Posts:
    206
    What falls to the ground first, a ball of 1 kg or 100 kg ball?

    Gravity also affects Ball 1 kg to 100 kg.

    Neither makes sense to set a speed jump, because the speed is not constant.

    What you can set in the jump, is their height.

    Knowing the height, you can calculate the initial velocity of the jump: Motion under constant acceleration of gravity.

    float initialVelocity = Mathf.Sqrt(jumpHeight*2f*-Physics.gravity.y);

    This initial velocity is applied to the rigidbody from ForceMode.VelocityChange way to the object's mass (1 kg or 100 kg) does not affect the jump height to be achieved.

    Code (CSharp):
    1. using UnityEngine;
    2. using System.Collections;
    3.  
    4. public class JumpTest : MonoBehaviour {
    5.  
    6.     public float jumpHeight = 2f;
    7.     public Vector3 direction = Vector3.forward;
    8.  
    9.     Vector3 position,jumpPosition;
    10.     float time;
    11.     bool jump = false;
    12.     bool up = false;
    13.  
    14.     void Update(){
    15.  
    16.         if(up) if(jumpPosition.y<=transform.position.y) jumpPosition = transform.position;
    17.                  else {
    18.                             up = false;
    19.                             Debug.Log("Jump Time: "+(Time.time-time));
    20.                             Debug.Log("Jump Height: "+(jumpPosition.y - position.y));
    21.        
    22.                       }
    23.  
    24.     }
    25.  
    26.    
    27.     void FixedUpdate () {      
    28.        
    29.         if (Input.GetKeyDown(KeyCode.Space)) if(!jump){
    30.  
    31.             float initialVelocity = Mathf.Sqrt(jumpHeight*2f*-Physics.gravity.y);
    32.             Debug.Log("initialVelocity: "+initialVelocity);
    33.             Vector3 jumpDirection = Vector3.up*initialVelocity+direction;
    34.             rigidbody.AddRelativeForce(jumpDirection,ForceMode.VelocityChange);
    35.             position = jumpPosition = transform.position;
    36.             jump = up = true;
    37.             time = Time.time;
    38.  
    39.         }
    40.  
    41.     }
    42.  
    43.  
    44.     void OnCollisionEnter(){
    45.  
    46.         jump = false;
    47.    
    48.     }
    49.  
    50. }
    51.  
     
    Ereous likes this.
  4. Troas

    Troas

    Joined:
    Jan 26, 2013
    Posts:
    157
    Thanks for the replies first of all, now to address this part.

    The only thing about this is that I wanted a jump that increased in height as the spacebar is held but I guess there is a better way to do that. Thanks!