From 26a029d407be480d791972afb5975cf62c9360a6 Mon Sep 17 00:00:00 2001 From: Daniel Baumann Date: Fri, 19 Apr 2024 02:47:55 +0200 Subject: Adding upstream version 124.0.1. Signed-off-by: Daniel Baumann --- accessible/generic/LocalAccessible.cpp | 4255 ++++++++++++++++++++++++++++++++ 1 file changed, 4255 insertions(+) create mode 100644 accessible/generic/LocalAccessible.cpp (limited to 'accessible/generic/LocalAccessible.cpp') diff --git a/accessible/generic/LocalAccessible.cpp b/accessible/generic/LocalAccessible.cpp new file mode 100644 index 0000000000..f02f68faa6 --- /dev/null +++ b/accessible/generic/LocalAccessible.cpp @@ -0,0 +1,4255 @@ +/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ +/* This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ + +#include "AccEvent.h" +#include "LocalAccessible-inl.h" + +#include "EmbeddedObjCollector.h" +#include "AccGroupInfo.h" +#include "AccIterator.h" +#include "CachedTableAccessible.h" +#include "DocAccessible-inl.h" +#include "mozilla/a11y/AccAttributes.h" +#include "mozilla/a11y/DocAccessibleChild.h" +#include "mozilla/a11y/Platform.h" +#include "nsAccUtils.h" +#include "nsAccessibilityService.h" +#include "ApplicationAccessible.h" +#include "nsGenericHTMLElement.h" +#include "NotificationController.h" +#include "nsEventShell.h" +#include "nsTextEquivUtils.h" +#include "EventTree.h" +#include "OuterDocAccessible.h" +#include "Pivot.h" +#include "Relation.h" +#include "mozilla/a11y/Role.h" +#include "RootAccessible.h" +#include "States.h" +#include "TextLeafRange.h" +#include "TextRange.h" +#include "HTMLElementAccessibles.h" +#include "HTMLSelectAccessible.h" +#include "HTMLTableAccessible.h" +#include "ImageAccessible.h" + +#include "nsComputedDOMStyle.h" +#include "nsGkAtoms.h" +#include "nsIDOMXULButtonElement.h" +#include "nsIDOMXULSelectCntrlEl.h" +#include "nsIDOMXULSelectCntrlItemEl.h" +#include "nsINodeList.h" + +#include "mozilla/dom/Document.h" +#include "mozilla/dom/HTMLFormElement.h" +#include "mozilla/dom/HTMLAnchorElement.h" +#include "mozilla/gfx/Matrix.h" +#include "nsIContent.h" +#include "nsIFormControl.h" + +#include "nsDisplayList.h" +#include "nsLayoutUtils.h" +#include "nsPresContext.h" +#include "nsIFrame.h" +#include "nsTextFrame.h" +#include "nsView.h" +#include "nsIDocShellTreeItem.h" +#include "nsIScrollableFrame.h" +#include "nsStyleStructInlines.h" +#include "nsFocusManager.h" + +#include "nsString.h" +#include "nsAtom.h" +#include "nsContainerFrame.h" + +#include "mozilla/Assertions.h" +#include "mozilla/BasicEvents.h" +#include "mozilla/ErrorResult.h" +#include "mozilla/FloatingPoint.h" +#include "mozilla/PresShell.h" +#include "mozilla/ProfilerMarkers.h" +#include "mozilla/StaticPrefs_ui.h" +#include "mozilla/dom/Element.h" +#include "mozilla/dom/HTMLLabelElement.h" +#include "mozilla/dom/KeyboardEventBinding.h" +#include "mozilla/dom/TreeWalker.h" +#include "mozilla/dom/UserActivation.h" +#include "mozilla/dom/MutationEventBinding.h" + +using namespace mozilla; +using namespace mozilla::a11y; + +//////////////////////////////////////////////////////////////////////////////// +// LocalAccessible: nsISupports and cycle collection + +NS_IMPL_CYCLE_COLLECTION_CLASS(LocalAccessible) +NS_IMPL_CYCLE_COLLECTION_UNLINK_BEGIN(LocalAccessible) + tmp->Shutdown(); +NS_IMPL_CYCLE_COLLECTION_UNLINK_END +NS_IMPL_CYCLE_COLLECTION_TRAVERSE_BEGIN(LocalAccessible) + NS_IMPL_CYCLE_COLLECTION_TRAVERSE(mContent, mDoc) +NS_IMPL_CYCLE_COLLECTION_TRAVERSE_END + +NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION(LocalAccessible) + NS_INTERFACE_MAP_ENTRY_CONCRETE(LocalAccessible) + NS_INTERFACE_MAP_ENTRY_AMBIGUOUS(nsISupports, LocalAccessible) +NS_INTERFACE_MAP_END + +NS_IMPL_CYCLE_COLLECTING_ADDREF(LocalAccessible) +NS_IMPL_CYCLE_COLLECTING_RELEASE_WITH_DESTROY(LocalAccessible, LastRelease()) + +LocalAccessible::LocalAccessible(nsIContent* aContent, DocAccessible* aDoc) + : mContent(aContent), + mDoc(aDoc), + mParent(nullptr), + mIndexInParent(-1), + mFirstLineStart(-1), + mStateFlags(0), + mContextFlags(0), + mReorderEventTarget(false), + mShowEventTarget(false), + mHideEventTarget(false), + mIndexOfEmbeddedChild(-1), + mGroupInfo(nullptr) {} + +LocalAccessible::~LocalAccessible() { + NS_ASSERTION(!mDoc, "LastRelease was never called!?!"); +} + +ENameValueFlag LocalAccessible::Name(nsString& aName) const { + aName.Truncate(); + + if (!HasOwnContent()) return eNameOK; + + ARIAName(aName); + if (!aName.IsEmpty()) return eNameOK; + + ENameValueFlag nameFlag = NativeName(aName); + if (!aName.IsEmpty()) return nameFlag; + + // In the end get the name from tooltip. + 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; + } + } + } + + aName.SetIsVoid(true); + + return nameFlag; +} + +void LocalAccessible::Description(nsString& aDescription) const { + // There are 4 conditions that make an accessible have no accDescription: + // 1. it's a text node; or + // 2. It has no ARIA describedby or description property + // 3. it doesn't have an accName; or + // 4. its title attribute already equals to its accName nsAutoString name; + + if (!HasOwnContent() || mContent->IsText()) return; + + ARIADescription(aDescription); + + if (aDescription.IsEmpty()) { + NativeDescription(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. + if (aDescription.Equals(name)) aDescription.Truncate(); + } +} + +KeyBinding LocalAccessible::AccessKey() const { + if (!HasOwnContent()) return KeyBinding(); + + uint32_t key = nsCoreUtils::GetAccessKeyFor(mContent); + if (!key && mContent->IsElement()) { + LocalAccessible* label = nullptr; + + // Copy access key from label node. + if (mContent->IsHTMLElement()) { + // Unless it is labeled via an ancestor