Skip to content

Instantly share code, notes, and snippets.

@noidexe
Created February 14, 2024 21:42
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save noidexe/6fe6786d7d946d3cbdf335bcc64a8c62 to your computer and use it in GitHub Desktop.
Save noidexe/6fe6786d7d946d3cbdf335bcc64a8c62 to your computer and use it in GitHub Desktop.
Godot 4 await parallel calls
extends RefCounted
class_name MultiAwaiter
## Can await till multiple method calls are done
##
## You use it like:
## [codeblock]
## var awaiter = MultipleAwait.new()
## awaiter.push_method( my_func.bind(arg_a, arg_b, ...) )
## await awaiter.run() # You can also connect stuff to it's completed signal
## [/codeblock]
##
## It's probably not a good idea to reuse it, so no method to clear the method_list is provided
signal completed
var _remaining : int = 0
var _method_list : Array[Callable] = []
## Used to build your list of methos to call. Use method_name.bind() to call with arguments
func push_method(method: Callable):
_method_list.append(method)
## Corroutine that calls all the methods in parallel and waits till they are done
func run():
assert( _remaining == 0, "Either you tried to call run() while it was already running or it's a bug")
_remaining = _method_list.size()
for m in _method_list:
(func(): await m.call(); _on_method_done() ).call()
# If _remaining is 0 either we had an empty _method_list or all the methods completed immediately
if _remaining == 0:
completed.emit() # not needed internally but there might be external connections
return
# otherwise await the completed signal
await completed
## Internal. Updates remaining count and emits the completed signal when it reaches 0
func _on_method_done():
_remaining -= 1
assert(_remaining >= 0)
if _remaining == 0:
completed.emit()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment