tor-browser

The Tor Browser
git clone https://git.dasho.dev/tor-browser.git
Log | Files | Refs | README | LICENSE

commit f06208ee3fb1188af2e93963d3ffd31f4b249ec5
parent 747ff4fee1e67b4babd34a4c9282f5f4031223eb
Author: iulian moraru <imoraru@mozilla.com>
Date:   Fri, 21 Nov 2025 03:21:34 +0200

Revert "Bug 1998242, Bug 1998255 1998255: apply code formatting via Lando" for causing dt failures on browser_accessibility_print_to_json.js.

This reverts commit d42283eaecd029884c6650cc39e7bc72813774b1.

Revert "Bug 1998255 - P4: Calculate labeled names remotely. r=morgan"

This reverts commit 4684fdbfa0261bef0c87078ca7af772a921f4fc6.

Revert "Bug 1998255 - P3: Return eNameFromRelations when name was exclusively calculated from relations. r=morgan"

This reverts commit 15919fad2fd9f25803177ede846a1ddc129f1a95.

Revert "Bug 1998255 - P2: Have GetTextEquivFromIDRefs return true if it used hidden content or referenced itself. r=morgan"

This reverts commit 2b6d3df0da0dd82b8e5f0bcbd979ffaeb9b5b8ab.

Revert "Bug 1998255 - P1: Intro and use ArrayAccIterator. r=morgan"

This reverts commit c6454665b0fac3766fda88243a948dd077847952.

Revert "Bug 1998242 - P5: Perform subtree name calculation in RemoteAccessible::Name. r=morgan"

This reverts commit 0629edfc297d29a276231f96618eee0c1511b4f7.

Revert "Bug 1998242 - P4: Break up name calculation to allow remote subtree calc. r=morgan"

This reverts commit 24e6864b25e87f383ecf373dd5af51f5d7b6df50.

Revert "Bug 1998242 - P3: Introduce DirectName() to be used by Name(). r=morgan"

This reverts commit 63a23a03e0a36855c9a2a144a6379772de36ea01.

Revert "Bug 1998242 - P2: Don't rely on NativeName override to suppress subtree name calc. r=morgan"

This reverts commit 95638bb76c40df06da5c07a0a77bfaf58e4af060.

Revert "Bug 1998242 - P1: Factor out tooltip calculation. r=morgan"

This reverts commit 25a9efa9b2cc3127dd745f22283d36d40a948cd1.

Diffstat:
Maccessible/atk/AccessibleWrap.cpp | 2--
Maccessible/atk/ApplicationAccessibleWrap.cpp | 2+-
Maccessible/atk/ApplicationAccessibleWrap.h | 3+--
Maccessible/base/AccIterator.cpp | 11-----------
Maccessible/base/AccIterator.h | 17-----------------
Maccessible/base/CacheConstants.h | 7+++----
Maccessible/base/CssAltContent.cpp | 4----
Maccessible/base/EventQueue.cpp | 2+-
Maccessible/base/nsTextEquivUtils.cpp | 135++++++++++++++++++++-----------------------------------------------------------
Maccessible/base/nsTextEquivUtils.h | 45+++++++++++++++++++--------------------------
Maccessible/generic/ApplicationAccessible.cpp | 2+-
Maccessible/generic/ApplicationAccessible.h | 2+-
Maccessible/generic/DocAccessible.cpp | 4++--
Maccessible/generic/DocAccessible.h | 3+--
Maccessible/generic/LocalAccessible.cpp | 160++++++++++++++++++++++++++++++++++++-------------------------------------------
Maccessible/generic/LocalAccessible.h | 10+---------
Maccessible/generic/RootAccessible.cpp | 4++--
Maccessible/generic/RootAccessible.h | 3+--
Maccessible/generic/TextLeafAccessible.cpp | 2+-
Maccessible/generic/TextLeafAccessible.h | 2+-
Maccessible/html/HTMLElementAccessibles.cpp | 3++-
Maccessible/html/HTMLFormControlAccessible.cpp | 34+++++++++++-----------------------
Maccessible/html/HTMLFormControlAccessible.h | 4++--
Maccessible/html/HTMLListAccessible.cpp | 2+-
Maccessible/html/HTMLListAccessible.h | 2+-
Maccessible/html/HTMLTableAccessible.cpp | 22++++++++++++++++++----
Maccessible/html/HTMLTableAccessible.h | 3+++
Maccessible/ipc/RemoteAccessible.cpp | 90++++++++++++++++++++-----------------------------------------------------------
Maccessible/ipc/RemoteAccessible.h | 4++--
Maccessible/mac/mozAccessible.mm | 3---
Maccessible/tests/browser/caching_granularity/browser_name_and_description_domain.js | 4++--
Maccessible/tests/browser/name_and_description/browser_name_general.js | 21+++++++--------------
Maccessible/tests/mochitest/name/markuprules.xml | 4++--
Maccessible/xul/XULAlertAccessible.cpp | 2+-
Maccessible/xul/XULAlertAccessible.h | 3+--
Maccessible/xul/XULElementAccessibles.cpp | 5++++-
Maccessible/xul/XULMenuAccessible.cpp | 4++--
Maccessible/xul/XULMenuAccessible.h | 2+-
Maccessible/xul/XULTreeAccessible.cpp | 2+-
Maccessible/xul/XULTreeAccessible.h | 2+-
Maccessible/xul/XULTreeGridAccessible.cpp | 4++--
Maccessible/xul/XULTreeGridAccessible.h | 4++--
42 files changed, 231 insertions(+), 413 deletions(-)

