Bug 1757812 - P2: Move pivot in parent when caching is enabled. r=morgan

This is a baby step in the caching direction. It isn't perfect yet.
Specifically, cache we have now in Android depends on a cache push
from content that doesn't happen if we do this all parent side.

So most of the junit tests pass, except for the heading one because
we don't cache heading levels in the less complete viewport cache.

tl;dr
This will work right when the accessibles being retrieved are from our
ctw cache. This will happen in followup bugs.

Differential Revision: https://phabricator.services.mozilla.com/D140120
This commit is contained in:
Eitan Isaacson 2022-03-03 22:04:39 +00:00
parent add4ad659f
commit 57f4ee0c7b
5 changed files with 58 additions and 36 deletions

View File

@ -298,16 +298,34 @@ void AccessibleWrap::PivotTo(int32_t aGranularity, bool aForward,
bool aInclusive) {
a11y::Pivot pivot(RootAccessible());
TraversalRule rule(aGranularity);
Accessible* maybeResult = aForward ? pivot.Next(this, rule, aInclusive)
: pivot.Prev(this, rule, aInclusive);
LocalAccessible* result = maybeResult ? maybeResult->AsLocal() : nullptr;
if (result && (result != this || aInclusive)) {
PivotMoveReason reason = aForward ? nsIAccessiblePivot::REASON_NEXT
: nsIAccessiblePivot::REASON_PREV;
RefPtr<AccEvent> event = new AccVCChangeEvent(
result->Document(), this, -1, -1, result, -1, -1, reason,
nsIAccessiblePivot::NO_BOUNDARY, eFromUserInput);
nsEventShell::FireEvent(event);
Accessible* current = IsProxy() ? Proxy() : static_cast<Accessible*>(this);
Accessible* result = aForward ? pivot.Next(current, rule, aInclusive)
: pivot.Prev(current, rule, aInclusive);
if (result && (result != current || aInclusive)) {
RefPtr<AccessibleWrap> newPosition =
result->IsRemote() ? WrapperFor(result->AsRemote())
: static_cast<AccessibleWrap*>(result->AsLocal());
if (IPCAccessibilityActive()) {
// We are in the child process. Dispatch a virtual cursor
// change event that will be turned into an android
// accessibility focused changed event in the parent.
PivotMoveReason reason = aForward ? nsIAccessiblePivot::REASON_NEXT
: nsIAccessiblePivot::REASON_PREV;
LocalAccessible* localResult = result->AsLocal();
MOZ_ASSERT(localResult);
RefPtr<AccEvent> event = new AccVCChangeEvent(
localResult->Document(), this, -1, -1, localResult, -1, -1, reason,
nsIAccessiblePivot::NO_BOUNDARY, eFromUserInput);
nsEventShell::FireEvent(event);
} else {
// We are in the parent process. Dispatch an accessibility focused
// event directly.
RefPtr<SessionAccessibility> sessionAcc =
SessionAccessibility::GetInstanceFor(result);
sessionAcc->SendAccessibilityFocusedEvent(newPosition);
}
}
}

View File

@ -36,6 +36,7 @@ class AccessibleWrap : public LocalAccessible {
virtual bool GetSelectionBounds(int32_t* aStartOffset, int32_t* aEndOffset);
MOZ_CAN_RUN_SCRIPT_BOUNDARY
virtual void PivotTo(int32_t aGranularity, bool aForward, bool aInclusive);
virtual void NavigateText(int32_t aGranularity, int32_t aStartOffset,

View File

@ -7,6 +7,7 @@
#include "LocalAccessible-inl.h"
#include "mozilla/a11y/DocAccessiblePlatformExtParent.h"
#include "mozilla/StaticPrefs_accessibility.h"
using namespace mozilla::a11y;
@ -110,6 +111,11 @@ bool RemoteAccessibleWrap::GetSelectionBounds(int32_t* aStartOffset,
void RemoteAccessibleWrap::PivotTo(int32_t aGranularity, bool aForward,
bool aInclusive) {
if (StaticPrefs::accessibility_cache_enabled_AtStartup()) {
AccessibleWrap::PivotTo(aGranularity, aForward, aInclusive);
return;
}
Unused << Proxy()->Document()->GetPlatformExtension()->SendPivot(
Proxy()->ID(), aGranularity, aForward, aInclusive);
}

View File

@ -18,6 +18,7 @@
#include "mozilla/PresShell.h"
#include "mozilla/dom/BrowserParent.h"
#include "mozilla/a11y/Accessible.h"
#include "mozilla/a11y/DocAccessibleParent.h"
#include "mozilla/a11y/DocManager.h"
#include "mozilla/jni/GeckoBundleUtils.h"
@ -173,9 +174,26 @@ void SessionAccessibility::Paste(int32_t aID) {
}
RefPtr<SessionAccessibility> SessionAccessibility::GetInstanceFor(
RemoteAccessible* aAccessible) {
auto tab =
static_cast<dom::BrowserParent*>(aAccessible->Document()->Manager());
Accessible* aAccessible) {
if (aAccessible->IsLocal()) {
RootAccessible* rootAcc = aAccessible->AsLocal()->RootAccessible();
nsViewManager* vm = rootAcc->PresShellPtr()->GetViewManager();
if (!vm) {
return nullptr;
}
nsCOMPtr<nsIWidget> rootWidget = vm->GetRootWidget();
// `rootWidget` can be one of several types. Here we make sure it is an
// android nsWindow.
if (RefPtr<nsWindow> window = nsWindow::From(rootWidget)) {
return window->GetSessionAccessibility();
}
return nullptr;
}
auto tab = static_cast<dom::BrowserParent*>(
aAccessible->AsRemote()->Document()->Manager());
dom::Element* frame = tab->GetOwnerElement();
MOZ_ASSERT(frame);
if (!frame) {
@ -186,24 +204,6 @@ RefPtr<SessionAccessibility> SessionAccessibility::GetInstanceFor(
return chromeDoc ? GetInstanceFor(chromeDoc) : nullptr;
}
RefPtr<SessionAccessibility> SessionAccessibility::GetInstanceFor(
LocalAccessible* aAccessible) {
RootAccessible* rootAcc = aAccessible->RootAccessible();
nsViewManager* vm = rootAcc->PresShellPtr()->GetViewManager();
if (!vm) {
return nullptr;
}
nsCOMPtr<nsIWidget> rootWidget = vm->GetRootWidget();
// `rootWidget` can be one of several types. Here we make sure it is an
// android nsWindow.
if (RefPtr<nsWindow> window = nsWindow::From(rootWidget)) {
return window->GetSessionAccessibility();
}
return nullptr;
}
void SessionAccessibility::SendAccessibilityFocusedEvent(
AccessibleWrap* aAccessible) {
mSessionAccessibility->SendEvent(

View File

@ -16,7 +16,7 @@ namespace mozilla {
namespace a11y {
class AccessibleWrap;
class RemoteAccessible;
class Accessible;
class RootAccessibleWrap;
class BatchData;
@ -42,10 +42,7 @@ class SessionAccessibility final
}
static void Init();
static RefPtr<SessionAccessibility> GetInstanceFor(
RemoteAccessible* aAccessible);
static RefPtr<SessionAccessibility> GetInstanceFor(
LocalAccessible* aAccessible);
static RefPtr<SessionAccessibility> GetInstanceFor(Accessible* aAccessible);
// Native implementations
using Base::AttachNative;