AXIsolatedObject support for table rows and ARIA tree/grid rows.
authorandresg_22@apple.com <andresg_22@apple.com@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Thu, 27 Feb 2020 22:59:24 +0000 (22:59 +0000)
committerandresg_22@apple.com <andresg_22@apple.com@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Thu, 27 Feb 2020 22:59:24 +0000 (22:59 +0000)
https://bugs.webkit.org/show_bug.cgi?id=208335

Reviewed by Chris Fleizach.

Covered by existing tests.

- Exposes the AccessibilityTableRow and AccessibilityARIAGridRow
interfaces through AXCoreObject.
- Eliminates the need of downcasting in the platform wrapper code, so
that it now works for both AXObjects and AXIsolatedObjects.
- Implements the above mentioned interfaces in AXIsolatedObject.

* accessibility/AccessibilityARIAGridRow.cpp:
(WebCore::AccessibilityARIAGridRow::disclosedRows):
* accessibility/AccessibilityARIAGridRow.h:
* accessibility/AccessibilityObject.cpp:
(WebCore::AccessibilityObject::disclosedRows):
(WebCore::AccessibilityObject::ariaTreeItemDisclosedRows): Became disclosedRows.
* accessibility/AccessibilityObject.h:
* accessibility/AccessibilityObjectInterface.h:
* accessibility/AccessibilityTableRow.h:
(WebCore::AccessibilityTableRow::setRowIndex):
(WebCore::AccessibilityTableRow::rowIndex const): Deleted.
* accessibility/isolatedtree/AXIsolatedObject.cpp:
(WebCore::AXIsolatedObject::initializeAttributeData):
* accessibility/isolatedtree/AXIsolatedObject.h:
* accessibility/mac/WebAccessibilityObjectWrapperMac.mm:
(-[WebAccessibilityObjectWrapper accessibilityAttributeValue:]):

git-svn-id: https://svn.webkit.org/repository/webkit/trunk@257589 268f45cc-cd09-0410-ab3c-d52691b4dbfc

Source/WebCore/ChangeLog
Source/WebCore/accessibility/AccessibilityARIAGridRow.cpp
Source/WebCore/accessibility/AccessibilityARIAGridRow.h
Source/WebCore/accessibility/AccessibilityObject.cpp
Source/WebCore/accessibility/AccessibilityObject.h
Source/WebCore/accessibility/AccessibilityObjectInterface.h
Source/WebCore/accessibility/AccessibilityTableRow.h
Source/WebCore/accessibility/isolatedtree/AXIsolatedObject.cpp
Source/WebCore/accessibility/isolatedtree/AXIsolatedObject.h
Source/WebCore/accessibility/mac/WebAccessibilityObjectWrapperMac.mm

index d4c6f71..57c734f 100644 (file)
@@ -1,3 +1,35 @@
+2020-02-27  Andres Gonzalez  <andresg_22@apple.com>
+
+        AXIsolatedObject support for table rows and ARIA tree/grid rows.
+        https://bugs.webkit.org/show_bug.cgi?id=208335
+
+        Reviewed by Chris Fleizach.
+
+        Covered by existing tests.
+
+        - Exposes the AccessibilityTableRow and AccessibilityARIAGridRow
+        interfaces through AXCoreObject.
+        - Eliminates the need of downcasting in the platform wrapper code, so
+        that it now works for both AXObjects and AXIsolatedObjects.
+        - Implements the above mentioned interfaces in AXIsolatedObject.
+
+        * accessibility/AccessibilityARIAGridRow.cpp:
+        (WebCore::AccessibilityARIAGridRow::disclosedRows):
+        * accessibility/AccessibilityARIAGridRow.h:
+        * accessibility/AccessibilityObject.cpp:
+        (WebCore::AccessibilityObject::disclosedRows):
+        (WebCore::AccessibilityObject::ariaTreeItemDisclosedRows): Became disclosedRows.
+        * accessibility/AccessibilityObject.h:
+        * accessibility/AccessibilityObjectInterface.h:
+        * accessibility/AccessibilityTableRow.h:
+        (WebCore::AccessibilityTableRow::setRowIndex):
+        (WebCore::AccessibilityTableRow::rowIndex const): Deleted.
+        * accessibility/isolatedtree/AXIsolatedObject.cpp:
+        (WebCore::AXIsolatedObject::initializeAttributeData):
+        * accessibility/isolatedtree/AXIsolatedObject.h:
+        * accessibility/mac/WebAccessibilityObjectWrapperMac.mm:
+        (-[WebAccessibilityObjectWrapper accessibilityAttributeValue:]):
+
 2020-02-27  Don Olmstead  <don.olmstead@sony.com>
 
         [CMake] Add WebKit::PAL target
index ebbe30f..c38dbcc 100644 (file)
@@ -55,19 +55,20 @@ bool AccessibilityARIAGridRow::isARIATreeGridRow() const
     return parent->isTreeGrid();
 }
     
-void AccessibilityARIAGridRow::disclosedRows(AccessibilityChildrenVector& disclosedRows)
+AXCoreObject::AccessibilityChildrenVector AccessibilityARIAGridRow::disclosedRows()
 {
+    AccessibilityChildrenVector disclosedRows;
     // The contiguous disclosed rows will be the rows in the table that 
     // have an aria-level of plus 1 from this row.
     AccessibilityObject* parent = parentObjectUnignored();
     if (!is<AccessibilityTable>(*parent) || !downcast<AccessibilityTable>(*parent).isExposable())
-        return;
+        return disclosedRows;
 
     // Search for rows that match the correct level. 
     // Only take the subsequent rows from this one that are +1 from this row's level.
     int index = rowIndex();
     if (index < 0)
-        return;
+        return disclosedRows;
 
     unsigned level = hierarchicalLevel();
     auto allRows = parent->rows();
@@ -80,6 +81,8 @@ void AccessibilityARIAGridRow::disclosedRows(AccessibilityChildrenVector& disclo
 
         disclosedRows.append(row);
     }
+
+    return disclosedRows;
 }
     
 AXCoreObject* AccessibilityARIAGridRow::disclosedByRow() const
index 8540683..4d3c831 100644 (file)
@@ -38,10 +38,10 @@ class AccessibilityARIAGridRow final : public AccessibilityTableRow {
 public:
     static Ref<AccessibilityARIAGridRow> create(RenderObject*);
     virtual ~AccessibilityARIAGridRow();
-    
-    void disclosedRows(AccessibilityChildrenVector&);
-    AXCoreObject* disclosedByRow() const;
-    
+
+    AccessibilityChildrenVector disclosedRows() override;
+    AXCoreObject* disclosedByRow() const override;
+
     AXCoreObject* headerObject() override;
     
 private:
index 952bbd7..ee83eab 100644 (file)
@@ -1822,8 +1822,10 @@ void AccessibilityObject::ariaTreeItemContent(AccessibilityChildrenVector& resul
     }
 }
 
-void AccessibilityObject::ariaTreeItemDisclosedRows(AccessibilityChildrenVector& result)
+AXCoreObject::AccessibilityChildrenVector AccessibilityObject::disclosedRows()
 {
+    AccessibilityChildrenVector result;
+
     for (const auto& obj : children()) {
         // Add tree items as the rows.
         if (obj->roleValue() == AccessibilityRole::TreeItem)
@@ -1831,9 +1833,11 @@ void AccessibilityObject::ariaTreeItemDisclosedRows(AccessibilityChildrenVector&
         // If it's not a tree item, then descend into the group to find more tree items.
         else 
             obj->ariaTreeRows(result);
-    }    
+    }
+
+    return result;
 }
