Fix every button being permanently blocked after closing the build menu
The real cause of "the crafter buttons do nothing", reported three times. IconButton._blocked_by_modal tested `menu.visible`, but hiding a parent leaves a child's own `visible` flag true - and the build menu's info popup is itself one of the modal panels. So opening any building's info popup and then closing the build menu with the X left an invisible popup still claiming to be open, and from that moment EVERY button in the game was blocked, with no way for a player to get out of it. It tests is_visible_in_tree() now, and closing the build menu also closes its popup rather than leaving it half-open. My earlier attempts kept missing it because the probes called the handlers directly - they exercised the crafter logic, which was fine all along, and never the input path in that state. The regression test reproduces the exact sequence: open the build menu, show a building's info, hide the menu, then check an unrelated button still fires. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
This commit is contained in:
parent
1cbae8ff70
commit
ee9d6ad9c6
3 changed files with 40 additions and 2 deletions
|
|
@ -148,7 +148,7 @@ var pending_time: float = 0.0
|
|||
|
||||
func _ready() -> void:
|
||||
build_button.pressed.connect(_on_build_pressed)
|
||||
build_close_button.pressed.connect(func(): build_menu.visible = false)
|
||||
build_close_button.pressed.connect(_close_build_menu)
|
||||
build_mothership_button.pressed.connect(_on_place_mothership)
|
||||
build_crafter_button.pressed.connect(_on_place_crafter)
|
||||
build_command_button.pressed.connect(_on_place_command_center)
|
||||
|
|
@ -394,6 +394,14 @@ func _on_place_command_center() -> void:
|
|||
_show_building_info(GameState.BUILDING_COMMAND_CENTER)
|
||||
|
||||
|
||||
func _close_build_menu() -> void:
|
||||
# The popup is a child panel of this menu; leaving it "open" while its
|
||||
# parent is hidden is what blocked every button in the game.
|
||||
info_popup.visible = false
|
||||
pending_build_type = ""
|
||||
build_menu.visible = false
|
||||
|
||||
|
||||
func _on_place_ship_lab() -> void:
|
||||
_show_building_info(GameState.BUILDING_SHIP_LAB)
|
||||
|
||||
|
|
|
|||
|
|
@ -61,7 +61,13 @@ func _blocked_by_modal() -> bool:
|
|||
# there. So the panels stay transparent to input and the buttons check
|
||||
# instead.
|
||||
for menu in get_tree().get_nodes_in_group("modal_menus"):
|
||||
if menu.visible and not menu.is_ancestor_of(self):
|
||||
# is_visible_in_tree(), NOT visible. Hiding a parent leaves the
|
||||
# child's own `visible` flag true, and the build menu's info popup is
|
||||
# itself a modal panel - so closing the build menu with the X left an
|
||||
# invisible popup still claiming to be open, and every button in the
|
||||
# game was blocked from then on. That is not a state a player can
|
||||
# get out of.
|
||||
if menu.is_visible_in_tree() and not menu.is_ancestor_of(self):
|
||||
return true
|
||||
return false
|
||||
|
||||
|
|
|
|||
|
|
@ -132,6 +132,30 @@ func _process(delta: float) -> bool:
|
|||
quit(1)
|
||||
return true
|
||||
print("touch on the panel consumed, fleet target unchanged")
|
||||
|
||||
# --- 5. a hidden parent must not leave a panel "open" -------
|
||||
# The build menu's info popup is itself a modal panel. Hiding the
|
||||
# build menu leaves the popup's own `visible` flag true, so a
|
||||
# guard testing `visible` rather than `is_visible_in_tree()`
|
||||
# blocked EVERY button in the game from then on - with no way for
|
||||
# a player to get out of it. Reported three times as "the buttons
|
||||
# do nothing".
|
||||
skill_menu.visible = false
|
||||
var controller2: Node = scene.get_node("BuildController")
|
||||
controller2._on_build_pressed()
|
||||
controller2._show_building_info(GameState.BUILDING_SHIP_CRAFTER)
|
||||
scene.get_node("UI/BuildMenu").visible = false
|
||||
var info: Control = scene.get_node("UI/BuildMenu/InfoPopup")
|
||||
print("popup after hiding its parent: visible=%s in_tree=%s" % [
|
||||
info.visible, info.is_visible_in_tree()
|
||||
])
|
||||
outside_fired = false
|
||||
_tap(map_button)
|
||||
if not outside_fired:
|
||||
print("TEST_MODAL_BLOCKS_INPUT: FAIL (a panel hidden with its parent still blocks every button)")
|
||||
quit(1)
|
||||
return true
|
||||
print("hidden-with-parent panel no longer blocks anything")
|
||||
print("TEST_MODAL_BLOCKS_INPUT: PASS")
|
||||
quit(0)
|
||||
return true
|
||||
|
|
|
|||
Loading…
Reference in a new issue