aboutsummaryrefslogtreecommitdiffstats
path: root/java/src/com/android/inputmethod/accessibility/KeyboardAccessibilityNodeProvider.java
diff options
context:
space:
mode:
Diffstat (limited to 'java/src/com/android/inputmethod/accessibility/KeyboardAccessibilityNodeProvider.java')
-rw-r--r--java/src/com/android/inputmethod/accessibility/KeyboardAccessibilityNodeProvider.java58
1 files changed, 54 insertions, 4 deletions
diff --git a/java/src/com/android/inputmethod/accessibility/KeyboardAccessibilityNodeProvider.java b/java/src/com/android/inputmethod/accessibility/KeyboardAccessibilityNodeProvider.java
index cb13483f2..61d066af5 100644
--- a/java/src/com/android/inputmethod/accessibility/KeyboardAccessibilityNodeProvider.java
+++ b/java/src/com/android/inputmethod/accessibility/KeyboardAccessibilityNodeProvider.java
@@ -65,6 +65,9 @@ final class KeyboardAccessibilityNodeProvider extends AccessibilityNodeProviderC
/** The virtual view identifier for the focused node. */
private int mAccessibilityFocusedView = UNDEFINED;
+ /** The virtual view identifier for the hovering node. */
+ private int mHoveringNodeId = UNDEFINED;
+
/** The current keyboard view. */
private final KeyboardView mKeyboardView;
@@ -76,7 +79,6 @@ final class KeyboardAccessibilityNodeProvider extends AccessibilityNodeProviderC
mKeyCodeDescriptionMapper = KeyCodeDescriptionMapper.getInstance();
mAccessibilityUtils = AccessibilityUtils.getInstance();
mKeyboardView = keyboardView;
- updateParentLocation();
// Since this class is constructed lazily, we might not get a subsequent
// call to setKeyboard() and therefore need to call it now.
@@ -141,6 +143,28 @@ final class KeyboardAccessibilityNodeProvider extends AccessibilityNodeProviderC
return event;
}
+ public void onHoverEnterTo(final Key key) {
+ final int id = getVirtualViewIdOf(key);
+ if (id == View.NO_ID) {
+ return;
+ }
+ // Start hovering on the key. Because our accessibility model is lift-to-type, we should
+ // report the node info without click and long click actions to avoid unnecessary
+ // announcements.
+ mHoveringNodeId = id;
+ // Invalidate the node info of the key.
+ sendAccessibilityEventForKey(key, AccessibilityEventCompat.TYPE_WINDOW_CONTENT_CHANGED);
+ sendAccessibilityEventForKey(key, AccessibilityEventCompat.TYPE_VIEW_HOVER_ENTER);
+ }
+
+ public void onHoverExitFrom(final Key key) {
+ mHoveringNodeId = UNDEFINED;
+ // Invalidate the node info of the key to be able to revert the change we have done
+ // in {@link #onHoverEnterTo(Key)}.
+ sendAccessibilityEventForKey(key, AccessibilityEventCompat.TYPE_WINDOW_CONTENT_CHANGED);
+ sendAccessibilityEventForKey(key, AccessibilityEventCompat.TYPE_VIEW_HOVER_EXIT);
+ }
+
/**
* Returns an {@link AccessibilityNodeInfoCompat} representing a virtual
* view, i.e. a descendant of the host View, with the given <code>virtualViewId</code> or
@@ -169,10 +193,23 @@ final class KeyboardAccessibilityNodeProvider extends AccessibilityNodeProviderC
}
if (virtualViewId == View.NO_ID) {
// We are requested to create an AccessibilityNodeInfo describing
- // this View. Returning an empty info is sufficient for a keyboard.
+ // this View, i.e. the root of the virtual sub-tree.
final AccessibilityNodeInfoCompat rootInfo =
AccessibilityNodeInfoCompat.obtain(mKeyboardView);
ViewCompat.onInitializeAccessibilityNodeInfo(mKeyboardView, rootInfo);
+ updateParentLocation();
+
+ // Add the virtual children of the root View.
+ final List<Key> sortedKeys = mKeyboard.getSortedKeys();
+ final int size = sortedKeys.size();
+ for (int index = 0; index < size; index++) {
+ final Key key = sortedKeys.get(index);
+ if (key.isSpacer()) {
+ continue;
+ }
+ // Use an index of the sorted keys list as a virtual view id.
+ rootInfo.addChild(mKeyboardView, index);
+ }
return rootInfo;
}
@@ -200,9 +237,16 @@ final class KeyboardAccessibilityNodeProvider extends AccessibilityNodeProviderC
info.setBoundsInScreen(boundsInScreen);
info.setParent(mKeyboardView);
info.setSource(mKeyboardView, virtualViewId);
- info.setBoundsInScreen(boundsInScreen);
- info.setEnabled(true);
+ info.setEnabled(key.isEnabled());
info.setVisibleToUser(true);
+ // Don't add ACTION_CLICK and ACTION_LONG_CLOCK actions while hovering on the key.
+ // See {@link #onHoverEnterTo(Key)} and {@link #onHoverExitFrom(Key)}.
+ if (virtualViewId != mHoveringNodeId) {
+ info.addAction(AccessibilityNodeInfoCompat.ACTION_CLICK);
+ if (key.isLongPressEnabled()) {
+ info.addAction(AccessibilityNodeInfoCompat.ACTION_LONG_CLICK);
+ }
+ }
if (mAccessibilityFocusedView == virtualViewId) {
info.addAction(AccessibilityNodeInfoCompat.ACTION_CLEAR_ACCESSIBILITY_FOCUS);
@@ -241,6 +285,12 @@ final class KeyboardAccessibilityNodeProvider extends AccessibilityNodeProviderC
sendAccessibilityEventForKey(
key, AccessibilityEventCompat.TYPE_VIEW_ACCESSIBILITY_FOCUS_CLEARED);
return true;
+ case AccessibilityNodeInfoCompat.ACTION_CLICK:
+ sendAccessibilityEventForKey(key, AccessibilityEvent.TYPE_VIEW_CLICKED);
+ return true;
+ case AccessibilityNodeInfoCompat.ACTION_LONG_CLICK:
+ sendAccessibilityEventForKey(key, AccessibilityEvent.TYPE_VIEW_LONG_CLICKED);
+ return true;
default:
return false;
}