diff --git a/addons/escoria-core/game/core-scripts/esc/types/esc_dialog.gd b/addons/escoria-core/game/core-scripts/esc/types/esc_dialog.gd index 0b89d3d9..77fe9d5c 100644 --- a/addons/escoria-core/game/core-scripts/esc/types/esc_dialog.gd +++ b/addons/escoria-core/game/core-scripts/esc/types/esc_dialog.gd @@ -90,9 +90,17 @@ func run(): escoria.dialog_player, "option_chosen" ) as ESCDialogOption - var rc = option.run() - if rc is GDScriptFunctionState: - rc = yield(rc, "completed") - if rc != ESCExecution.RC_CANCEL: - return self.run() + + var rc = ESCExecution.RC_OK + + # If no valid option was returned, it means this level of dialog is done. + # If this is the case and the current level of dialog has a parent, it means + # it is still yielding and so will be shown again. + if option: + rc = option.run() + if rc is GDScriptFunctionState: + rc = yield(rc, "completed") + if rc != ESCExecution.RC_CANCEL: + return self.run() + return rc diff --git a/addons/escoria-dialog-simple/chooser/simple.gd b/addons/escoria-dialog-simple/chooser/simple.gd index 5b5b1fa7..278629af 100644 --- a/addons/escoria-dialog-simple/chooser/simple.gd +++ b/addons/escoria-dialog-simple/chooser/simple.gd @@ -2,10 +2,14 @@ # Supports timeout and avatar display extends ESCDialogOptionsChooser + export(Color, RGB) var color_normal = Color(1.0,1.0,1.0,1.0) export(Color, RGB) var color_hover = Color(165.0,42.0,42.0, 1.0) +var _no_more_options: bool = false + + # Hide the chooser at the start just to be safe func _ready() -> void: hide_chooser() @@ -40,6 +44,15 @@ func show_chooser(): option ]) + # If we've no options left, signify as much and start the timer with a + # very short interval so the appropriate signal can be fired. Note that + # we have to fire the signal AFTER this method returns as the caller + # is almost certainly yielding after this method returns. + if _vbox.get_child_count() == 0: + _no_more_options = true + $Timer.start(0.05) + return + if self.dialog.avatar != "-": $AvatarContainer.add_child( ResourceLoader.load(self.dialog.avatar).instance() @@ -76,7 +89,9 @@ func _on_answer_selected(option: ESCDialogOption): # The timeout came and a option was selected func _on_Timer_timeout() -> void: - _option_chosen(self.dialog.options[self.dialog.timeout_option - 1]) + var option_chosen = null if _no_more_options else self.dialog.options[self.dialog.timeout_option - 1] + _no_more_options = false + _option_chosen(option_chosen) # Remove the avatar