-    
+
 const String AccessibilityObject::defaultLiveRegionStatusForRole(AccessibilityRole role)
 {
     switch (role) {
index 6b15de2..a13309b 100644 (file)
@@ -180,15 +180,22 @@ public:
     int axColumnIndex() const override { return -1; }
     int axRowIndex() const override { return -1; }
 
-    bool isTableRow() const override { return false; }
-
+    // Table column support.
     bool isTableColumn() const override { return false; }
     unsigned columnIndex() const override { return 0; }
     AXCoreObject* columnHeader() override { return nullptr; }
 
+    // Table row support.
+    bool isTableRow() const override { return false; }
+    unsigned rowIndex() const override { return 0; }
+
+    // ARIA tree/grid row support.
+    bool isARIATreeGridRow() const override { return false; }
+    AccessibilityChildrenVector disclosedRows() override; // ARIATreeItem implementation. AccessibilityARIAGridRow overrides this method.
+    AXCoreObject* disclosedByRow() const override { return nullptr; }
+
     bool isFieldset() const override { return false; }
     bool isGroup() const override { return false; }
-    bool isARIATreeGridRow() const override { return false; }
     bool isImageMapLink() const override { return false; }
     bool isMenuList() const override { return false; }
     bool isMenuListPopup() const override { return false; }
@@ -600,8 +607,6 @@ public:
 
     // Used by an ARIA tree to get all its rows.
     void ariaTreeRows(AccessibilityChildrenVector&) override;
-    // Used by an ARIA tree item to get all of its direct rows that it can disclose.
-    void ariaTreeItemDisclosedRows(AccessibilityChildrenVector&) override;
     // Used by an ARIA tree item to get only its content, and not its child tree items and groups.
     void ariaTreeItemContent(AccessibilityChildrenVector&) override;
 
index 204c98a..759e3f1 100644 (file)
@@ -561,16 +561,22 @@ public:
     virtual int axColumnIndex() const = 0;
     virtual int axRowIndex() const = 0;
 
-    virtual bool isTableRow() const = 0;
-
     // Table column support.
     virtual bool isTableColumn() const = 0;
     virtual unsigned columnIndex() const = 0;
     virtual AXCoreObject* columnHeader() = 0;
 
+    // Table row support.
+    virtual bool isTableRow() const = 0;
+    virtual unsigned rowIndex() const = 0;
+
+    // ARIA tree/grid row support.
+    virtual bool isARIATreeGridRow() const = 0;
+    virtual AccessibilityChildrenVector disclosedRows() = 0; // Also implemented by ARIATreeItems.
+    virtual AXCoreObject* disclosedByRow() const = 0;
+
     virtual bool isFieldset() const = 0;
     virtual bool isGroup() const = 0;
-    virtual bool isARIATreeGridRow() const = 0;
     virtual bool isImageMapLink() const = 0;
     virtual bool isMenuList() const = 0;
     virtual bool isMenuListPopup() const = 0;
@@ -1004,8 +1010,6 @@ public:
 
     // Used by an ARIA tree to get all its rows.
     virtual void ariaTreeRows(AccessibilityChildrenVector&) = 0;
-    // Used by an ARIA tree item to get all of its direct rows that it can disclose.
-    virtual void ariaTreeItemDisclosedRows(AccessibilityChildrenVector&) = 0;
     // Used by an ARIA tree item to get only its content, and not its child tree items and groups.
     virtual void ariaTreeItemContent(AccessibilityChildrenVector&) = 0;
 
index cf42578..95358cf 100644 (file)
@@ -42,9 +42,9 @@ public:
     // retrieves the "row" header (a th tag in the rightmost column)
     virtual AXCoreObject* headerObject();
     virtual AccessibilityTable* parentTable() const;
-    
-    void setRowIndex(int rowIndex) { m_rowIndex = rowIndex; }
-    int rowIndex() const { return m_rowIndex; }
+
+    void setRowIndex(unsigned rowIndex) { m_rowIndex = rowIndex; }
+    unsigned rowIndex() const override { return m_rowIndex; }
 
     // allows the table to add other children that may not originate
     // in the row, but their col/row spans overlap into it
@@ -65,7 +65,7 @@ private:
     AccessibilityObject* observableObject() const final;
     bool computeAccessibilityIsIgnored() const final;
 
-    int m_rowIndex;
+    unsigned m_rowIndex;
 };
 
 } // namespace WebCore
