Skip to content

Instantly share code, notes, and snippets.

@apples
Created December 11, 2024 09:07
Show Gist options
  • Save apples/5f23ac5e84b2e3a7872de85cd556b5a5 to your computer and use it in GitHub Desktop.
Save apples/5f23ac5e84b2e3a7872de85cd556b5a5 to your computer and use it in GitHub Desktop.
A simple and memory-efficient implementation of futures/promises in GDScript.
class_name Future
extends RefCounted
static var _UNFULFILLED = RefCounted.new()
static var _initial_state = [_UNFULFILLED]
static var _fulfilled_signal = _FulfilledSignal.new()
func _init() -> void:
push_error("Static class. Do not instantiate.")
static func is_future(v: Variant) -> bool:
return v is Array and v.size() == 1
static func create() -> Variant:
return _initial_state.duplicate()
static func create_fulfilled(v: Variant) -> Variant:
return [v]
static func is_fulfilled(future: Variant) -> bool:
assert(is_future(future))
return future[0] != _UNFULFILLED
static func set_value(future: Variant, value: Variant) -> void:
assert(is_future(future))
if future[0] != _UNFULFILLED:
push_warning("Future was already fulfilled (previous value: %s)" % [future[0]])
future[0] = value
_fulfilled_signal.something_fulfilled.emit()
static func get_value(future: Variant) -> Variant:
assert(is_future(future))
var v = future[0]
return v if v != _UNFULFILLED else null
static func get_value_async(future: Variant) -> Variant:
assert(is_future(future))
while future[0] == _UNFULFILLED:
await _fulfilled_signal.something_fulfilled
return future[0]
class _FulfilledSignal:
signal something_fulfilled()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment