Closed ghost closed 3 years ago
yield()
is a GDScript concept. It can't be used as-is in Godot's C++ code nor in GDNative C/C++.
(Also, yield()
will be removed in favor of the await
keyword in Godot 4.0.)
So, what can we do to tell godot to ignore us for one frame and then comeback to finish the function?
Timers can be used for that but the time might not exactly be the next frame. There's also call deferred.
not as efficient as yield
or await
.
and call deferred
can't be done in a function.
C does not have the concept of "coroutine" necessary to implement await or yield. The closest thing you can do is subscribe a method to a signal manually.
Example GDScript code (as I haven't used GDNative enough to suggest proper GDNative code):
## Original code:
func test():
var a = 4
print(a)
yield(get_tree().create_timer(50), "timeout") # This example is with create_timer, but it can be trivially modified to use yield(get_tree(), "idle_frame") instead.
print(a + 1)
## Becomes:
func test():
var a = 4
print(a)
var timer = get_tree().create_timer(50)
timer.connect("timeout", self, "_test_cont", [a, timer]) # It is important to pass the timer as a parameter to the other method, as otherwise exiting the test() function will get its reference count down to 0
func _test_cont(a, _timer):
print(a + 1)
(Note that Godot 4.0 mightly allow for connecting to a function pointer directly instead of having to bind an extra function for each resumption point)
C++20 does have coroutines, as do D and Rust. Requests for supporting yielding/awaiting to a signal in those languages should be opened on the respective bindings repository.
yield
is a language-specific concept and this repository is language-agnostic (it's only a partial copy of Godot source to be easily used as a submodule).
yield is Missing.