Skip to content

Commit

Permalink
Redirect "ui_accept" input for specific Tree edge cases.
Browse files Browse the repository at this point in the history
Trees appear to eat "ui_accept" before `gui_input` receives it. This makes certain use cases--triggering buttons in cells--impossible via the keyboard.

Here, `ScreenReader` attempts to intercept recent presses of "ui_accept" and, if a button in a cell should receive focus, redirects the `InputEvent` to the custom handler for `Tree`.

Unfortunately, this loses the ability to click buttons in cells in the editor's node tree for some reason. It restores, or maybe gets working in the first place, clicking on the _Remove_ button in the input mapping screen. Not sure how to restore the former functionality--these trees are complex and not well-documented.
  • Loading branch information
ndarilek committed Jul 22, 2020
1 parent d522da8 commit 6beeaa0
Show file tree
Hide file tree
Showing 2 changed files with 32 additions and 11 deletions.
31 changes: 20 additions & 11 deletions Accessible.gd
Original file line number Diff line number Diff line change
Expand Up @@ -351,6 +351,8 @@ func text_edit_input(event):

var _last_tree_item_tokens

var button_index


func _tree_item_render():
if not node.has_focus():
Expand All @@ -372,20 +374,29 @@ func _tree_item_render():
tokens.append("expanded")
var button_count = cell.get_button_count(i)
if button_count != 0:
button_index = 0
var column
for j in range(node.columns):
if cell.is_selected(j):
column = j
break
if column == i:
button_index = 0
else:
button_index = null
tokens.append(
(
str(button_count)
+ " "
+ TTS.singular_or_plural(button_count, "button", "buttons")
)
)
var button_tooltip = cell.get_button_tooltip(i, button_index)
if button_tooltip:
tokens.append(button_tooltip)
tokens.append("button")
if button_count > 1:
tokens.append("Use Home and End to switch focus.")
if button_index != null:
var button_tooltip = cell.get_button_tooltip(i, button_index)
if button_tooltip:
tokens.append(button_tooltip)
tokens.append("button")
if button_count > 1:
tokens.append("Use Home and End to switch focus.")
tokens.append("tree item")
if tokens != _last_tree_item_tokens:
TTS.speak(tokens.join(": "), true)
Expand All @@ -394,8 +405,6 @@ func _tree_item_render():

var prev_selected_cell

var button_index


func _tree_item_or_cell_selected():
button_index = null
Expand Down Expand Up @@ -430,8 +439,8 @@ func _tree_input(event):
node.rect_global_position.y + area.position.y + area.size.y / 2
)
node.get_tree().root.warp_mouse(position)
if item and column != null and button_index != null:
if event.is_action_pressed("ui_accept"):
if item and column != null and item.get_button_count(column):
if Input.is_action_just_pressed("ui_accept"):
node.accept_event()
return node.emit_signal("button_pressed", item, column, button_index + 1)
var new_button_index = button_index
Expand Down
12 changes: 12 additions & 0 deletions ScreenReader.gd
Original file line number Diff line number Diff line change
Expand Up @@ -173,6 +173,18 @@ var in_focus_mode_handler = false
func _input(event):
if not enabled:
return
var focus = find_focusable_control(get_tree().root)
if focus:
focus = focus.get_focus_owner()
if focus is Tree and Input.is_action_just_pressed("ui_accept"):
var accessible
for n in focus.get_children():
if n is Accessible:
accessible = n
break
if accessible and accessible.button_index != null:
accessible._tree_input(event)
get_tree().set_input_as_handled()
if enable_focus_mode:
if (
event is InputEventKey
Expand Down

4 comments on commit 6beeaa0

@follower
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Just as an FYI, Godot's Tree is currently quite broken with regard to keyboard support due to a number of issues introduced when it was moved from direct keyboard input to action-based input.

I had to write a wrapper to workaround some of the issues for a project I'm working on.

I'm partway through writing up an issue describing all the issues I encountered but...it's currently disappeared in all the tabs I currently have open. :)

@follower
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Update: Added an issue here: godotengine/godot#41014 with a supporting comment here: godotengine/godot#36291 (comment)

@ndarilek
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Nice, any chance your wrapper is easy to extract and share?

I'm vaguely thinking of some sort of accessibility/audio-related utility pack separate from this plugin, and separate from but used by the accessible starter template. Candidates for inclusion are my audio hack to use 3-D audio streams in 2-D, helpers for automatically stopping speech under certain conditions, etc. Not all of them would need to be used in a given project, but they'd be general patterns for making accessible games that aren't necessarily universal but are still common.

Anyhow, a more accessible Tree wrapper would be amazing, as that widget has been the bane of my existence since I started trying to work with it. Future titles I'm planning would make heavy use of trees, and having them actually work as intended would be key to that. :)

And thanks for filing that issue. Diagnosing tree issues is hard when you can't actually see what they do visually and how that reflects in the data they expose.

@follower
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Nice, any chance your wrapper is easy to extract and share?

I had done a quick copy paste of the code and put it in this follow-up comment but I wasn't sure if the screen reader software you use works with the "disclosure triangle": godotengine/godot#41014 (comment)

So have just pasted into the following new issue for you, in case it's helpful: #2

Diagnosing tree issues is hard when you can't actually see what they do visually and how that reflects in the data they expose.

It took a lot of time to figure out the Tree control issues even with being able to see what they were doing visually, so I imagine it was incredibly frustrating without!

How about we move further Tree control-related discussion to: #2

Future titles I'm planning would make heavy use of trees, and having them actually work as intended would be key to that. :)

Lol, indeed. :)

BTW there was a discussion on Hacker News the other day about "Making Advanced GUI Applications with Godot" where the lack of accessibility was brought up, I mentioned this project in a couple of comments and you might find the thread interesting to read/comment in. (Or, I guess, given some of the comments, frustrating. :/ )

Some weeks ago I actually started writing up a more general discussion issue when I first discovered this project in relation to some of the things you mentioned in the README, so I think I'll quickly paste what I started in another new issue & maybe we can continue wider discussion there.

Please sign in to comment.