changeset 7218:570ce4be0938

RT-36630: [Accessibility] Mac, sometimes VO focus starts at the wrong node
author Felipe Heidrich <felipe.heidrich@oracle.com>
date Mon, 09 Jun 2014 13:22:14 -0700
parents bc2f5bd0feac
children 8a087879ffc5
files modules/graphics/src/main/java/com/sun/glass/ui/mac/MacAccessible.java modules/graphics/src/main/java/com/sun/glass/ui/win/WinAccessible.java modules/graphics/src/main/java/javafx/scene/Node.java
diffstat 3 files changed, 42 insertions(+), 0 deletions(-) [+]
line wrap: on
line diff
--- a/modules/graphics/src/main/java/com/sun/glass/ui/mac/MacAccessible.java	Mon Jun 09 13:54:29 2014 -0700
+++ b/modules/graphics/src/main/java/com/sun/glass/ui/mac/MacAccessible.java	Mon Jun 09 13:22:14 2014 -0700
@@ -776,6 +776,9 @@
                 }
                 break;
             }
+            case PARENT:
+                ignoreInnerText = null;
+                break;
             default:
                 macNotification = MacNotification.NSAccessibilityValueChangedNotification;
         }
@@ -830,6 +833,39 @@
         return inSlider;
     }
 
+    Boolean ignoreInnerText;
+    boolean ignoreInnerText() {
+        if (ignoreInnerText != null) return ignoreInnerText;
+        /* JavaFX controls are implemented by the skin by adding new nodes.
+         * In accessibility these nodes sometimes duplicate the data in the
+         * control. For example, a Label is implemented using a Text, creating a
+         * AXStaticText inside an AXStaticText. In order to  improve accessibility
+         * navigation to following code ignores these inner text for the most 
+         * common cases.
+         */
+        Role role = (Role)getAttribute(ROLE);
+        ignoreInnerText = false;
+        if (role == Role.TEXT) {
+            Node parent = (Node)getAttribute(PARENT);
+            if (parent == null) return ignoreInnerText;
+            Role parentRole = (Role)parent.getAccessible().getAttribute(ROLE);
+            if (parentRole == null) return ignoreInnerText;
+            switch (parentRole) {
+                case BUTTON:
+                case TOGGLE_BUTTON:
+                case CHECKBOX:
+                case RADIO_BUTTON:
+                case COMBOBOX:
+                case TEXT:
+                case HYPERLINK:
+                case TAB_ITEM:
+                    ignoreInnerText = true;
+                default:
+            }
+        }
+        return ignoreInnerText;
+    }
+
     private int getMenuItemCmdGlyph(KeyCode code) {
         // Based on System/Library/Frameworks/Carbon.framework/Frameworks/HIToolbox.framework/Headers/Menus.h
         switch (code) {
@@ -1758,6 +1794,9 @@
             Role role = (Role)getAttribute(ROLE);
             return role != Role.CONTEXT_MENU && role != Role.MENU_ITEM && role != Role.MENU_BAR;
         }
+        if (ignoreInnerText()) {
+            return true;
+        }
         return false;
     }
 
--- a/modules/graphics/src/main/java/com/sun/glass/ui/win/WinAccessible.java	Mon Jun 09 13:54:29 2014 -0700
+++ b/modules/graphics/src/main/java/com/sun/glass/ui/win/WinAccessible.java	Mon Jun 09 13:22:14 2014 -0700
@@ -413,6 +413,8 @@
                 }
                 break;
             }
+            case PARENT:
+                break;
             default:
                 UiaRaiseAutomationEvent(peer, UIA_AutomationPropertyChangedEventId);
         }
--- a/modules/graphics/src/main/java/javafx/scene/Node.java	Mon Jun 09 13:54:29 2014 -0700
+++ b/modules/graphics/src/main/java/javafx/scene/Node.java	Mon Jun 09 13:22:14 2014 -0700
@@ -745,6 +745,7 @@
                     oldParent = newParent;
                     invalidateLocalToSceneTransform();
                     parentResolvedOrientationInvalidated();
+                    accSendNotification(Attribute.PARENT);
                 }
 
                 @Override