Godot: Use coroutines in Godot as in UNITY3D Example CODE GITHUB

Created on 18 Jul 2019  路  8Comments  路  Source: godotengine/godot

Godot c # is perfect, however you need functions like unity to handle corutinas ... Here is an example of code, hopefully you can implement it, I could not make it work.

https://github.com/paulohyy/Godot-Coroutine

In my case I want to make a series of tutorials, but the way to handle the corrutinas do not know if they are so good in GODOT C # and that's why I'm waiting for you. I understand that you have to use an awake in the function, however they told me that do that is not well optimized or something like that. That's why I would like to implement this in the next version of godot c #. Corutinas are something fundamental in a Game Engine and implement a model similar to unity would be very practical.

Spanish

archived

Most helpful comment

If I understand correctly, you want to pause the _Process method. That's not how coroutines work (not sure if Unity does it differently). _Process is called each frame and when you use a coroutine, you halt only this single call, thus creating a coroutine each frame. One way to solve this could be calling SetProcess to stop processing during the coroutine, something like

public override void _Process(float delta)
{
//GetNode("Cubo").SetRotation(new Vector3(0,1 * delta,0));//gira el cubo
GetNode("Cubo").RotateY(5 *delta);
Hola();
}

private async void Hola()
{
SetProcess(false); //don't call _Process anymore

for (int i = 0; i < 5; i++)
{
GD.Print("hola mundo");
}
GD.Print("empieza conteo");
await ToSignal(GetTree().CreateTimer(5.0f), "timeout");
GD.Print("termino conteo");

SetProcess(true); //call it again
}

Not sure if this would work though. The "correct" way is to create a Timer node and connect its timeout signal to your Hola method to call it periodically.

All 8 comments

Godot supports co-routines using async/await. They can be used to wait for any signal (including the next idle or physics frame).

This is covered briefly in the C sharp section of the docs, but is also used for the ShowGameOver() method in the Your First Game tutorial.

Yeah, Godot already has coroutines, both in C# and GDScript, so closing this (unless you think the functionality is somehow lacking, but I suggest to read the docs first and test it out).

Yeah, Godot already has coroutines, both in C# and GDScript, so closing this (unless you think the functionality is somehow lacking, but I suggest to read the docs first and test it out).

If you create a function with a corroutine and call it the update does not work. I mean in this test script I want to make 5 hello worlds and then 5 seconds, repeat the 5 hello world ... However it doesn't work
Screenshot_4

`
public override void _Process(float delta)
{
//GetNode("Cubo").SetRotation(new Vector3(0,1 * delta,0));//gira el cubo
GetNode("Cubo").RotateY(5 *delta);
Hola();
}

private async void Hola()
{
for (int i = 0; i < 5; i++)
{
GD.Print("hola mundo");
}
GD.Print("empieza conteo");
await ToSignal(GetTree().CreateTimer(5.0f), "timeout");
GD.Print("termino conteo");
}`

If I understand correctly, you want to pause the _Process method. That's not how coroutines work (not sure if Unity does it differently). _Process is called each frame and when you use a coroutine, you halt only this single call, thus creating a coroutine each frame. One way to solve this could be calling SetProcess to stop processing during the coroutine, something like

public override void _Process(float delta)
{
//GetNode("Cubo").SetRotation(new Vector3(0,1 * delta,0));//gira el cubo
GetNode("Cubo").RotateY(5 *delta);
Hola();
}

private async void Hola()
{
SetProcess(false); //don't call _Process anymore

for (int i = 0; i < 5; i++)
{
GD.Print("hola mundo");
}
GD.Print("empieza conteo");
await ToSignal(GetTree().CreateTimer(5.0f), "timeout");
GD.Print("termino conteo");

SetProcess(true); //call it again
}

Not sure if this would work though. The "correct" way is to create a Timer node and connect its timeout signal to your Hola method to call it periodically.

If I understand correctly, you want to pause the _Process method. That's not how coroutines work (not sure if Unity does it differently). _Process is called each frame and when you use a coroutine, you halt only this single call, thus creating a coroutine each frame. One way to solve this could be calling SetProcess to stop processing during the coroutine, something like

public override void _Process(float delta)
{
//GetNode("Cubo").SetRotation(new Vector3(0,1 * delta,0));//gira el cubo
GetNode("Cubo").RotateY(5 *delta);
Hola();
}

private async void Hola()
{
SetProcess(false); //don't call _Process anymore

for (int i = 0; i < 5; i++)
{
GD.Print("hola mundo");
}
GD.Print("empieza conteo");
await ToSignal(GetTree().CreateTimer(5.0f), "timeout");
GD.Print("termino conteo");

SetProcess(true); //call it again
}

Not sure if this would work though. The "correct" way is to create a Timer node and connect its timeout signal to your Hola method to call it periodically.

Ok .. stopping the process works perfectly well, however the meo I see weird .. in unity there is a function of type IENUMERATOR that can be called in any other function without having to stop stopping anything.
I understand that the corrutina serves to continue executing the flow of code while another executes ... I do not remember 100% but with GDscript if you can call a function stop the time without using setprocess (false) ... I mean the idea is to stop the flow of the code to execute a function and separate the project in parts ... That's why I said if you could implement that form of coroutine, but good if stopping the process is fine and the performance is optimal then there are no problems and I'll have to get used to this ... Thank you very much ...
https://docs.unity3d.com/Manual/Coroutines.html

Yeah, if you look at the doc you just linked

void Update()
{
    if (Input.GetKeyDown("f")) 
    {
        StartCoroutine("Fade");
    }
}

StartCoroutine is called inside a condition block that checks if a button was just pressed. If you remove the condition, you will run into the same problem as you had in Godot.

StartCoroutine is called inside a condition block that checks if a button was just pressed. If you remove the condition, you will run into the same problem as you had in Godot.

It's true what you decide, I just tried it in unity ..
I'm going to have to do several tests to see how it works ... thank you very much.

Was this page helpful?
0 / 5 - 0 ratings