- Home /
Problem with yield
Hello everybody,
I want to enable the rigidbody's gravity of an object by collision after waiting for 2 seconds. Here is my script so far (I am new to scripting):
using UnityEngine;
using System.Collections;
public class Collision_Bridge : MonoBehaviour {
void Start () {
}
void Update () {
}
void OnCollisionEnter(Collision other) {
if (other.gameObject.tag == "Player") {
StartCoroutine(waiting ());
}
}
IEnumerator waiting() {
Debug.Log ("Before Waiting");
yield return new WaitForSeconds(2);
Debug.Log ("After Waiting");
GetComponent<Rigidbody>().useGravity = true;
}
}
My problem is that the rigidbody's gravity is enabled by the collision straight away and not after 2 seconds. Even if I put GetComponent().useGravity = true; in the Update funtion it does not work. "Before Waiting" and "After Waiting" is printed with an intervall of 2 seconds as I want it to be.
Does anybody know what is wrong? Thanks a lot!
So you are saying that the useGravity line is executing immediately, but the After Waiting line above it is not executing for 2 seconds?
Yes, that's right and I don't know why the useGravity line is executing immediately but the After Waiting line not.
Just to be sure, is the "Use Gravity" checkbox in the inspector unchecked by default?
Something to try, comment out that useGravity line and see if the gravity still kicks in.
The "Use Gravity" checkbox was unchecked but when I comment out that useGravity line the bridge keeps falling although there is no gravity. Could it depend on the rigidbody and the collision?
Answer by wibble82 · May 01, 2014 at 10:04 PM
(EDIT: a new answer)
It strikes me that the useGravity line must not be the cause of this. I suspect gravity is being applied anyway for some reason, so the useGravity line is simply not having any effect at all.
I would try explicitly setting useGravity to false, and set the rigid body's velocity to 0 right at the start of that coroutine. We just need identify where the problem is occuring, so eliminating gravity and velocity at the start of your coroutine puts the rigid body in a known state.
It'll either be that the bridge already had gravity enabled, or the collision is causing it to fall - either by enabling gravity incorrectly or perhaps just knocking it downwards (giving the perception of gravity).
Once you've made those tweaks:
check useGravity is false
remove the useGravity=true line
set the wait to be 10s (just to give yourself some time)
add a Debug.Log to print useGravity at the start of your coroutine
add a Debug.Log to print useGravity inside your collision enter function
run the game
check useGravity is false
check the object isn't falling under gravity
hit pause immediately after collision
check useGravity is false
If that works, the bridge should just stay where it is. Adding back your useGravity=true line should bring it back. I suspect it'll then give you the desired effect, then we could try working out exactly what's causing the problem.
I assume there's nothing that fulls under gravity sitting on the bridge?
-Chris
(This next bit was wrong, and is what the comments below referred to!)
Subtle one. Your code should read startcoroutine("waiting") What you are doing is calling waiting just like a normal function. Then you are passing the return value of waiting into StartCoroutine!
Are you sure about that? I always call coroutines using the syntax StartCoroutine(myCoroutine()); and it definitely does not ignore the yield.
He already said above that even when commenting out the useGravity line the object still has gravity, so clearly the issue is elsewhere.
Yeah, I mean the Debug.Log lines work perfectly. I think it has something to do with the colliders. I keep thinking
(by the way I'm a girl ;) )
So many thanks for all your help!
It had something to do with the rigidbody because the object as well as the player had one. As soon as I removed the rigidbody from the object it did not fall anymore. So I just attached the rigidbody after 2 seconds after collision. It works fine now :)