diff --git a/accessible/atk/AccessibleWrap.cpp b/accessible/atk/AccessibleWrap.cpp @@ -964,8 +964,6 @@ void a11y::PlatformEvent(Accessible* aTarget, uint32_t aEventType) { g_signal_emit_by_name(wrapper, "text-attributes-changed"); break; case nsIAccessibleEvent::EVENT_NAME_CHANGE: { - // Don't want to passively activate the cache because a name changed. - CacheDomainActivationBlocker cacheBlocker; nsAutoString newName; aTarget->Name(newName); MaybeFireNameChange(wrapper, newName); diff --git a/accessible/atk/ApplicationAccessibleWrap.cpp b/accessible/atk/ApplicationAccessibleWrap.cpp @@ -66,7 +66,7 @@ gboolean toplevel_event_watcher(GSignalInvocationHint* ihint, return TRUE; } -ENameValueFlag ApplicationAccessibleWrap::DirectName(nsString& aName) const { +ENameValueFlag ApplicationAccessibleWrap::Name(nsString& aName) const { // ATK doesn't provide a way to obtain an application name (for example, // Firefox or Thunderbird) like IA2 does. Thus let's return an application // name as accessible name that was used to get a branding name (for example, diff --git a/accessible/atk/ApplicationAccessibleWrap.h b/accessible/atk/ApplicationAccessibleWrap.h @@ -18,8 +18,7 @@ class ApplicationAccessibleWrap : public ApplicationAccessible { virtual ~ApplicationAccessibleWrap(); // LocalAccessible - virtual mozilla::a11y::ENameValueFlag DirectName( - nsString& aName) const override; + virtual mozilla::a11y::ENameValueFlag Name(nsString& aName) const override; virtual bool InsertChildAt(uint32_t aIdx, LocalAccessible* aChild) override; virtual bool RemoveChild(LocalAccessible* aChild) override; diff --git a/accessible/base/AccIterator.cpp b/accessible/base/AccIterator.cpp @@ -411,14 +411,3 @@ Accessible* RemoteAccIterator::Next() { } return nullptr; } - -//////////////////////////////////////////////////////////////////////////////// -// ArrayAccIterator -//////////////////////////////////////////////////////////////////////////////// - -Accessible* ArrayAccIterator::Next() { - if (mIndex < mAccs.Length()) { - return mAccs[mIndex++]; - } - return nullptr; -} diff --git a/accessible/base/AccIterator.h b/accessible/base/AccIterator.h @@ -333,23 +333,6 @@ class RemoteAccIterator : public AccIterable { uint32_t mIndex; }; -/** - * Used to iterate through an array of accessibles - */ -class ArrayAccIterator : public AccIterable { - public: - explicit ArrayAccIterator(nsTArray<Accessible*>&& aAccs) - : mAccs(std::move(aAccs)), mIndex(0) {} - - virtual ~ArrayAccIterator() = default; - - virtual Accessible* Next() override; - - private: - nsTArray<Accessible*> mAccs; - uint32_t mIndex; -}; - } // namespace a11y } // namespace mozilla diff --git a/accessible/base/CacheConstants.h b/accessible/base/CacheConstants.h @@ -160,8 +160,6 @@ class CacheKey { // CSS position; e.g. fixed. static constexpr nsStaticAtom* CssPosition = nsGkAtoms::position; // nsString, CacheDomain::NameAndDescription - static constexpr nsStaticAtom* CssAltContent = nsGkAtoms::content; - // nsString, CacheDomain::NameAndDescription static constexpr nsStaticAtom* Description = nsGkAtoms::description; // EDescriptionValueFlag, CacheDomain::NameAndDescription // Returned by Accessible::Description. @@ -209,6 +207,9 @@ class CacheKey { static constexpr nsStaticAtom* MinValue = nsGkAtoms::min; // nsString, CacheDomain::NameAndDescription static constexpr nsStaticAtom* Name = nsGkAtoms::name; + // ENameValueFlag, CacheDomain::NameAndDescription + // Returned by Accessible::Name. + static constexpr nsStaticAtom* NameValueFlag = nsGkAtoms::explicit_name; // double, CacheDomain::Value // The numeric value returned by Accessible::CurValue. static constexpr nsStaticAtom* NumericValue = nsGkAtoms::value; @@ -267,8 +268,6 @@ class CacheKey { // The textual value returned by Accessible::Value (as opposed to // the numeric value returned by Accessible::CurValue). static constexpr nsStaticAtom* TextValue = nsGkAtoms::aria_valuetext; - // nsString, CacheDomain::NameAndDescription - static constexpr nsStaticAtom* Tooltip = nsGkAtoms::tooltip; // gfx::Matrix4x4, CacheDomain::TransformMatrix static constexpr nsStaticAtom* TransformMatrix = nsGkAtoms::transform; // int32_t, CacheDomain::Value diff --git a/accessible/base/CssAltContent.cpp b/accessible/base/CssAltContent.cpp @@ -17,10 +17,6 @@ namespace mozilla::a11y { CssAltContent::CssAltContent(nsIContent* aContent) { - if (!aContent) { - return; - } - nsIFrame* frame = aContent->GetPrimaryFrame(); if (!frame) { return; diff --git a/accessible/base/EventQueue.cpp b/accessible/base/EventQueue.cpp @@ -130,7 +130,7 @@ bool EventQueue::PushNameOrDescriptionChange(AccEvent* aOrigEvent) { bool fireNameChange = parent->IsHTMLFileInput(); if (!fireNameChange) { nsAutoString name; - ENameValueFlag nameFlag = parent->DirectName(name); + ENameValueFlag nameFlag = parent->Name(name); switch (nameFlag) { case eNameOK: // Descendants of subtree may have been removed, making the name diff --git a/accessible/base/nsTextEquivUtils.cpp b/accessible/base/nsTextEquivUtils.cpp @@ -11,7 +11,6 @@ #include "AccIterator.h" #include "CssAltContent.h" #include "nsCoreUtils.h" -#include "Relation.h" #include "mozilla/dom/ChildIterator.h" #include "mozilla/dom/Text.h" @@ -46,20 +45,8 @@ static nsTHashSet<const Accessible*>& GetReferencedAccs() { //////////////////////////////////////////////////////////////////////////////// // nsTextEquivUtils. Public. -bool nsTextEquivUtils::HasNameRule(const Accessible* aAccessible, - ETextEquivRule aRule) { - uint32_t rule = GetRoleRule(aAccessible->Role()); - if (aAccessible->IsHTMLTableRow() && !aAccessible->HasStrongARIARole()) { - // For table row accessibles, we only want to calculate the name from the - // sub tree if an ARIA role is present. - rule = eNameFromSubtreeIfReqRule; - } - - return (rule & aRule) == aRule; -} - -nsresult nsTextEquivUtils::GetNameFromSubtree(const Accessible* aAccessible, - nsAString& aName) { +nsresult nsTextEquivUtils::GetNameFromSubtree( + const LocalAccessible* aAccessible, nsAString& aName) { aName.Truncate(); if (GetReferencedAccs().Contains(aAccessible)) { @@ -72,18 +59,24 @@ nsresult nsTextEquivUtils::GetNameFromSubtree(const Accessible* aAccessible, } GetReferencedAccs().Insert(aAccessible); - Relation customActions(aAccessible->RelationByType(RelationType::ACTION)); - while (Accessible* target = customActions.Next()) { - // aria-action targets are excluded from name calculation, so consider any - // of these targets as "referenced" for our purposes. - GetReferencedAccs().Insert(target); + if (nsIContent* content = aAccessible->GetContent()) { + AssociatedElementsIterator iter(aAccessible->Document(), content, + nsGkAtoms::aria_actions); + while (Accessible* actionTarget = iter.Next()) { + // aria-action targets are excluded from name calculation, so consider any + // of these targets as "referenced" for our purposes. + GetReferencedAccs().Insert(actionTarget); + } } - if (HasNameRule(aAccessible, eNameFromSubtreeRule)) { - nsAutoString name; - AppendFromAccessibleChildren(aAccessible, &name); - name.CompressWhitespace(); - if (!nsCoreUtils::IsWhitespaceString(name)) aName = name; + if (GetRoleRule(aAccessible->Role()) == eNameFromSubtreeRule) { + // XXX: is it necessary to care the accessible is not a document? + if (aAccessible->IsContent()) { + nsAutoString name; + AppendFromAccessibleChildren(aAccessible, &name); + name.CompressWhitespace(); + if (!nsCoreUtils::IsWhitespaceString(name)) aName = name; + } } // Once the text alternative computation is complete (i.e., once we've @@ -97,48 +90,9 @@ nsresult nsTextEquivUtils::GetNameFromSubtree(const Accessible* aAccessible, return NS_OK; } -void nsTextEquivUtils::GetTextEquivFromAccIterable( - const Accessible* aAccessible, AccIterable* aIter, nsAString& aTextEquiv) { - if (GetReferencedAccs().Contains(aAccessible)) { - // We got here when trying to resolve a dependant label or description, - // early out. - return; - } - // Remember the initiating accessible so we know when we've returned to it. - if (GetReferencedAccs().IsEmpty()) { - sInitiatorAcc = aAccessible; - } - // This method doesn't allow self-referencing accessibles, so add the - // initiator to the referenced accs hash. - GetReferencedAccs().Insert(aAccessible); - - aTextEquiv.Truncate(); - - while (Accessible* acc = aIter->Next()) { - if (!aTextEquiv.IsEmpty()) aTextEquiv += ' '; - - if (GetReferencedAccs().Contains(acc)) { - continue; - } - GetReferencedAccs().Insert(acc); - - AppendFromAccessible(acc, &aTextEquiv); - } - - if (aAccessible == sInitiatorAcc) { - // This is the top-level initiator, clear the hash. - GetReferencedAccs().Clear(); - sInitiatorAcc = nullptr; - } else { - // This is not the top-level initiator, just remove the calling accessible. - GetReferencedAccs().Remove(aAccessible); - } -} - -bool nsTextEquivUtils::GetTextEquivFromIDRefs( +nsresult nsTextEquivUtils::GetTextEquivFromIDRefs( const LocalAccessible* aAccessible, nsAtom* aIDRefsAttr, nsAString& aTextEquiv) { - bool usedHiddenOrSelf = false; // If this is an aria-labelledby or aria-describedby traversal and we're // already in such a traversal, or if we've already consulted the given // accessible, early out. @@ -146,15 +100,13 @@ bool nsTextEquivUtils::GetTextEquivFromIDRefs( aIDRefsAttr == nsGkAtoms::aria_describedby; if ((sInAriaRelationTraversal && isAriaTraversal) || GetReferencedAccs().Contains(aAccessible)) { - return usedHiddenOrSelf; + return NS_OK; } aTextEquiv.Truncate(); nsIContent* content = aAccessible->GetContent(); - if (!content) { - return usedHiddenOrSelf; - } + if (!content) return NS_OK; nsIContent* refContent = nullptr; AssociatedElementsIterator iter(aAccessible->Document(), content, @@ -174,23 +126,23 @@ bool nsTextEquivUtils::GetTextEquivFromIDRefs( sInAriaRelationTraversal = false; } }); - usedHiddenOrSelf |= + nsresult rv = AppendTextEquivFromContent(aAccessible, refContent, &aTextEquiv); + NS_ENSURE_SUCCESS(rv, rv); } - return usedHiddenOrSelf; + return NS_OK; } -bool nsTextEquivUtils::AppendTextEquivFromContent( +nsresult nsTextEquivUtils::AppendTextEquivFromContent( const LocalAccessible* aInitiatorAcc, nsIContent* aContent, nsAString* aString) { // Prevent recursion which can cause infinite loops. LocalAccessible* accessible = aInitiatorAcc->Document()->GetAccessible(aContent); - bool usedHiddenOrSelf = aInitiatorAcc == accessible; if (GetReferencedAccs().Contains(aInitiatorAcc) || GetReferencedAccs().Contains(accessible)) { - return usedHiddenOrSelf; + return NS_OK; } // Remember the initiating accessible so we know when we've returned to it. @@ -199,14 +151,14 @@ bool nsTextEquivUtils::AppendTextEquivFromContent( } GetReferencedAccs().Insert(aInitiatorAcc); + nsresult rv = NS_ERROR_FAILURE; if (accessible) { - AppendFromAccessible(accessible, aString); + rv = AppendFromAccessible(accessible, aString); GetReferencedAccs().Insert(accessible); } else { // The given content is invisible or otherwise inaccessible, so use the DOM // subtree. - AppendFromDOMNode(aContent, aString); - usedHiddenOrSelf = true; + rv = AppendFromDOMNode(aContent, aString); } // Once the text alternative computation is complete (i.e., once we've @@ -216,8 +168,7 @@ bool nsTextEquivUtils::AppendTextEquivFromContent( GetReferencedAccs().Clear(); sInitiatorAcc = nullptr; } - - return usedHiddenOrSelf; + return rv; } nsresult nsTextEquivUtils::AppendTextEquivFromTextContent(nsIContent* aContent, @@ -317,24 +268,6 @@ nsresult nsTextEquivUtils::AppendFromAccessible(Accessible* aAccessible, } } } - } else if (aAccessible->IsRemote()) { - if (aAccessible->IsText()) { - // Leafs should have their text appended with no spacing. - nsAutoString name; - aAccessible->Name(name); - aString->Append(name); - return NS_OK; - } - if (RefPtr<nsAtom>(aAccessible->DisplayStyle()) == nsGkAtoms::block || - aAccessible->IsHTMLListItem() || aAccessible->IsTableRow() || - aAccessible->IsTableCell()) { - // Similar to local case above, we need to add spaces around block level - // accessibles. - isHTMLBlock = true; - if (!aString->IsEmpty()) { - aString->Append(char16_t(' ')); - } - } } bool isEmptyTextEquiv = true; @@ -384,7 +317,7 @@ nsresult nsTextEquivUtils::AppendFromAccessible(Accessible* aAccessible, nsresult nsTextEquivUtils::AppendFromValue(Accessible* aAccessible, nsAString* aString) { - if (!HasNameRule(aAccessible, eNameFromValueRule)) { + if (GetRoleRule(aAccessible->Role()) != eNameFromValueRule) { return NS_OK_NO_NAME_CLAUSE_HANDLED; } @@ -481,11 +414,11 @@ uint32_t nsTextEquivUtils::GetRoleRule(role aRole) { bool nsTextEquivUtils::ShouldIncludeInSubtreeCalculation( Accessible* aAccessible) { - if (HasNameRule(aAccessible, eNameFromSubtreeRule)) { + uint32_t nameRule = GetRoleRule(aAccessible->Role()); + if (nameRule == eNameFromSubtreeRule) { return true; } - - if (!HasNameRule(aAccessible, eNameFromSubtreeIfReqRule)) { + if (!(nameRule & eNameFromSubtreeIfReqRule)) { return false; } diff --git a/accessible/base/nsTextEquivUtils.h b/accessible/base/nsTextEquivUtils.h @@ -16,8 +16,7 @@ class nsIContent; namespace mozilla { namespace a11y { class LocalAccessible; -class AccIterable; -} // namespace a11y +} } // namespace mozilla /** @@ -52,7 +51,6 @@ class nsTextEquivUtils { public: typedef mozilla::a11y::LocalAccessible LocalAccessible; typedef mozilla::a11y::Accessible Accessible; - typedef mozilla::a11y::AccIterable AccIterable; /** * Determines if the accessible has a given name rule. @@ -61,7 +59,10 @@ class nsTextEquivUtils { * @param aRule [in] a given name rule * @return true if the accessible has the rule */ - static bool HasNameRule(const Accessible* aAccessible, ETextEquivRule aRule); + static inline bool HasNameRule(Accessible* aAccessible, + ETextEquivRule aRule) { + return (GetRoleRule(aAccessible->Role()) & aRule) == aRule; + } /** * Calculates the name from the given accessible's subtree, if allowed. @@ -69,7 +70,7 @@ class nsTextEquivUtils { * @param aAccessible [in] the given accessible * @param aName [out] accessible name */ - static nsresult GetNameFromSubtree(const Accessible* aAccessible, + static nsresult GetNameFromSubtree(const LocalAccessible* aAccessible, nsAString& aName); /** @@ -93,16 +94,10 @@ class nsTextEquivUtils { * @param aAccessible [in] the accessible text equivalent is computed for * @param aIDRefsAttr [in] IDRefs attribute on DOM node of the accessible * @param aTextEquiv [out] result text equivalent - * @return true if either hidden content was used to compute the text - * equivalent, or if the initiator accessible itself was used. */ - static bool GetTextEquivFromIDRefs(const LocalAccessible* aAccessible, - nsAtom* aIDRefsAttr, - nsAString& aTextEquiv); - - static void GetTextEquivFromAccIterable(const Accessible* aAccessible, - AccIterable* aIter, - nsAString& aTextEquiv); + static nsresult GetTextEquivFromIDRefs(const LocalAccessible* aAccessible, + nsAtom* aIDRefsAttr, + nsAString& aTextEquiv); /** * Calculates the text equivalent from the given content - and its subtree, if @@ -114,12 +109,10 @@ class nsTextEquivUtils { * @param aContent [in] the given content the text equivalent is * computed from * @param aString [in, out] the string - * @return true if either hidden content was used to compute the text - * equivalent, or if the initiator accessible itself was used. */ - static bool AppendTextEquivFromContent(const LocalAccessible* aInitiatorAcc, - nsIContent* aContent, - nsAString* aString); + static nsresult AppendTextEquivFromContent( + const LocalAccessible* aInitiatorAcc, nsIContent* aContent, + nsAString* aString); /** * Calculates the text equivalent from the given text content (may be text @@ -141,13 +134,6 @@ class nsTextEquivUtils { static nsresult AppendFromDOMChildren(nsIContent* aContent, nsAString* aString); - /** - * Calculates the text equivalent from the given accessible - and its subtree, - * if allowed. Then, appends the calculated text to the given string. - */ - static nsresult AppendFromAccessible(Accessible* aAccessible, - nsAString* aString); - private: /** * Iterates the given accessible's children and calculates the text equivalent @@ -157,6 +143,13 @@ class nsTextEquivUtils { nsAString* aString); /** + * Calculates the text equivalent from the given accessible - and its subtree, + * if allowed. Then, appends the calculated text to the given string. + */ + static nsresult AppendFromAccessible(Accessible* aAccessible, + nsAString* aString); + + /** * Calculates the text equivalent from the value of the given accessible. * Then, appends the calculated text to the given string. This function * implements the "Embedded Control" section of the AccName spec. diff --git a/accessible/generic/ApplicationAccessible.cpp b/accessible/generic/ApplicationAccessible.cpp @@ -31,7 +31,7 @@ ApplicationAccessible::ApplicationAccessible() //////////////////////////////////////////////////////////////////////////////// // nsIAccessible -ENameValueFlag ApplicationAccessible::DirectName(nsString& aName) const { +ENameValueFlag ApplicationAccessible::Name(nsString& aName) const { aName.Truncate(); nsCOMPtr<nsIStringBundleService> bundleService = diff --git a/accessible/generic/ApplicationAccessible.h b/accessible/generic/ApplicationAccessible.h @@ -37,7 +37,7 @@ class ApplicationAccessible : public AccessibleWrap { virtual nsRect BoundsInAppUnits() const override; virtual already_AddRefed<AccAttributes> NativeAttributes() override; virtual GroupPos GroupPosition() override; - virtual ENameValueFlag DirectName(nsString& aName) const override; + virtual ENameValueFlag Name(nsString& aName) const override; virtual void ApplyARIAState(uint64_t* aState) const override; virtual EDescriptionValueFlag Description( nsString& aDescription) const override; diff --git a/accessible/generic/DocAccessible.cpp b/accessible/generic/DocAccessible.cpp @@ -166,7 +166,7 @@ NS_IMPL_RELEASE_INHERITED(DocAccessible, HyperTextAccessible) //////////////////////////////////////////////////////////////////////////////// // nsIAccessible -ENameValueFlag DocAccessible::DirectName(nsString& aName) const { +ENameValueFlag DocAccessible::Name(nsString& aName) const { aName.Truncate(); if (mParent) { @@ -174,7 +174,7 @@ ENameValueFlag DocAccessible::DirectName(nsString& aName) const { } if (aName.IsEmpty()) { // Allow name via aria-labelledby or title attribute - LocalAccessible::DirectName(aName); + LocalAccessible::Name(aName); } if (aName.IsEmpty()) { Title(aName); // Try title element diff --git a/accessible/generic/DocAccessible.h b/accessible/generic/DocAccessible.h @@ -65,8 +65,7 @@ class DocAccessible : public HyperTextAccessible, virtual nsINode* GetNode() const override; Document* DocumentNode() const { return mDocumentNode; } - virtual mozilla::a11y::ENameValueFlag DirectName( - nsString& aName) const override; + virtual mozilla::a11y::ENameValueFlag Name(nsString& aName) const override; virtual EDescriptionValueFlag Description( nsString& aDescription) const override; virtual Accessible* FocusedChild() override; diff --git a/accessible/generic/LocalAccessible.cpp b/accessible/generic/LocalAccessible.cpp @@ -124,30 +124,38 @@ LocalAccessible::~LocalAccessible() { NS_ASSERTION(!mDoc, "LastRelease was never called!?!"); } -ENameValueFlag LocalAccessible::DirectName(nsString& aName) const { +ENameValueFlag LocalAccessible::Name(nsString& aName) const { + aName.Truncate(); + if (!HasOwnContent()) return eNameOK; ENameValueFlag nameFlag = ARIAName(aName); if (!aName.IsEmpty()) return nameFlag; nameFlag = NativeName(aName); - aName.CompressWhitespace(); - - return nameFlag; -} - -ENameValueFlag LocalAccessible::Name(nsString& aName) const { - aName.Truncate(); - - ENameValueFlag nameFlag = DirectName(aName); if (!aName.IsEmpty()) return nameFlag; - nsTextEquivUtils::GetNameFromSubtree(this, aName); - if (!aName.IsEmpty()) return eNameFromSubtree; - // In the end get the name from tooltip. - if (Tooltip(aName)) { - return eNameFromTooltip; + if (mContent->IsHTMLElement()) { + if (mContent->AsElement()->GetAttr(nsGkAtoms::title, aName)) { + aName.CompressWhitespace(); + return eNameFromTooltip; + } + } else if (mContent->IsXULElement()) { + if (mContent->AsElement()->GetAttr(nsGkAtoms::tooltiptext, aName)) { + aName.CompressWhitespace(); + return eNameFromTooltip; + } + } else if (mContent->IsSVGElement()) { + // If user agents need to choose among multiple 'desc' or 'title' + // elements for processing, the user agent shall choose the first one. + for (nsIContent* childElm = mContent->GetFirstChild(); childElm; + childElm = childElm->GetNextSibling()) { + if (childElm->IsSVGElement(nsGkAtoms::desc)) { + nsTextEquivUtils::AppendTextEquivFromContent(this, childElm, &aName); + return eNameFromTooltip; + } + } } if (auto cssAlt = CssAltContent(mContent)) { @@ -157,7 +165,7 @@ ENameValueFlag LocalAccessible::Name(nsString& aName) const { aName.SetIsVoid(true); - return eNameOK; + return nameFlag; } EDescriptionValueFlag LocalAccessible::Description( @@ -181,14 +189,28 @@ EDescriptionValueFlag LocalAccessible::Description( if (aDescription.IsEmpty()) { NativeDescription(aDescription); - aDescription.CompressWhitespace(); - } - if (aDescription.IsEmpty()) { - Tooltip(aDescription); + if (aDescription.IsEmpty()) { + // Keep the Name() method logic. + if (mContent->IsHTMLElement()) { + mContent->AsElement()->GetAttr(nsGkAtoms::title, aDescription); + } else if (mContent->IsXULElement()) { + mContent->AsElement()->GetAttr(nsGkAtoms::tooltiptext, aDescription); + } else if (mContent->IsSVGElement()) { + for (nsIContent* childElm = mContent->GetFirstChild(); childElm; + childElm = childElm->GetNextSibling()) { + if (childElm->IsSVGElement(nsGkAtoms::desc)) { + nsTextEquivUtils::AppendTextEquivFromContent(this, childElm, + &aDescription); + break; + } + } + } + } } if (!aDescription.IsEmpty()) { + aDescription.CompressWhitespace(); nsAutoString name; Name(name); // Don't expose a description if it is the same as the name. @@ -1540,9 +1562,13 @@ void LocalAccessible::DOMAttributeChanged(int32_t aNameSpaceID, if (aAttribute == nsGkAtoms::title) { nsAutoString name; - if (Name(name) == eNameFromTooltip || name.IsVoid()) { - mDoc->FireDelayedEvent(nsIAccessibleEvent::EVENT_NAME_CHANGE, this); - return; + ARIAName(name); + if (name.IsEmpty()) { + NativeName(name); + if (name.IsEmpty()) { + mDoc->FireDelayedEvent(nsIAccessibleEvent::EVENT_NAME_CHANGE, this); + return; + } } if (!elm->HasAttr(nsGkAtoms::aria_describedby)) { @@ -2596,12 +2622,14 @@ ENameValueFlag LocalAccessible::ARIAName(nsString& aName) const { return eNameOK; } // aria-labelledby now takes precedence over aria-label - bool notSimpleRelation = nsTextEquivUtils::GetTextEquivFromIDRefs( + nsresult rv = nsTextEquivUtils::GetTextEquivFromIDRefs( this, nsGkAtoms::aria_labelledby, aName); - aName.CompressWhitespace(); + if (NS_SUCCEEDED(rv)) { + aName.CompressWhitespace(); + } if (!aName.IsEmpty()) { - return notSimpleRelation ? eNameOK : eNameFromRelations; + return eNameFromRelations; } if (mContent->IsElement() && @@ -2616,9 +2644,11 @@ ENameValueFlag LocalAccessible::ARIAName(nsString& aName) const { // LocalAccessible protected bool LocalAccessible::ARIADescription(nsString& aDescription) const { // aria-describedby takes precedence over aria-description - nsTextEquivUtils::GetTextEquivFromIDRefs(this, nsGkAtoms::aria_describedby, - aDescription); - aDescription.CompressWhitespace(); + nsresult rv = nsTextEquivUtils::GetTextEquivFromIDRefs( + this, nsGkAtoms::aria_describedby, aDescription); + if (NS_SUCCEEDED(rv)) { + aDescription.CompressWhitespace(); + } if (aDescription.IsEmpty() && mContent->IsElement() && nsAccUtils::GetARIAAttr(mContent->AsElement(), @@ -2630,48 +2660,18 @@ bool LocalAccessible::ARIADescription(nsString& aDescription) const { } // LocalAccessible protected -bool LocalAccessible::Tooltip(nsString& aTooltip) const { - if (!HasOwnContent()) { - return false; - } - - if (mContent->IsHTMLElement()) { - mContent->AsElement()->GetAttr(nsGkAtoms::title, aTooltip); - aTooltip.CompressWhitespace(); - return !aTooltip.IsEmpty(); - } else if (mContent->IsXULElement()) { - mContent->AsElement()->GetAttr(nsGkAtoms::tooltiptext, aTooltip); - aTooltip.CompressWhitespace(); - return !aTooltip.IsEmpty(); - } else if (mContent->IsSVGElement()) { - // If user agents need to choose among multiple 'desc' or 'title' - // elements for processing, the user agent shall choose the first one. - for (nsIContent* childElm = mContent->GetFirstChild(); childElm; - childElm = childElm->GetNextSibling()) { - if (childElm->IsSVGElement(nsGkAtoms::desc)) { - nsTextEquivUtils::AppendTextEquivFromContent(this, childElm, &aTooltip); - aTooltip.CompressWhitespace(); - return !aTooltip.IsEmpty(); - } - } - } - return false; -} - -// LocalAccessible protected ENameValueFlag LocalAccessible::NativeName(nsString& aName) const { if (mContent->IsHTMLElement()) { LocalAccessible* label = nullptr; HTMLLabelIterator iter(Document(), this); - bool notSimpleRelation = false; while ((label = iter.Next())) { - notSimpleRelation |= nsTextEquivUtils::AppendTextEquivFromContent( - this, label->GetContent(), &aName); + nsTextEquivUtils::AppendTextEquivFromContent(this, label->GetContent(), + &aName); aName.CompressWhitespace(); } if (!aName.IsEmpty()) { - return notSimpleRelation ? eNameOK : eNameFromRelations; + return eNameFromRelations; } NameFromAssociatedXULLabel(mDoc, mContent, aName); @@ -2679,20 +2679,16 @@ ENameValueFlag LocalAccessible::NativeName(nsString& aName) const { return eNameOK; } - // We return eNameFromSubtree here to indicate that if there is no native - // name we will calculate the name from the subtree next. This is useful for - // noting where the name will come from in cases like name change - // notifications. - return eNameFromSubtree; + nsTextEquivUtils::GetNameFromSubtree(this, aName); + return aName.IsEmpty() ? eNameOK : eNameFromSubtree; } if (mContent->IsXULElement()) { XULElmName(mDoc, mContent, aName); if (!aName.IsEmpty()) return eNameOK; - // We return eNameFromSubtree here to indicate that if there is no native - // name we will calculate the name from the subtree next. See above. - return eNameFromSubtree; + nsTextEquivUtils::GetNameFromSubtree(this, aName); + return aName.IsEmpty() ? eNameOK : eNameFromSubtree; } if (mContent->IsSVGElement()) { @@ -3389,7 +3385,12 @@ already_AddRefed<AccAttributes> LocalAccessible::BundleFieldsForCache( // always their text. Text gets handled below. if (aCacheDomain & CacheDomain::NameAndDescription && !IsText()) { nsString name; - ENameValueFlag nameFlag = DirectName(name); + int32_t nameFlag = Name(name); + if (nameFlag != eNameOK) { + fields->SetAttribute(CacheKey::NameValueFlag, nameFlag); + } else if (IsUpdatePush(CacheDomain::NameAndDescription)) { + fields->SetAttribute(CacheKey::NameValueFlag, DeleteEntry()); + } if (IsTextField()) { MOZ_ASSERT(mContent); @@ -3403,27 +3404,12 @@ already_AddRefed<AccAttributes> LocalAccessible::BundleFieldsForCache( } } - if (nameFlag != eNameFromRelations && !name.IsEmpty()) { + if (!name.IsEmpty()) { fields->SetAttribute(CacheKey::Name, std::move(name)); } else if (IsUpdatePush(CacheDomain::NameAndDescription)) { fields->SetAttribute(CacheKey::Name, DeleteEntry()); } - nsString tooltip; - if (Tooltip(tooltip)) { - fields->SetAttribute(CacheKey::Tooltip, std::move(tooltip)); - } else if (IsUpdatePush(CacheDomain::NameAndDescription)) { - fields->SetAttribute(CacheKey::Tooltip, DeleteEntry()); - } - - nsString cssAltContent; - if (auto cssAlt = CssAltContent(mContent)) { - cssAlt.AppendToString(cssAltContent); - fields->SetAttribute(CacheKey::CssAltContent, std::move(cssAltContent)); - } else if (IsUpdatePush(CacheDomain::NameAndDescription)) { - fields->SetAttribute(CacheKey::CssAltContent, DeleteEntry()); - } - nsString description; int32_t descFlag = Description(description); if (!description.IsEmpty()) { diff --git a/accessible/generic/LocalAccessible.h b/accessible/generic/LocalAccessible.h @@ -155,9 +155,7 @@ class LocalAccessible : public nsISupports, public Accessible { /** * Get the name of this accessible. */ - virtual ENameValueFlag Name(nsString& aName) const override final; - - virtual ENameValueFlag DirectName(nsString& aName) const; + virtual ENameValueFlag Name(nsString& aName) const override; /** * Maps ARIA state attributes to state of accessible. Note the given state @@ -875,12 +873,6 @@ class LocalAccessible : public nsISupports, public Accessible { bool ARIADescription(nsString& aDescription) const; /** - * Returns the accessible "tooltip", usually derived from title attribute in - * HTML or tooltiptext in XUL. - */ - bool Tooltip(nsString& aTooltip) const; - - /** * Returns the accessible name specified for this control using XUL * <label control="id" ...>. */ diff --git a/accessible/generic/RootAccessible.cpp b/accessible/generic/RootAccessible.cpp @@ -64,11 +64,11 @@ RootAccessible::~RootAccessible() {} //////////////////////////////////////////////////////////////////////////////// // LocalAccessible -ENameValueFlag RootAccessible::DirectName(nsString& aName) const { +ENameValueFlag RootAccessible::Name(nsString& aName) const { aName.Truncate(); if (ARIARoleMap()) { - LocalAccessible::DirectName(aName); + LocalAccessible::Name(aName); if (!aName.IsEmpty()) return eNameOK; } diff --git a/accessible/generic/RootAccessible.h b/accessible/generic/RootAccessible.h @@ -35,8 +35,7 @@ class RootAccessible : public DocAccessibleWrap, public nsIDOMEventListener { // LocalAccessible virtual void Shutdown() override; - virtual mozilla::a11y::ENameValueFlag DirectName( - nsString& aName) const override; + virtual mozilla::a11y::ENameValueFlag Name(nsString& aName) const override; virtual Relation RelationByType(RelationType aType) const override; virtual uint64_t NativeState() const override; diff --git a/accessible/generic/TextLeafAccessible.cpp b/accessible/generic/TextLeafAccessible.cpp @@ -39,7 +39,7 @@ void TextLeafAccessible::AppendTextTo(nsAString& aText, uint32_t aStartOffset, aText.Append(Substring(mText, aStartOffset, aLength)); } -ENameValueFlag TextLeafAccessible::DirectName(nsString& aName) const { +ENameValueFlag TextLeafAccessible::Name(nsString& aName) const { // Text node, ARIA can't be used. aName = mText; return eNameOK; diff --git a/accessible/generic/TextLeafAccessible.h b/accessible/generic/TextLeafAccessible.h @@ -23,7 +23,7 @@ class TextLeafAccessible : public LinkableAccessible { virtual mozilla::a11y::role NativeRole() const override; virtual void AppendTextTo(nsAString& aText, uint32_t aStartOffset = 0, uint32_t aLength = UINT32_MAX) override; - virtual ENameValueFlag DirectName(nsString& aName) const override; + virtual ENameValueFlag Name(nsString& aName) const override; // TextLeafAccessible void SetText(const nsAString& aText) { mText = aText; } diff --git a/accessible/html/HTMLElementAccessibles.cpp b/accessible/html/HTMLElementAccessibles.cpp @@ -42,7 +42,8 @@ ENameValueFlag HTMLBRAccessible::NativeName(nsString& aName) const { //////////////////////////////////////////////////////////////////////////////// ENameValueFlag HTMLLabelAccessible::NativeName(nsString& aName) const { - return eNameOK; + nsTextEquivUtils::GetNameFromSubtree(this, aName); + return aName.IsEmpty() ? eNameOK : eNameFromSubtree; } Relation HTMLLabelAccessible::RelationByType(RelationType aType) const { diff --git a/accessible/html/HTMLFormControlAccessible.cpp b/accessible/html/HTMLFormControlAccessible.cpp @@ -331,8 +331,8 @@ already_AddRefed<AccAttributes> HTMLTextFieldAccessible::NativeAttributes() { return attributes.forget(); } -ENameValueFlag HTMLTextFieldAccessible::DirectName(nsString& aName) const { - ENameValueFlag nameFlag = LocalAccessible::DirectName(aName); +ENameValueFlag HTMLTextFieldAccessible::Name(nsString& aName) const { + ENameValueFlag nameFlag = LocalAccessible::Name(aName); if (!aName.IsEmpty()) return nameFlag; // text inputs and textareas might have useful placeholder text @@ -510,8 +510,8 @@ bool HTMLFileInputAccessible::IsAcceptableChild(nsIContent* aEl) const { return aEl->IsText(); } -ENameValueFlag HTMLFileInputAccessible::DirectName(nsString& aName) const { - ENameValueFlag flag = HyperTextAccessible::DirectName(aName); +ENameValueFlag HTMLFileInputAccessible::Name(nsString& aName) const { + ENameValueFlag flag = HyperTextAccessible::Name(aName); if (flag == eNameFromSubtree) { // The author didn't provide a name. We'll compute the name from our subtree // below. @@ -539,11 +539,7 @@ ENameValueFlag HTMLFileInputAccessible::DirectName(nsString& aName) const { } aName += leaf->Text(); } - - // XXX: Return eNameOK even if we got the name from a label or subtree. This - // is to force us to cache the name, since the calculation of this type is out - // of spec and pretty nuanced. - return eNameOK; + return flag; } bool HTMLFileInputAccessible::HasPrimaryAction() const { return true; } @@ -687,15 +683,11 @@ ENameValueFlag HTMLGroupboxAccessible::NativeName(nsString& aName) const { nsIContent* legendContent = GetLegend(); if (legendContent) { - bool usedHiddenContent = nsTextEquivUtils::AppendTextEquivFromContent( - this, legendContent, &aName); - aName.CompressWhitespace(); - if (!usedHiddenContent && !aName.IsEmpty()) { - return eNameFromRelations; - } + nsTextEquivUtils::AppendTextEquivFromContent(this, legendContent, &aName); } - return eNameOK; + aName.CompressWhitespace(); + return aName.IsEmpty() ? eNameOK : eNameFromRelations; } Relation HTMLGroupboxAccessible::RelationByType(RelationType aType) const { @@ -740,15 +732,11 @@ ENameValueFlag HTMLFigureAccessible::NativeName(nsString& aName) const { nsIContent* captionContent = Caption(); if (captionContent) { - bool usedHiddenContent = nsTextEquivUtils::AppendTextEquivFromContent( - this, captionContent, &aName); - aName.CompressWhitespace(); - if (!usedHiddenContent && !aName.IsEmpty()) { - return eNameFromRelations; - } + nsTextEquivUtils::AppendTextEquivFromContent(this, captionContent, &aName); } - return eNameOK; + aName.CompressWhitespace(); + return aName.IsEmpty() ? eNameOK : eNameFromRelations; } Relation HTMLFigureAccessible::RelationByType(RelationType aType) const { diff --git a/accessible/html/HTMLFormControlAccessible.h b/accessible/html/HTMLFormControlAccessible.h @@ -118,7 +118,7 @@ class HTMLTextFieldAccessible : public HyperTextAccessible { virtual ~HTMLTextFieldAccessible() {} // LocalAccessible - virtual ENameValueFlag DirectName(nsString& aName) const override; + virtual ENameValueFlag Name(nsString& aName) const override; virtual void DOMAttributeChanged(int32_t aNameSpaceID, nsAtom* aAttribute, AttrModType aModType, @@ -136,7 +136,7 @@ class HTMLFileInputAccessible : public HyperTextAccessible { // LocalAccessible virtual mozilla::a11y::role NativeRole() const override; virtual bool IsAcceptableChild(nsIContent* aEl) const override; - virtual ENameValueFlag DirectName(nsString& aName) const override; + virtual ENameValueFlag Name(nsString& aName) const override; virtual bool HasPrimaryAction() const override; virtual void ActionNameAt(uint8_t aIndex, nsAString& aName) override; virtual bool IsWidget() const override; diff --git a/accessible/html/HTMLListAccessible.cpp b/accessible/html/HTMLListAccessible.cpp @@ -85,7 +85,7 @@ HTMLListBulletAccessible::HTMLListBulletAccessible(nsIContent* aContent, //////////////////////////////////////////////////////////////////////////////// // HTMLListBulletAccessible: LocalAccessible -ENameValueFlag HTMLListBulletAccessible::DirectName(nsString& aName) const { +ENameValueFlag HTMLListBulletAccessible::Name(nsString& aName) const { nsLayoutUtils::GetMarkerSpokenText(mContent, aName); return eNameOK; } diff --git a/accessible/html/HTMLListAccessible.h b/accessible/html/HTMLListAccessible.h @@ -67,7 +67,7 @@ class HTMLListBulletAccessible : public LeafAccessible { virtual ~HTMLListBulletAccessible() {} // LocalAccessible - virtual ENameValueFlag DirectName(nsString& aName) const override; + virtual ENameValueFlag Name(nsString& aName) const override; virtual a11y::role NativeRole() const override; virtual uint64_t NativeState() const override; virtual already_AddRefed<AccAttributes> NativeAttributes() override; diff --git a/accessible/html/HTMLTableAccessible.cpp b/accessible/html/HTMLTableAccessible.cpp @@ -283,6 +283,21 @@ role HTMLTableHeaderCellAccessible::NativeRole() const { } //////////////////////////////////////////////////////////////////////////////// +// HTMLTableRowAccessible +//////////////////////////////////////////////////////////////////////////////// + +// LocalAccessible protected +ENameValueFlag HTMLTableRowAccessible::NativeName(nsString& aName) const { + // For table row accessibles, we only want to calculate the name from the + // sub tree if an ARIA role is present. + if (HasStrongARIARole()) { + return AccessibleWrap::NativeName(aName); + } + + return eNameOK; +} + +//////////////////////////////////////////////////////////////////////////////// // HTMLTableAccessible //////////////////////////////////////////////////////////////////////////////// @@ -314,11 +329,10 @@ ENameValueFlag HTMLTableAccessible::NativeName(nsString& aName) const { if (caption) { nsIContent* captionContent = caption->GetContent(); if (captionContent) { - bool usedHiddenContent = nsTextEquivUtils::AppendTextEquivFromContent( - this, captionContent, &aName); - aName.CompressWhitespace(); + nsTextEquivUtils::AppendTextEquivFromContent(this, captionContent, + &aName); if (!aName.IsEmpty()) { - return usedHiddenContent ? eNameOK : eNameFromRelations; + return eNameFromRelations; } } } diff --git a/accessible/html/HTMLTableAccessible.h b/accessible/html/HTMLTableAccessible.h @@ -84,6 +84,9 @@ class HTMLTableRowAccessible : public HyperTextAccessible { protected: virtual ~HTMLTableRowAccessible() {} + + // LocalAccessible + virtual ENameValueFlag NativeName(nsString& aName) const override; }; /** diff --git a/accessible/ipc/RemoteAccessible.cpp b/accessible/ipc/RemoteAccessible.cpp @@ -226,79 +226,31 @@ void RemoteAccessible::ApplyCache(CacheUpdateType aUpdateType, ENameValueFlag RemoteAccessible::Name(nsString& aName) const { if (RequestDomainsIfInactive(CacheDomain::NameAndDescription | - CacheDomain::Text | CacheDomain::Relations) || - !mCachedFields) { + CacheDomain::Text)) { aName.SetIsVoid(true); return eNameOK; } - if (IsText()) { - mCachedFields->GetAttribute(CacheKey::Text, aName); - return eNameOK; - } - - if (mCachedFields->GetAttribute(CacheKey::Name, aName)) { - VERIFY_CACHE(CacheDomain::NameAndDescription); - return eNameOK; - } - - if (auto maybeAriaLabelIds = mCachedFields->GetAttribute<nsTArray<uint64_t>>( - nsGkAtoms::aria_labelledby)) { - RemoteAccIterator iter(*maybeAriaLabelIds, Document()); - nsTextEquivUtils::GetTextEquivFromAccIterable(this, &iter, aName); - aName.CompressWhitespace(); - } - - if (!aName.IsEmpty()) { - return eNameFromRelations; - } - - if (auto accRelMapEntry = mDoc->mReverseRelations.Lookup(ID())) { - nsTArray<uint64_t> relationCandidateIds; - for (const auto& data : kRelationTypeAtoms) { - if (data.mAtom != nsGkAtoms::_for || data.mValidTag != nsGkAtoms::label) { - continue; - } - - if (auto labelIds = accRelMapEntry.Data().Lookup(&data)) { - RemoteAccIterator iter(*labelIds, Document()); - nsTextEquivUtils::GetTextEquivFromAccIterable(this, &iter, aName); - aName.CompressWhitespace(); - } + ENameValueFlag nameFlag = eNameOK; + if (mCachedFields) { + if (IsText()) { + mCachedFields->GetAttribute(CacheKey::Text, aName); + return eNameOK; + } + auto cachedNameFlag = + mCachedFields->GetAttribute<int32_t>(CacheKey::NameValueFlag); + if (cachedNameFlag) { + nameFlag = static_cast<ENameValueFlag>(*cachedNameFlag); + } + if (mCachedFields->GetAttribute(CacheKey::Name, aName)) { + VERIFY_CACHE(CacheDomain::NameAndDescription); + return nameFlag; } - aName.CompressWhitespace(); - } - - if (!aName.IsEmpty()) { - return eNameFromRelations; - } - - ArrayAccIterator iter(LegendsOrCaptions()); - nsTextEquivUtils::GetTextEquivFromAccIterable(this, &iter, aName); - aName.CompressWhitespace(); - - if (!aName.IsEmpty()) { - return eNameFromRelations; - } - - nsTextEquivUtils::GetNameFromSubtree(this, aName); - if (!aName.IsEmpty()) { - return eNameFromSubtree; - } - - if (mCachedFields->GetAttribute(CacheKey::Tooltip, aName)) { - VERIFY_CACHE(CacheDomain::NameAndDescription); - return eNameFromTooltip; - } - - if (mCachedFields->GetAttribute(CacheKey::CssAltContent, aName)) { - VERIFY_CACHE(CacheDomain::NameAndDescription); - return eNameOK; } MOZ_ASSERT(aName.IsEmpty()); aName.SetIsVoid(true); - return eNameOK; + return nameFlag; } EDescriptionValueFlag RemoteAccessible::Description( @@ -1327,7 +1279,9 @@ Relation RemoteAccessible::RelationByType(RelationType aType) const { // both aria-labelledby and a <figcaption> must return two LABELLED_BY // targets: the aria-labelledby and then the <figcaption>. if (aType == RelationType::LABELLED_BY) { - rel.AppendIter(new ArrayAccIterator(LegendsOrCaptions())); + for (RemoteAccessible* label : LegendsOrCaptions()) { + rel.AppendTarget(label); + } } else if (aType == RelationType::LABEL_FOR) { if (RemoteAccessible* labelTarget = LegendOrCaptionFor()) { rel.AppendTarget(labelTarget); @@ -1337,12 +1291,12 @@ Relation RemoteAccessible::RelationByType(RelationType aType) const { return rel; } -nsTArray<Accessible*> RemoteAccessible::LegendsOrCaptions() const { - nsTArray<Accessible*> children; +nsTArray<RemoteAccessible*> RemoteAccessible::LegendsOrCaptions() const { + nsTArray<RemoteAccessible*> children; auto AddChildWithTag = [this, &children](nsAtom* aTarget) { uint32_t count = ChildCount(); for (uint32_t c = 0; c < count; ++c) { - Accessible* child = ChildAt(c); + RemoteAccessible* child = RemoteChildAt(c); MOZ_ASSERT(child); if (child->TagName() == aTarget) { children.AppendElement(child); diff --git a/accessible/ipc/RemoteAccessible.h b/accessible/ipc/RemoteAccessible.h @@ -181,7 +181,7 @@ class RemoteAccessible : public Accessible, public HyperTextAccessibleBase { // Methods that potentially access a cache. - virtual ENameValueFlag Name(nsString& aName) const override final; + virtual ENameValueFlag Name(nsString& aName) const override; virtual EDescriptionValueFlag Description( nsString& aDescription) const override; virtual void Value(nsString& aValue) const override; @@ -500,7 +500,7 @@ class RemoteAccessible : public Accessible, public HyperTextAccessibleBase { virtual nsTArray<int32_t>& GetCachedHyperTextOffsets() override; - nsTArray<Accessible*> LegendsOrCaptions() const; + nsTArray<RemoteAccessible*> LegendsOrCaptions() const; RemoteAccessible* LegendOrCaptionFor() const; diff --git a/accessible/mac/mozAccessible.mm b/accessible/mac/mozAccessible.mm @@ -493,7 +493,6 @@ static bool ProvidesTitle(const Accessible* aAccessible, nsString& aName) { switch (aAccessible->Role()) { case roles::PAGETAB: case roles::COMBOBOX_OPTION: - case roles::OPTION: case roles::PARENT_MENUITEM: case roles::MENUITEM: // These roles always supply a title. @@ -1131,8 +1130,6 @@ static bool ProvidesTitle(const Accessible* aAccessible, nsString& aName) { mIsLiveRegion = false; break; case nsIAccessibleEvent::EVENT_NAME_CHANGE: { - // Don't want to passively activate the cache because a name changed. - CacheDomainActivationBlocker cacheBlocker; nsAutoString nameNotUsed; if (ProvidesTitle(mGeckoAccessible, nameNotUsed)) { [self moxPostNotification:NSAccessibilityTitleChangedNotification]; diff --git a/accessible/tests/browser/caching_granularity/browser_name_and_description_domain.js b/accessible/tests/browser/caching_granularity/browser_name_and_description_domain.js @@ -55,10 +55,10 @@ addAccessibleTask( // CacheKey::NameValueFlag, CacheDomain::NameAndDescription addAccessibleTask( - `<h3 id="test" aria-label="test me"><p>test</p></h3>`, + `<h3 id="test"><p>test</p></h3>`, async function (browser, docAcc) { let acc = findAccessibleChildByID(docAcc, "test"); - verifyAttributeCachedNoRetry(acc, "name"); + verifyAttributeCachedNoRetry(acc, "explicit-name"); }, { topLevel: true, diff --git a/accessible/tests/browser/name_and_description/browser_name_general.js b/accessible/tests/browser/name_and_description/browser_name_general.js @@ -225,38 +225,31 @@ addAccessibleTask( </label> `, async function testARIACoreExamples(browser, docAcc) { - function testName_(id, expected, cached) { + function testName_(id, expected) { const acc = findAccessibleChildByID(docAcc, id); - if (browser.isRemoteBrowser) { - is( - acc.cache.has("name"), - cached, - `Name should ${cached ? "" : "not "}be in cache for '${id}'` - ); - } testName(acc, expected); } // Example 1 from section 4.3.1 under 2.B. // Element1 should get its name from the text in element3. // Element2 should not get its name from element1 because that already // gets its name from another element. - testName_("el1", "hello", false); - testName_("el2", null, false); + testName_("el1", "hello"); + testName_("el2", null); // Example 2 from section 4.3.1 under 2.C. // The buttons should get their name from their labels and the links. - testName_("del_row1", "Delete Documentation.pdf", true); - testName_("del_row2", "Delete HolidayLetter.pdf", true); + testName_("del_row1", "Delete Documentation.pdf"); + testName_("del_row2", "Delete HolidayLetter.pdf"); // Example 3 from section 4.3.1 under 2.F. // Name should be own content text plus the value of the input plus // more own inner text, separated by 1 space. - testName_("chkbx", "Flash the screen 5 times", false); + testName_("chkbx", "Flash the screen 5 times"); // Example 4 from section 4.3.1 under 2.F. // Name from content should include all the child nodes, including // table cells. - testName_("input_with_html_label", "foo bar baz", false); + testName_("input_with_html_label", "foo bar baz"); }, { topLevel: true, chrome: true } ); diff --git a/accessible/tests/mochitest/name/markuprules.xml b/accessible/tests/mochitest/name/markuprules.xml @@ -141,8 +141,8 @@ <ruleset id="HTMLInputImageNoValidSrc" defaultName="Submit Query"> <ruleset ref="HTMLControl:Head"/> - <rule attr="alt" type="string"/> - <rule attr="value" type="string"/> + <rule attr="alt" type="string" explicit-name="false"/> + <rule attr="value" type="string" explicit-name="false"/> </ruleset> <ruleset id="HTMLOption"> diff --git a/accessible/xul/XULAlertAccessible.cpp b/accessible/xul/XULAlertAccessible.cpp @@ -29,7 +29,7 @@ uint64_t XULAlertAccessible::NativeState() const { return LocalAccessible::NativeState() | states::ALERT; } -ENameValueFlag XULAlertAccessible::DirectName(nsString& aName) const { +ENameValueFlag XULAlertAccessible::Name(nsString& aName) const { // Screen readers need to read contents of alert, not the accessible name. // If we have both some screen readers will read the alert twice. aName.Truncate(); diff --git a/accessible/xul/XULAlertAccessible.h b/accessible/xul/XULAlertAccessible.h @@ -22,8 +22,7 @@ class XULAlertAccessible : public AccessibleWrap { NS_INLINE_DECL_REFCOUNTING_INHERITED(XULAlertAccessible, AccessibleWrap) // LocalAccessible - virtual mozilla::a11y::ENameValueFlag DirectName( - nsString& aName) const override; + virtual mozilla::a11y::ENameValueFlag Name(nsString& aName) const override; virtual a11y::role NativeRole() const override; virtual uint64_t NativeState() const override; diff --git a/accessible/xul/XULElementAccessibles.cpp b/accessible/xul/XULElementAccessibles.cpp @@ -146,7 +146,10 @@ void XULLinkAccessible::Value(nsString& aValue) const { ENameValueFlag XULLinkAccessible::NativeName(nsString& aName) const { mContent->AsElement()->GetAttr(nsGkAtoms::value, aName); - return eNameOK; + if (!aName.IsEmpty()) return eNameOK; + + nsTextEquivUtils::GetNameFromSubtree(this, aName); + return aName.IsEmpty() ? eNameOK : eNameFromSubtree; } role XULLinkAccessible::NativeRole() const { return roles::LINK; } diff --git a/accessible/xul/XULMenuAccessible.cpp b/accessible/xul/XULMenuAccessible.cpp @@ -130,8 +130,8 @@ ENameValueFlag XULMenuitemAccessible::NativeName(nsString& aName) const { return eNameOK; } -ENameValueFlag XULMenuitemAccessible::DirectName(nsString& aName) const { - ENameValueFlag flag = AccessibleWrap::DirectName(aName); +ENameValueFlag XULMenuitemAccessible::Name(nsString& aName) const { + ENameValueFlag flag = AccessibleWrap::Name(aName); if (!aName.IsEmpty()) { // We can't handle this in NativeName() because some menuitems use // aria-label rather than label, and aria-label is returned by diff --git a/accessible/xul/XULMenuAccessible.h b/accessible/xul/XULMenuAccessible.h @@ -22,7 +22,7 @@ class XULMenuitemAccessible : public AccessibleWrap { XULMenuitemAccessible(nsIContent* aContent, DocAccessible* aDoc); // LocalAccessible - virtual ENameValueFlag DirectName(nsString& aName) const override; + virtual ENameValueFlag Name(nsString& aName) const override; virtual EDescriptionValueFlag Description( nsString& aDescription) const override; virtual a11y::role NativeRole() const override; diff --git a/accessible/xul/XULTreeAccessible.cpp b/accessible/xul/XULTreeAccessible.cpp @@ -924,7 +924,7 @@ NS_IMPL_RELEASE_INHERITED(XULTreeItemAccessible, XULTreeItemAccessibleBase) //////////////////////////////////////////////////////////////////////////////// // XULTreeItemAccessible: nsIAccessible implementation -ENameValueFlag XULTreeItemAccessible::DirectName(nsString& aName) const { +ENameValueFlag XULTreeItemAccessible::Name(nsString& aName) const { aName.Truncate(); GetCellName(mColumn, aName); diff --git a/accessible/xul/XULTreeAccessible.h b/accessible/xul/XULTreeAccessible.h @@ -223,7 +223,7 @@ class XULTreeItemAccessible : public XULTreeItemAccessibleBase { // LocalAccessible virtual void Shutdown() override; - virtual ENameValueFlag DirectName(nsString& aName) const override; + virtual ENameValueFlag Name(nsString& aName) const override; virtual a11y::role NativeRole() const override; // XULTreeItemAccessibleBase diff --git a/accessible/xul/XULTreeGridAccessible.cpp b/accessible/xul/XULTreeGridAccessible.cpp @@ -251,7 +251,7 @@ void XULTreeGridRowAccessible::Shutdown() { role XULTreeGridRowAccessible::NativeRole() const { return roles::ROW; } -ENameValueFlag XULTreeGridRowAccessible::DirectName(nsString& aName) const { +ENameValueFlag XULTreeGridRowAccessible::Name(nsString& aName) const { aName.Truncate(); // XXX: the row name sholdn't be a concatenation of cell names (bug 664384). @@ -400,7 +400,7 @@ void XULTreeGridCellAccessible::Shutdown() { Accessible* XULTreeGridCellAccessible::FocusedChild() { return nullptr; } -ENameValueFlag XULTreeGridCellAccessible::DirectName(nsString& aName) const { +ENameValueFlag XULTreeGridCellAccessible::Name(nsString& aName) const { aName.Truncate(); if (!mTreeView) return eNameOK; diff --git a/accessible/xul/XULTreeGridAccessible.h b/accessible/xul/XULTreeGridAccessible.h @@ -87,7 +87,7 @@ class XULTreeGridRowAccessible final : public XULTreeItemAccessibleBase { // LocalAccessible virtual void Shutdown() override; virtual a11y::role NativeRole() const override; - virtual ENameValueFlag DirectName(nsString& aName) const override; + virtual ENameValueFlag Name(nsString& aName) const override; virtual LocalAccessible* LocalChildAtPoint( int32_t aX, int32_t aY, EWhichChildAtPoint aWhichChild) override; @@ -131,7 +131,7 @@ class XULTreeGridCellAccessible : public LeafAccessible, virtual TableCellAccessible* AsTableCell() override { return this; } virtual nsRect BoundsInAppUnits() const override; virtual nsIntRect BoundsInCSSPixels() const override; - virtual ENameValueFlag DirectName(nsString& aName) const override; + virtual ENameValueFlag Name(nsString& aName) const override; virtual Accessible* FocusedChild() override; virtual already_AddRefed<AccAttributes> NativeAttributes() override; virtual int32_t IndexInParent() const override;