- Home /
Update () cant be a coroutine
I´m making a script that loads a level after collecting certain amount of pages like slender.... here is the FULL script;
#pragma strict
@script RequireComponent ( AudioSource )
var papers : int = 0;
var papersToWin = 8;
var distanceToPaper : float = 2.5;
public var paperPickup : AudioClip;
function Start ()
{
Screen.lockCursor = true;
}
function Update ()
{
if(Input.GetMouseButtonDown (0) || Input.GetKeyDown (KeyCode.E))
{
var ray = Camera.main.ScreenPointToRay(Vector3(Screen.width * 0.5, Screen.height * 0.5, 0.0));
var hit : RaycastHit;
if(Physics.Raycast(ray, hit, distanceToPaper))
{
if(hit.collider.gameObject.name == "Paper")
{
papers += 1;
audio.PlayClipAtPoint(paperPickup, transform.position);
Destroy(hit.collider.gameObject);
if( papers < papersToWin)
yield WaitForSeconds(3);
Application.LoadLevel("next");
}
}
}
}
function OnGUI ()
{
if(papers < papersToWin)
{
GUI.Box(Rect((Screen.width * 0.5) -60, 10, 120, 25), papers.ToString() + " of " + papersToWin.ToString() + " Pages");
}
else
GUI.Box(Rect((Screen.width/2) - 100, 10, 200, 35), "You Won!");
}
I get this error BCE0089: Type 'Collect' already has a definition for 'Start()'
As said below, you can't use yield inside Update - move the code to another function. About the error: the script Collect.js has two functions Start declared - apparently that's not the case of the script above, but it may have changed since the question was posted.
Answer by aldonaletto · Aug 04, 2013 at 04:00 PM
Unity is right: Update can't be a coroutine. You can call a coroutine from Update, or use a "CoUpdate" coroutine instead:
function Start(): IEnumerator { // turn Start into a coroutine
while (true){// create an eternal loop
yield CoUpdate(); // call CoUpdate each frame
}
}
function CoUpdate(): IEnumerator { // CoUpdate is called every frame
if (papers < papersToWin){
yield WaitForSeconds(3); // CoUpdate can WaitForSeconds!
Application.LoadLevel("next");
}
}
If you want to use Update, write a separate coroutine and make sure it's not called again while executing! : each time you call a coroutine, a new instance of it is created and starts running, thus in a few seconds you may have lots of coroutines executing in parallel:
var running = false; // tells whether LoadNext is running
function LoadNext(): IEnumerator {
running = true; // LoadNext started
WaitForSeconds(3);
Application.LoadLevel("next");
running = false; // LoadNext ended (unnecessary, since this level has finished)
}
function Update(){
if (!running && papers < papersToWin){
LoadNext(); // only call LoadNext if it's not already running
}
}
@aldonaletto thnx, i was looking for something like this. you just saved my time.
Answer by Lovrenc · Aug 04, 2013 at 03:50 PM
Update is reserved name for function in unity. Update gets called in a loop by game engine. Therefore you cannot use
yield WaitForSeconds(3);
in Update function. Write separate function for that.
Your answer
Follow this Question
Related Questions
Using Coroutine rather than Update to Check Whether Time Passed 1 Answer
[ANSWERED]Move object without Update or coroutine 2 Answers
Confused about using Update vs. Coroutines 2 Answers
What is the best approach? Coroutine or calculate the "Elapsed Time" in the Update? 3 Answers
How can I get my camera to momentarily pause between different positions when using lerp? 0 Answers