index d4946d5..8fc744d 100644 (file)
@@ -60,7 +60,6 @@ void AXIsolatedObject::initializeAttributeData(AXCoreObject& object, bool isRoot
     setProperty(AXPropertyName::Description, object.descriptionAttributeValue().isolatedCopy());
     setProperty(AXPropertyName::ElementRect, object.elementRect());
     setProperty(AXPropertyName::HelpText, object.helpTextAttributeValue().isolatedCopy());
-    setProperty(AXPropertyName::IsARIATreeGridRow, object.isARIATreeGridRow());
     setProperty(AXPropertyName::IsAccessibilityIgnored, object.accessibilityIsIgnored());
     setProperty(AXPropertyName::IsActiveDescendantOfFocusedContainer, object.isActiveDescendantOfFocusedContainer());
     setProperty(AXPropertyName::IsAttachment, object.isAttachment());
@@ -114,7 +113,6 @@ void AXIsolatedObject::initializeAttributeData(AXCoreObject& object, bool isRoot
     setProperty(AXPropertyName::IsSelectedOptionActive, object.isSelectedOptionActive());
     setProperty(AXPropertyName::IsSlider, object.isSlider());
     setProperty(AXPropertyName::IsStyleFormatGroup, object.isStyleFormatGroup());
-    setProperty(AXPropertyName::IsTableRow, object.isTableRow());
     setProperty(AXPropertyName::IsTextControl, object.isTextControl());
     setProperty(AXPropertyName::IsTree, object.isTree());
     setProperty(AXPropertyName::IsUnorderedList, object.isUnorderedList());
@@ -217,7 +215,7 @@ void AXIsolatedObject::initializeAttributeData(AXCoreObject& object, bool isRoot
     setProperty(AXPropertyName::LiveRegionAtomic, object.liveRegionAtomic());
 
     if (object.isTable()) {
-        setProperty(AXPropertyName::IsTable, object.isTable());
+        setProperty(AXPropertyName::IsTable, true);
         setProperty(AXPropertyName::IsExposable, object.isExposable());
         setProperty(AXPropertyName::IsDataTable, object.isDataTable());
         setProperty(AXPropertyName::TableLevel, object.tableLevel());
@@ -236,7 +234,7 @@ void AXIsolatedObject::initializeAttributeData(AXCoreObject& object, bool isRoot
     }
 
     if (object.isTableCell()) {
-        setProperty(AXPropertyName::IsTableCell, object.isTableCell());
+        setProperty(AXPropertyName::IsTableCell, true);
         setProperty(AXPropertyName::ColumnIndexRange, object.columnIndexRange());
         setProperty(AXPropertyName::RowIndexRange, object.rowIndexRange());
         setObjectVectorProperty(AXPropertyName::ColumnHeaders, object.columnHeaders());
@@ -246,11 +244,23 @@ void AXIsolatedObject::initializeAttributeData(AXCoreObject& object, bool isRoot
     }
 
     if (object.isTableColumn()) {
-        setProperty(AXPropertyName::IsTableColumn, object.isTableColumn());
+        setProperty(AXPropertyName::IsTableColumn, true);
         setProperty(AXPropertyName::ColumnIndex, object.columnIndex());
         setProperty(AXPropertyName::ColumnHeader, object.columnHeader());
+    } else if (object.isTableRow()) {
+        setProperty(AXPropertyName::IsTableRow, true);
+        setProperty(AXPropertyName::RowIndex, object.rowIndex());
     }
 
+    if (object.isARIATreeGridRow()) {
+        setProperty(AXPropertyName::IsARIATreeGridRow, true);
+        setObjectVectorProperty(AXPropertyName::DisclosedRows, object.disclosedRows());
+        setProperty(AXPropertyName::DisclosedByRow, object.disclosedByRow());
+    }
+
+    if (object.isTreeItem())
+        setObjectVectorProperty(AXPropertyName::DisclosedRows, object.disclosedRows());
+
     if (object.isTextControl())
         setProperty(AXPropertyName::TextLength, object.textLength());
 
@@ -270,10 +280,6 @@ void AXIsolatedObject::initializeAttributeData(AXCoreObject& object, bool isRoot
     object.ariaTreeRows(ariaTreeRows);
     setObjectVectorProperty(AXPropertyName::ARIATreeRows, ariaTreeRows);
 
-    AccessibilityChildrenVector ariaTreeItemDisclosedRows;
-    object.ariaTreeItemDisclosedRows(ariaTreeItemDisclosedRows);
-    setObjectVectorProperty(AXPropertyName::ARIATreeItemDisclosedRows, ariaTreeItemDisclosedRows);
-
     AccessibilityChildrenVector ariaTreeItemContent;
     object.ariaTreeItemContent(ariaTreeItemContent);
     setObjectVectorProperty(AXPropertyName::ARIATreeItemContent, ariaTreeItemContent);
index 5a03fd0..1371895 100644 (file)
@@ -94,7 +94,6 @@ private:
         ARIAFlowToElements,
         ARIALandmarkRoleDescription,
         ARIATreeItemContent,
-        ARIATreeItemDisclosedRows,
         ARIATreeRows,
         ARIARoleAttribute,
         ARIAOwnsElements,
@@ -133,6 +132,8 @@ private:
         DatetimeAttributeValue,
         DecrementButton,
         Description,
+        DisclosedByRow,
+        DisclosedRows,
         DocumentEncoding,
         DocumentURI,
         EditableAncestor,
@@ -287,6 +288,7 @@ private:
         Rows,
         RowCount,
         RowHeaders,
+        RowIndex,
         RowIndexRange,
         SelectedChildren,
         SelectedRadioButton,
@@ -414,16 +416,22 @@ private:
     int axColumnIndex() const override { return intAttributeValue(AXPropertyName::AXColumnIndex); }
     int axRowIndex() const override { return intAttributeValue(AXPropertyName::AXRowIndex); }
 
-    bool isTableRow() const override { return boolAttributeValue(AXPropertyName::IsTableRow); }
-
     // Table column support.
     bool isTableColumn() const override { return boolAttributeValue(AXPropertyName::IsTableColumn); }
     unsigned columnIndex() const override { return unsignedAttributeValue(AXPropertyName::ColumnIndex); }
     AXCoreObject* columnHeader() override { return objectAttributeValue(AXPropertyName::ColumnHeader); }
 
+    // Table row support.
+    bool isTableRow() const override { return boolAttributeValue(AXPropertyName::IsTableRow); }
+    unsigned rowIndex() const override { return unsignedAttributeValue(AXPropertyName::RowIndex); }
+
+    // ARIA tree/grid row support.
+    bool isARIATreeGridRow() const override { return boolAttributeValue(AXPropertyName::IsARIATreeGridRow); }
+    AccessibilityChildrenVector disclosedRows() override { return tree()->objectsForIDs(vectorAttributeValue<AXID>(AXPropertyName::DisclosedRows)); }
+    AXCoreObject* disclosedByRow() const override { return objectAttributeValue(AXPropertyName::DisclosedByRow); }
+
     bool isFieldset() const override { return boolAttributeValue(AXPropertyName::IsFieldset); }
     bool isGroup() const override { return boolAttributeValue(AXPropertyName::IsGroup); }
-    bool isARIATreeGridRow() const override { return boolAttributeValue(AXPropertyName::IsARIATreeGridRow); }
     bool isMenuList() const override { return boolAttributeValue(AXPropertyName::IsMenuList); }
     bool isMenuListPopup() const override { return boolAttributeValue(AXPropertyName::IsMenuListPopup); }
     bool isMenuListOption() const override { return boolAttributeValue(AXPropertyName::IsMenuListOption); }
@@ -526,7 +534,6 @@ private:
     bool isValueAutofillAvailable() const override { return boolAttributeValue(AXPropertyName::IsValueAutofillAvailable); }
     AutoFillButtonType valueAutofillButtonType() const override { return static_cast<AutoFillButtonType>(intAttributeValue(AXPropertyName::ValueAutofillButtonType)); }
     void ariaTreeRows(AccessibilityChildrenVector& children) override { fillChildrenVectorForProperty(AXPropertyName::ARIATreeRows, children); }
-    void ariaTreeItemDisclosedRows(AccessibilityChildrenVector& children) override { fillChildrenVectorForProperty(AXPropertyName::ARIATreeItemDisclosedRows, children); }
     void ariaTreeItemContent(AccessibilityChildrenVector& children) override { fillChildrenVectorForProperty(AXPropertyName::ARIATreeItemContent, children); }
     URL url() const override { return urlAttributeValue(AXPropertyName::URL); }
     String accessKey() const override { return stringAttributeValue(AXPropertyName::AccessKey); }
index 657e3f7..2fbacf4 100644 (file)
@@ -2818,25 +2818,15 @@ ALLOW_DEPRECATED_IMPLEMENTATIONS_END
 
             return nil;
         }
-        if (is<AccessibilityTableRow>(*backingObject)) {
-            if ([attributeName isEqualToString:NSAccessibilityIndexAttribute])
-                return [NSNumber numberWithInt:downcast<AccessibilityTableRow>(*backingObject).rowIndex()];
-        }
+
+        if (backingObject->isTableRow())
+            return [NSNumber numberWithInt:backingObject->rowIndex()];
     }
 
     // The rows that are considered inside this row.
     if ([attributeName isEqualToString:NSAccessibilityDisclosedRowsAttribute]) {
-        if (backingObject->isTreeItem()) {
-            AccessibilityObject::AccessibilityChildrenVector rowsCopy;
-            backingObject->ariaTreeItemDisclosedRows(rowsCopy);
-            return convertToNSArray(rowsCopy);
-        }
-
-        if (is<AccessibilityARIAGridRow>(*backingObject)) {
-            AccessibilityObject::AccessibilityChildrenVector rowsCopy;
-            downcast<AccessibilityARIAGridRow>(*backingObject).disclosedRows(rowsCopy);
-            return convertToNSArray(rowsCopy);
-        }
+        if (backingObject->isTreeItem() || backingObject->isARIATreeGridRow())
+            return convertToNSArray(backingObject->disclosedRows());
     }
 
     // The row that contains this row. It should be the same as the first parent that is a treeitem.
@@ -2854,11 +2844,9 @@ ALLOW_DEPRECATED_IMPLEMENTATIONS_END
             return nil;
         }
 
-        if (is<AccessibilityARIAGridRow>(*backingObject)) {
-            AXCoreObject* row = downcast<AccessibilityARIAGridRow>(*backingObject).disclosedByRow();
-            if (!row)
-                return nil;
-            return row->wrapper();
+        if (backingObject->isARIATreeGridRow()) {
+            auto* row = backingObject->disclosedByRow();
+            return row ? row->wrapper() : nil;
         }
     }