diff --git a/accessible/base/nsTextEquivUtils.cpp b/accessible/base/nsTextEquivUtils.cpp index 65211b93833a..e693bb349f49 100644 --- a/accessible/base/nsTextEquivUtils.cpp +++ b/accessible/base/nsTextEquivUtils.cpp @@ -7,6 +7,7 @@ #include "nsTextEquivUtils.h" +#include "LocalAccessible.h" #include "LocalAccessible-inl.h" #include "AccIterator.h" #include "nsCoreUtils.h" @@ -21,7 +22,7 @@ using namespace mozilla::a11y; * for bailing out during recursive text computation, or for special cases * like step f. of the ARIA implementation guide. */ -static const LocalAccessible* sInitiatorAcc = nullptr; +static const Accessible* sInitiatorAcc = nullptr; //////////////////////////////////////////////////////////////////////////////// // nsTextEquivUtils. Public. @@ -88,7 +89,7 @@ nsresult nsTextEquivUtils::AppendTextEquivFromContent( if (isVisible) { LocalAccessible* accessible = - sInitiatorAcc->Document()->GetAccessible(aContent); + aInitiatorAcc->Document()->GetAccessible(aContent); if (accessible) { rv = AppendFromAccessible(accessible, aString); goThroughDOMSubtree = false; @@ -167,12 +168,12 @@ nsresult nsTextEquivUtils::AppendFromDOMChildren(nsIContent* aContent, // nsTextEquivUtils. Private. nsresult nsTextEquivUtils::AppendFromAccessibleChildren( - const LocalAccessible* aAccessible, nsAString* aString) { + const Accessible* aAccessible, nsAString* aString) { nsresult rv = NS_OK_NO_NAME_CLAUSE_HANDLED; uint32_t childCount = aAccessible->ChildCount(); for (uint32_t childIdx = 0; childIdx < childCount; childIdx++) { - LocalAccessible* child = aAccessible->LocalChildAt(childIdx); + Accessible* child = aAccessible->ChildAt(childIdx); rv = AppendFromAccessible(child, aString); NS_ENSURE_SUCCESS(rv, rv); } @@ -180,12 +181,12 @@ nsresult nsTextEquivUtils::AppendFromAccessibleChildren( return rv; } -nsresult nsTextEquivUtils::AppendFromAccessible(LocalAccessible* aAccessible, +nsresult nsTextEquivUtils::AppendFromAccessible(Accessible* aAccessible, nsAString* aString) { // XXX: is it necessary to care the accessible is not a document? - if (aAccessible->IsContent()) { - nsresult rv = - AppendTextEquivFromTextContent(aAccessible->GetContent(), aString); + if (aAccessible->IsLocal() && aAccessible->AsLocal()->IsContent()) { + nsresult rv = AppendTextEquivFromTextContent( + aAccessible->AsLocal()->GetContent(), aString); if (rv != NS_OK_NO_NAME_CLAUSE_HANDLED) return rv; } @@ -225,7 +226,7 @@ nsresult nsTextEquivUtils::AppendFromAccessible(LocalAccessible* aAccessible, return rv; } -nsresult nsTextEquivUtils::AppendFromValue(LocalAccessible* aAccessible, +nsresult nsTextEquivUtils::AppendFromValue(Accessible* aAccessible, nsAString* aString) { if (GetRoleRule(aAccessible->Role()) != eNameFromValueRule) { return NS_OK_NO_NAME_CLAUSE_HANDLED; @@ -246,24 +247,18 @@ nsresult nsTextEquivUtils::AppendFromValue(LocalAccessible* aAccessible, // XXX: is it necessary to care the accessible is not a document? if (aAccessible->IsDoc()) return NS_ERROR_UNEXPECTED; - nsIContent* content = aAccessible->GetContent(); - - for (nsIContent* childContent = content->GetPreviousSibling(); childContent; - childContent = childContent->GetPreviousSibling()) { - // check for preceding text... - if (!childContent->TextIsOnlyWhitespace()) { - for (nsIContent* siblingContent = content->GetNextSibling(); - siblingContent; siblingContent = siblingContent->GetNextSibling()) { - // .. and subsequent text - if (!siblingContent->TextIsOnlyWhitespace()) { + for (Accessible* next = aAccessible->NextSibling(); next; + next = next->NextSibling()) { + if (!IsWhitespaceLeaf(next)) { + for (Accessible* prev = aAccessible->PrevSibling(); prev; + prev = prev->PrevSibling()) { + if (!IsWhitespaceLeaf(prev)) { aAccessible->Value(text); return AppendString(aString, text) ? NS_OK : NS_OK_NO_NAME_CLAUSE_HANDLED; - break; } } - break; } } @@ -332,7 +327,7 @@ uint32_t nsTextEquivUtils::GetRoleRule(role aRole) { } bool nsTextEquivUtils::ShouldIncludeInSubtreeCalculation( - LocalAccessible* aAccessible) { + Accessible* aAccessible) { uint32_t nameRule = GetRoleRule(aAccessible->Role()); if (nameRule == eNameFromSubtreeRule) { return true; @@ -360,3 +355,13 @@ bool nsTextEquivUtils::ShouldIncludeInSubtreeCalculation( return true; } + +bool nsTextEquivUtils::IsWhitespaceLeaf(Accessible* aAccessible) { + if (!aAccessible || !aAccessible->IsTextLeaf()) { + return false; + } + + nsAutoString name; + aAccessible->Name(name); + return nsCoreUtils::IsWhitespaceString(name); +} diff --git a/accessible/base/nsTextEquivUtils.h b/accessible/base/nsTextEquivUtils.h index c3880637f556..90f8a56a541b 100644 --- a/accessible/base/nsTextEquivUtils.h +++ b/accessible/base/nsTextEquivUtils.h @@ -8,11 +8,17 @@ #ifndef _nsTextEquivUtils_H_ #define _nsTextEquivUtils_H_ -#include "LocalAccessible.h" +#include "mozilla/a11y/Accessible.h" #include "Role.h" class nsIContent; +namespace mozilla { +namespace a11y { +class LocalAccessible; +} +} // namespace mozilla + /** * Text equivalent computation rules (see nsTextEquivUtils::gRoleToNameRulesMap) */ @@ -40,6 +46,7 @@ enum ETextEquivRule { class nsTextEquivUtils { public: typedef mozilla::a11y::LocalAccessible LocalAccessible; + typedef mozilla::a11y::Accessible Accessible; /** * Determines if the accessible has a given name rule. @@ -48,7 +55,7 @@ class nsTextEquivUtils { * @param aRule [in] a given name rule * @return true if the accessible has the rule */ - static inline bool HasNameRule(LocalAccessible* aAccessible, + static inline bool HasNameRule(Accessible* aAccessible, ETextEquivRule aRule) { return (GetRoleRule(aAccessible->Role()) & aRule) == aRule; } @@ -66,7 +73,7 @@ class nsTextEquivUtils { * Calculates text equivalent from the subtree. Similar to GetNameFromSubtree. * However it returns not empty result for things like HTML p. */ - static void GetTextEquivFromSubtree(const LocalAccessible* aAccessible, + static void GetTextEquivFromSubtree(const Accessible* aAccessible, nsString& aTextEquiv) { aTextEquiv.Truncate(); @@ -126,21 +133,20 @@ class nsTextEquivUtils { * Iterates accessible children and calculates text equivalent from each * child. */ - static nsresult AppendFromAccessibleChildren( - const LocalAccessible* aAccessible, nsAString* aString); + static nsresult AppendFromAccessibleChildren(const Accessible* aAccessible, + nsAString* aString); /** * Calculates text equivalent from the given accessible and its subtree if * allowed. */ - static nsresult AppendFromAccessible(LocalAccessible* aAccessible, + static nsresult AppendFromAccessible(Accessible* aAccessible, nsAString* aString); /** * Calculates text equivalent from the value of given accessible. */ - static nsresult AppendFromValue(LocalAccessible* aAccessible, - nsAString* aString); + static nsresult AppendFromValue(Accessible* aAccessible, nsAString* aString); /** * Calculates text equivalent from the given DOM node and its subtree if @@ -164,7 +170,13 @@ class nsTextEquivUtils { * Returns true if a given accessible should be included when calculating * the text equivalent for the initiator's subtree. */ - static bool ShouldIncludeInSubtreeCalculation(LocalAccessible* aAccessible); + static bool ShouldIncludeInSubtreeCalculation(Accessible* aAccessible); + + /** + * Returns true if a given accessible is a text leaf containing only + * whitespace. + */ + static bool IsWhitespaceLeaf(Accessible* aAccessible); }; #endif