A closure is a lambda function or a bounded function that can remember its surrounding scope and use it even when called from another scope.Here is a slightly convoluted example: a function that creates functions that multiply by a given amount:
funccreate_multiplier(amount:int)->Callable:var closure :=func(num:int)->int:return num * amount
return closure
func_ready()->void:var multiply_by_two :=create_multiplier(2)print(multiply_by_two.call(5))# will print `10`print(multiply_by_two.call(7))# will print `14`
The important part I want you to notice is that the amount I provided the function, 2, is retained in the function's scope. It is said that the function "closes over" its scope; this is where the name comes from.amount is not accessible anymore to anything other than the function itself; it can't be changed. If we wanted to multiply by another amount, we would have to create a new lambda.Here's a more realistic example, where we have a number of characters, and we want to dynamically create a button per character, that when pressed, will change the currently selected hero.
@onreadyvar hbox_container :=%HBoxContainer # to store the buttonsvar characters_list :=["Wizard","Knight","Archer"]var current_character :="Wizard"func_ready()->void:for character in characters_list:var button := Button.new() button.text = character
button.pressed.connect(func()->void:print("Selected ", character) current_character = character
) hbox_container.add_child(button)
In this example, character is, in turn, equal to "Wizard", "Knight", and "Archer". We create 3 buttons, one for each character, and 3 functions that will be called when the button is pressed. Each function is closing over the character variable, which gets captured inside.After _ready() has finished running, the character variable won't exist anymore; but the lambda functions attached to each buttons will keep it inside, and can use it.