Check if character is grounded?

Hey Community
I use this script to make a jump n run… but the problem is : when i press jump and he is in mid air i can press again and he jumps from mid air. So he gets higher and higher… He should only can jump after he hits the ground…
This is my script:

using UnityEngine;
using System.Collections;

public class PlayerMovement : MonoBehaviour {

private bool grounded;

private float speed;

private Vector2 startPos;

//
void Start () {

speed = 7;

grounded = true;

}

//
void FixedUpdate ()
{

transform.Translate(-Vector3.forward * -speed * Time.deltaTime);//

#if UNITY_EDITOR

transform.Translate (Vector2.right * Input.GetAxis (“Horizontal”) * 5 * Time.deltaTime);
if (Input.GetKey (KeyCode.Space) grounded == true)
{
rigidbody.AddForce (0,50,0,ForceMode.Force);
grounded = true;

}
#endif
#if UNITY_ANDROID
transform.Translate (Vector3.right * Input.acceleration.x * 7.5f * Time.deltaTime);
if (Input.touchCount > 0)
{

Touch touch = Input.touches [0];

switch (touch.phase)

{

case TouchPhase.Began:
startPos = touch.position;
break;

case TouchPhase.Moved:
if (Mathf.Abs (touch.position.y - startPos.y) > 100) //

{

float swipeValue = Mathf.Sign (touch.position.y - startPos.y);

if (swipeValue > 0 grounded == true) //
{
rigidbody.AddForce (0,50,0,ForceMode.Force);
grounded = true;
break;
}
else if (swipeValue < 0) //
{ //
break;
}
}
break;
}
}
#endif
}
}

It’s happening because when u jump you set grounded to true, so you can jump again. Change those line to grounded = false when jumping and add a if statement in your update function checking height of your player to set back grounded to true. Or add a OnCollisionEnter function checking collision with ground to set back grounded to true.

i changed it, and now i cant jump even once…
could u may copy my scrip, and put in what i need to change?
Im really bad at scripting…

Hey there,

You most likely want to do a Raycast downwards to see if you are grounded. Add something like this in your FixedUpdate:

grounded = Physics.Raycast(transform.position, Vector3.down, .5f);

This draws a line from where the player is to .5 down. If it hits, thus we are not far from the ground, it returns true. You might have to tweak the .5f to be smaller/bigger, depending on the scale of your scene.

1 Like

Like this?

using UnityEngine;
using System.Collections;

public class PlayerMovement : MonoBehaviour {

private bool grounded;

private float speed;

private Vector2 startPos;

//
void Start () {

speed = 7;

grounded = true;

}

//
void FixedUpdate ()
{

transform.Translate(-Vector3.forward * -speed * Time.deltaTime);//

#if UNITY_EDITOR

transform.Translate (Vector2.right * Input.GetAxis (“Horizontal”) * 5 * Time.deltaTime);
if (Input.GetKey (KeyCode.Space) grounded == true)
{
rigidbody.AddForce (0,50,0,ForceMode.Force);
grounded = true;
grounded = Physics.Raycast(transform.position, Vector3.down, .5f);
}
#endif
#if UNITY_ANDROID
transform.Translate (Vector3.right * Input.acceleration.x * 7.5f * Time.deltaTime);
if (Input.touchCount > 0)
{

Touch touch = Input.touches [0];

switch (touch.phase)

{

case TouchPhase.Began:
startPos = touch.position;
break;

case TouchPhase.Moved:
if (Mathf.Abs (touch.position.y - startPos.y) > 100) //

{

float swipeValue = Mathf.Sign (touch.position.y - startPos.y);

if (swipeValue > 0 grounded == true) //
{
rigidbody.AddForce (0,50,0,ForceMode.Force);
grounded = true;
break;
}
else if (swipeValue < 0) //
{ //
break;
}
}
break;
}
}
#endif
}
}
This dont even let me jump?
Im sorry im really bad at scripting… could u copy my script and put it in where u think it should work?
Thank u

using UnityEngine;
using System.Collections;

public class PlayerMovement : MonoBehaviour {

private bool grounded;

private float speed;

private Vector2 startPos;

//
void Start () {

speed = 7;

grounded = true;

}


//
void FixedUpdate ()
{

transform.Translate(-Vector3.forward * -speed * Time.deltaTime);//

if(transform.position.y < 1){
grounded = true;
}

#if UNITY_EDITOR

transform.Translate (Vector2.right * Input.GetAxis ("Horizontal") * 5 * Time.deltaTime);
if (Input.GetKey (KeyCode.Space)  grounded == true)
{
rigidbody.AddForce (0,50,0,ForceMode.Force);
grounded = false;

}
#endif
#if UNITY_ANDROID
transform.Translate (Vector3.right * Input.acceleration.x * 7.5f * Time.deltaTime);
if (Input.touchCount > 0)
{

Touch touch = Input.touches [0];


switch (touch.phase)

{

case TouchPhase.Began:
startPos = touch.position;
break;


case TouchPhase.Moved:
if (Mathf.Abs (touch.position.y - startPos.y) > 100) //

{

float swipeValue = Mathf.Sign (touch.position.y - startPos.y);

if (swipeValue > 0  grounded == true) //
{
rigidbody.AddForce (0,50,0,ForceMode.Force);
grounded = false;
break;
}
else if (swipeValue < 0) //
{ //
break;
}
}
break;
}
}
#endif
}
}

you may need to change the value in the if statement i added. I have put 1 but i don’t know how your level is set, so i don’t know the height of your player and terrain.

if(transform.position.y < 1){
grounded = true;
}

If you have different height in terrain, this won’t work and you’ll need to replace that if statement by a OnCollisionEnter function (dont put it in the update function). I’m more used to Unity script so here it goes in Javascript, u’ll have to translate it to C# . By the way, if u’re bad at scripting, u should really script in JS instead of C#, it’s a bit easier and more clear to read:

function OnCollisionEnter ( hit : Collision ){
    if(hit.gameObject.tag == "Ground"){
      grounded = true;
             
       }
           
     }    
}

for that function to work, you need to add the tag Ground to your ground, and make sure that your ground and your player have a collider and at least one have a rigidbody.

Hmm it just let me jump once maybe a mm high :frowning:
This is not my script i took it from a tutorial…
I want to make a game with controls like temple run but without the script for the controls i cant iven start…
Its a school project…

If you put the raycast check inside the IF we’d only check if we where grounded when the button is down. This is incorrect, we want to always check. When we know if we are grounded or not, we check if we are and if the space key is down, then jump.

void FixedUpdate ()
{
   transform.Translate(-Vector3.forward * -speed * Time.deltaTime);
   grounded = Physics.Raycast(transform.position, Vector3.down, .5f);

   if (grounded  Input.GetKeyDown (KeyCode.Space))
   {
       rigidbody.AddForce (0,50,0,ForceMode.Force);
   }
}

How long do you have to make your game ? Making a game is really time consumming, AAA games are made in 2 or 3 years with 30 or more people working on it full time. Don’t expect to make a great game if you have like one month to make it and do others stuffs at the same time. And you really need to learn scripting to make a game, because each game is different so you will have, at least, to tweak the code you find.

U mean like this:?
using UnityEngine;
using System.Collections;

public class PlayerMovement : MonoBehaviour {

private bool grounded;

private float speed;

private Vector2 startPos;

//
void Start () {

speed = 7;

grounded = true;

}

//
void FixedUpdate ()

{
#if UNITY_EDITOR
transform.Translate (-Vector3.forward * -speed * Time.deltaTime);

grounded = Physics.Raycast (transform.position, Vector3.down, .5f);

if (grounded Input.GetKeyDown (KeyCode.Space)) {

rigidbody.AddForce (0, 50, 0, ForceMode.Force);

}
}
#endif
#if UNITY_ANDROID
transform.Translate (Vector3.right * Input.acceleration.x * 7.5f * Time.deltaTime);
if (Input.touchCount > 0)
{

Touch touch = Input.touches [0];

switch (touch.phase)

{

case TouchPhase.Began:
startPos = touch.position;
break;

case TouchPhase.Moved:
if (Mathf.Abs (touch.position.y - startPos.y) > 100) //

{

float swipeValue = Mathf.Sign (touch.position.y - startPos.y);

if (swipeValue > 0 grounded == true) //
{
rigidbody.AddForce (0,50,0,ForceMode.Force);
grounded = true;
break;
}
else if (swipeValue < 0) //
{ //
break;
}
}
break;
}
}
#endif
}
}

this gives me an error…

I have maybe 2 months for it… It shouldnt be a perfect game… the character should just run automaticly and jump when u want but only when he is on the ground… and if he touches a wrong object the game should restart(this i want to make after i fixed this jump error…)

Can you please post code in

 [ /code] tags? 

Errors are very, very valuable. What is the error you are seeing, what does it tell you?
using UnityEngine;
using System.Collections;

public class PlayerMovement : MonoBehaviour {
	
	private bool grounded;
	
	private float speed;
	
	private Vector2 startPos;
	
	//
	void Start () {
		
		speed = 7;
		
		grounded = true;
		
	}
	
	
	//
		void FixedUpdate ()

		{
		#if UNITY_EDITOR	
				transform.Translate (-Vector3.forward * -speed * Time.deltaTime);
	
				grounded = Physics.Raycast (transform.position, Vector3.down, .5f);
			
			
			
				if (grounded  Input.GetKeyDown (KeyCode.Space)) {
				
						rigidbody.AddForce (0, 50, 0, ForceMode.Force);
				
				}
		}
		#endif
		#if UNITY_ANDROID
		transform.Translate (Vector3.right * Input.acceleration.x * 7.5f * Time.deltaTime);
		if (Input.touchCount > 0)
		{
			
			Touch touch = Input.touches [0];
			
			
			switch (touch.phase) 
				
			{	
				
			case TouchPhase.Began:
				startPos = touch.position;
				break;
				
				
			case TouchPhase.Moved:
				if (Mathf.Abs (touch.position.y - startPos.y) > 100) //
					
				{
					
					float swipeValue = Mathf.Sign (touch.position.y - startPos.y);
					
					if (swipeValue > 0  grounded == true) //
					{
						rigidbody.AddForce (0,50,0,ForceMode.Force);
						grounded = true;
						break;
					} 
					else if (swipeValue < 0) //
					{	 //
						break;
					}
				}
				break;
			}
		}
		#endif
	}
}

Im sorry i didnt knew that…
the error is: error cs1519 unexpected symbol `(’ in class, struct or interface member declaration