blob: b0a6af9418b38888f330b89f16e617857ad4615e [file] [log] [blame]
// Copyright 2023 The Chromium Authors
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "chrome/browser/ash/accessibility/service/user_interface_impl.h"
#include "ash/public/cpp/accessibility_focus_ring_info.h"
#include "chrome/browser/ash/accessibility/accessibility_manager.h"
#include "content/public/common/color_parser.h"
#include "mojo/public/cpp/bindings/pending_receiver.h"
#include "services/accessibility/public/mojom/user_interface.mojom-shared.h"
#include "services/accessibility/public/mojom/user_interface.mojom.h"
namespace ash {
UserInterfaceImpl::UserInterfaceImpl() = default;
UserInterfaceImpl::~UserInterfaceImpl() = default;
void UserInterfaceImpl::Bind(
mojo::PendingReceiver<ax::mojom::UserInterface> ui_receiver) {
ui_receivers_.Add(this, std::move(ui_receiver));
}
void UserInterfaceImpl::SetFocusRings(
std::vector<ax::mojom::FocusRingInfoPtr> focus_rings,
ax::mojom::AssistiveTechnologyType at_type) {
auto* accessibility_manager = AccessibilityManager::Get();
for (auto& focus_ring_info : focus_rings) {
auto focus_ring = std::make_unique<ash::AccessibilityFocusRingInfo>();
focus_ring->behavior = ash::FocusRingBehavior::PERSIST;
for (const gfx::Rect& rect : focus_ring_info->rects) {
focus_ring->rects_in_screen.emplace_back(rect);
}
const std::string id = accessibility_manager->GetFocusRingId(
at_type,
focus_ring_info->id.has_value() ? focus_ring_info->id.value() : "");
if (focus_ring_info->color.has_value()) {
focus_ring->color = focus_ring_info->color.value();
}
if (focus_ring_info->secondary_color.has_value()) {
focus_ring->secondary_color = focus_ring_info->secondary_color.value();
}
if (focus_ring_info->background_color.has_value()) {
focus_ring->background_color = focus_ring_info->background_color.value();
}
switch (focus_ring_info->type) {
case ax::mojom::FocusType::kSolid:
focus_ring->type = ash::FocusRingType::SOLID;
break;
case ax::mojom::FocusType::kDashed:
focus_ring->type = ash::FocusRingType::DASHED;
break;
case ax::mojom::FocusType::kGlow:
focus_ring->type = ash::FocusRingType::GLOW;
break;
}
if (focus_ring_info->stacking_order.has_value()) {
switch (focus_ring_info->stacking_order.value()) {
case ax::mojom::FocusRingStackingOrder::kAboveAccessibilityBubbles:
focus_ring->stacking_order =
ash::FocusRingStackingOrder::ABOVE_ACCESSIBILITY_BUBBLES;
break;
case ax::mojom::FocusRingStackingOrder::kBelowAccessibilityBubbles:
focus_ring->stacking_order =
ash::FocusRingStackingOrder::BELOW_ACCESSIBILITY_BUBBLES;
break;
}
}
// Update the touch exploration controller so that synthesized touch events
// are anchored within the focused object.
// NOTE: The final anchor point will be determined by the first rect of the
// final focus ring.
if (!focus_ring->rects_in_screen.empty()) {
accessibility_manager->SetTouchAccessibilityAnchorPoint(
focus_ring->rects_in_screen[0].CenterPoint());
}
accessibility_manager->SetFocusRing(id, std::move(focus_ring));
}
}
} // namespace ash