blob: c5fba7a785e80e02da0766104d2db6958e22d6b0 [file] [log] [blame]
// Copyright 2017 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef CHROME_BROWSER_ASH_ARC_ACCESSIBILITY_ARC_ACCESSIBILITY_HELPER_BRIDGE_H_
#define CHROME_BROWSER_ASH_ARC_ACCESSIBILITY_ARC_ACCESSIBILITY_HELPER_BRIDGE_H_
#include <map>
#include <memory>
#include <set>
#include <string>
#include <tuple>
#include "ash/public/cpp/external_arc/message_center/arc_notification_surface_manager.h"
#include "base/callback_list.h"
#include "chrome/browser/ash/accessibility/accessibility_manager.h"
#include "chrome/browser/ash/arc/accessibility/accessibility_helper_instance_remote_proxy.h"
#include "chrome/browser/ash/arc/accessibility/arc_accessibility_tree_tracker.h"
#include "chrome/browser/ash/arc/accessibility/ax_tree_source_arc.h"
#include "components/arc/mojom/accessibility_helper.mojom-forward.h"
#include "components/arc/session/connection_observer.h"
#include "components/keyed_service/core/keyed_service.h"
class PrefService;
class Profile;
namespace content {
class BrowserContext;
} // namespace content
namespace extensions {
class EventRouter;
}
namespace gfx {
class Rect;
} // namespace gfx
namespace arc {
class AXTreeSourceArc;
class ArcBridgeService;
arc::mojom::CaptionStylePtr GetCaptionStyleFromPrefs(PrefService* prefs);
// ArcAccessibilityHelperBridge is an instance to receive converted Android
// accessibility events and info via mojo interface and dispatch them to Chrome
// OS components.
class ArcAccessibilityHelperBridge
: public KeyedService,
public mojom::AccessibilityHelperHost,
public ConnectionObserver<mojom::AccessibilityHelperInstance>,
public AXTreeSourceArc::Delegate,
public ash::ArcNotificationSurfaceManager::Observer,
public extensions::AutomationEventRouterObserver {
public:
// Builds the ArcAccessibilityHelperBridgeFactory.
static void CreateFactory();
// Returns singleton instance for the given BrowserContext,
// or nullptr if the browser |context| is not allowed to use ARC.
static ArcAccessibilityHelperBridge* GetForBrowserContext(
content::BrowserContext* context);
ArcAccessibilityHelperBridge(content::BrowserContext* browser_context,
ArcBridgeService* arc_bridge_service);
~ArcAccessibilityHelperBridge() override;
// Sets ChromeVox or TalkBack active for the current task.
void SetNativeChromeVoxArcSupport(bool enabled);
// Request Android to send the entire tree with the tree id. Returns true if
// the specified tree exists in ARC and a request was sent.
bool RefreshTreeIfInActiveWindow(const ui::AXTreeID& tree_id);
// KeyedService overrides.
void Shutdown() override;
// ConnectionObserver<mojom::AccessibilityHelperInstance> overrides.
void OnConnectionReady() override;
// mojom::AccessibilityHelperHost overrides.
void OnAccessibilityEvent(
mojom::AccessibilityEventDataPtr event_data) override;
void OnNotificationStateChanged(
const std::string& notification_key,
mojom::AccessibilityNotificationStateType state) override;
void OnToggleNativeChromeVoxArcSupport(bool enabled) override;
// AXTreeSourceArc::Delegate overrides.
void OnAction(const ui::AXActionData& data) const override;
bool UseFullFocusMode() const override;
// ArcNotificationSurfaceManager::Observer overrides.
// TODO(hirokisato): Remove this method once refactoring finishes.
// This exists only to do refactoring without large test change.
void OnNotificationSurfaceAdded(
ash::ArcNotificationSurface* surface) override;
void OnNotificationSurfaceRemoved(
ash::ArcNotificationSurface* surface) override {}
// AutomationEventRouterObserver overrides.
void AllAutomationExtensionsGone() override;
void ExtensionListenerAdded() override;
const ArcAccessibilityTreeTracker::TreeMap& trees_for_test() const {
return tree_tracker_.trees_for_test();
}
private:
// virtual for testing.
virtual aura::Window* GetFocusedArcWindow() const;
virtual extensions::EventRouter* GetEventRouter() const;
virtual arc::mojom::AccessibilityFilterType GetFilterType();
std::unique_ptr<PrefChangeRegistrar> pref_change_registrar_;
void UpdateCaptionSettings() const;
void OnActionResult(const ui::AXActionData& data, bool result) const;
void OnGetTextLocationDataResult(
const ui::AXActionData& data,
const absl::optional<gfx::Rect>& result_rect) const;
absl::optional<gfx::Rect> OnGetTextLocationDataResultInternal(
const ui::AXTreeID& ax_tree_id,
const absl::optional<gfx::Rect>& result_rect) const;
void OnAccessibilityStatusChanged(
const ash::AccessibilityStatusEventDetails& event_details);
void UpdateEnabledFeature();
void HandleFilterTypeFocusEvent(mojom::AccessibilityEventDataPtr event_data);
void HandleFilterTypeAllEvent(mojom::AccessibilityEventDataPtr event_data);
void DispatchEventTextAnnouncement(
mojom::AccessibilityEventData* event_data) const;
bool is_focus_event_enabled_ = false;
bool use_full_focus_mode_ = false;
Profile* const profile_;
ArcBridgeService* const arc_bridge_service_;
const AccessibilityHelperInstanceRemoteProxy accessibility_helper_instance_;
ArcAccessibilityTreeTracker tree_tracker_;
base::CallbackListSubscription accessibility_status_subscription_;
arc::mojom::AccessibilityFilterType filter_type_ =
arc::mojom::AccessibilityFilterType::OFF;
base::ScopedObservation<extensions::AutomationEventRouter,
extensions::AutomationEventRouterObserver>
automation_event_router_observer_{this};
DISALLOW_COPY_AND_ASSIGN(ArcAccessibilityHelperBridge);
};
} // namespace arc
#endif // CHROME_BROWSER_ASH_ARC_ACCESSIBILITY_ARC_ACCESSIBILITY_HELPER_BRIDGE_H_