Commit c6dc55ee authored by Yuichiro Hanada's avatar Yuichiro Hanada Committed by Commit Bot

Set keyboard type to virtual when a11y keyboard is enabled.

Bug: b/111833294
Test: Open Hangouts app and enable a11y keyboard in laptop mode, then
      confirm a11y keyboard shows up by clicking on the text field.

Change-Id: Ibf8202b572939dd8040918f9c64fab01ce6de306
Reviewed-on: https://chromium-review.googlesource.com/1221407
Commit-Queue: Yuichiro Hanada <yhanada@chromium.org>
Reviewed-by: default avatarMitsuru Oshima <oshima@chromium.org>
Cr-Commit-Position: refs/heads/master@{#594547}
parent 459099e1
......@@ -391,6 +391,7 @@ component("ash") {
"keyboard/virtual_keyboard_container_layout_manager.h",
"keyboard/virtual_keyboard_controller.cc",
"keyboard/virtual_keyboard_controller.h",
"keyboard/virtual_keyboard_controller_observer.h",
"laser/laser_pointer_controller.cc",
"laser/laser_pointer_controller.h",
"laser/laser_pointer_view.cc",
......
......@@ -257,6 +257,8 @@ void VirtualKeyboardController::SetKeyboardEnabled(bool enabled) {
} else {
Shell::Get()->DisableKeyboard();
}
for (VirtualKeyboardControllerObserver& observer : observers_)
observer.OnVirtualKeyboardStateChanged(is_enabled);
}
void VirtualKeyboardController::ForceShowKeyboard() {
......@@ -300,6 +302,16 @@ void VirtualKeyboardController::OnActiveUserSessionChanged(
Shell::Get()->EnableKeyboard();
}
void VirtualKeyboardController::AddObserver(
VirtualKeyboardControllerObserver* observer) {
observers_.AddObserver(observer);
}
void VirtualKeyboardController::RemoveObserver(
VirtualKeyboardControllerObserver* observer) {
observers_.RemoveObserver(observer);
}
void VirtualKeyboardController::UpdateBluetoothDevice(
device::BluetoothDevice* device) {
// We only care about keyboard type bluetooth device change.
......
......@@ -9,9 +9,11 @@
#include "ash/ash_export.h"
#include "ash/bluetooth_devices_observer.h"
#include "ash/keyboard/virtual_keyboard_controller_observer.h"
#include "ash/session/session_observer.h"
#include "ash/wm/tablet_mode/tablet_mode_observer.h"
#include "base/macros.h"
#include "base/observer_list.h"
#include "ui/base/ime/chromeos/public/interfaces/ime_keyset.mojom.h"
#include "ui/events/devices/input_device_event_observer.h"
#include "ui/keyboard/keyboard_controller_observer.h"
......@@ -60,6 +62,10 @@ class ASH_EXPORT VirtualKeyboardController
// SessionObserver:
void OnActiveUserSessionChanged(const AccountId& account_id) override;
// Management of the observer list.
void AddObserver(VirtualKeyboardControllerObserver* observer);
void RemoveObserver(VirtualKeyboardControllerObserver* observer);
private:
// Updates the list of active input devices.
void UpdateDevices();
......@@ -89,6 +95,8 @@ class ASH_EXPORT VirtualKeyboardController
// Observer to observe the bluetooth devices.
std::unique_ptr<BluetoothDevicesObserver> bluetooth_devices_observer_;
base::ObserverList<VirtualKeyboardControllerObserver> observers_;
DISALLOW_COPY_AND_ASSIGN(VirtualKeyboardController);
};
......
// Copyright 2018 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 ASH_KEYBOARD_VIRTUAL_KEYBOARD_CONTROLLER_OBSERVER_H_
#define ASH_KEYBOARD_VIRTUAL_KEYBOARD_CONTROLLER_OBSERVER_H_
#include "base/observer_list.h"
namespace ash {
class VirtualKeyboardControllerObserver : public base::CheckedObserver {
public:
virtual void OnVirtualKeyboardStateChanged(bool enabled) = 0;
protected:
~VirtualKeyboardControllerObserver() override = default;
};
} // namespace ash
#endif // ASH_KEYBOARD_VIRTUAL_KEYBOARD_CONTROLLER_OBSERVER_H_
......@@ -17,9 +17,8 @@
#include "ui/aura/window.h"
#include "ui/base/ime/input_method.h"
#include "ui/events/base_event_utils.h"
#include "ui/events/devices/input_device.h"
#include "ui/events/devices/input_device_manager.h"
#include "ui/events/event.h"
#include "ui/keyboard/keyboard_util.h"
#include "ui/views/widget/widget.h"
namespace exo {
......@@ -112,17 +111,9 @@ bool ConsumedByIme(Surface* focus, const ui::KeyEvent* event) {
return false;
}
bool IsPhysicalKeyboardEnabled() {
// The internal keyboard is enabled if tablet mode is not enabled.
if (!WMHelper::GetInstance()->IsTabletModeWindowManagerEnabled())
return true;
for (auto& keyboard :
ui::InputDeviceManager::GetInstance()->GetKeyboardDevices()) {
if (keyboard.type != ui::InputDeviceType::INPUT_DEVICE_INTERNAL)
return true;
}
return false;
bool IsVirtualKeyboardEnabled() {
return WMHelper::GetInstance()->IsAccessibilityKeyboardEnabled() ||
keyboard::GetTouchKeyboardEnabled();
}
bool IsReservedAccelerator(const ui::KeyEvent* event) {
......@@ -168,8 +159,8 @@ Keyboard::Keyboard(KeyboardDelegate* delegate, Seat* seat)
auto* helper = WMHelper::GetInstance();
AddEventHandler();
seat_->AddObserver(this);
helper->AddTabletModeObserver(this);
helper->AddInputDeviceEventObserver(this);
helper->AddAccessibilityObserver(this);
helper->AddVirtualKeyboardControllerObserver(this);
OnSurfaceFocused(seat_->GetFocusedSurface());
}
......@@ -181,8 +172,8 @@ Keyboard::~Keyboard() {
auto* helper = WMHelper::GetInstance();
RemoveEventHandler();
seat_->RemoveObserver(this);
helper->RemoveTabletModeObserver(this);
helper->RemoveInputDeviceEventObserver(this);
helper->RemoveVirtualKeyboardControllerObserver(this);
helper->RemoveAccessibilityObserver(this);
}
bool Keyboard::HasDeviceConfigurationDelegate() const {
......@@ -192,7 +183,7 @@ bool Keyboard::HasDeviceConfigurationDelegate() const {
void Keyboard::SetDeviceConfigurationDelegate(
KeyboardDeviceConfigurationDelegate* delegate) {
device_configuration_delegate_ = delegate;
OnKeyboardDeviceConfigurationChanged();
OnAccessibilityStatusChanged();
}
void Keyboard::AddObserver(KeyboardObserver* observer) {
......@@ -330,29 +321,6 @@ void Keyboard::OnSurfaceDestroying(Surface* surface) {
SetFocus(nullptr);
}
////////////////////////////////////////////////////////////////////////////////
// ui::InputDeviceEventObserver overrides:
void Keyboard::OnKeyboardDeviceConfigurationChanged() {
if (device_configuration_delegate_) {
device_configuration_delegate_->OnKeyboardTypeChanged(
IsPhysicalKeyboardEnabled());
}
}
////////////////////////////////////////////////////////////////////////////////
// ash::TabletModeObserver overrides:
void Keyboard::OnTabletModeStarted() {
OnKeyboardDeviceConfigurationChanged();
}
void Keyboard::OnTabletModeEnding() {}
void Keyboard::OnTabletModeEnded() {
OnKeyboardDeviceConfigurationChanged();
}
////////////////////////////////////////////////////////////////////////////////
// SeatObserver overrides:
......@@ -367,6 +335,24 @@ void Keyboard::OnSurfaceFocused(Surface* gained_focus) {
SetFocus(gained_focus_surface);
}
////////////////////////////////////////////////////////////////////////////////
// AccessibilityObserver overrides:
void Keyboard::OnAccessibilityStatusChanged() {
if (device_configuration_delegate_) {
device_configuration_delegate_->OnKeyboardTypeChanged(
!IsVirtualKeyboardEnabled());
}
}
////////////////////////////////////////////////////////////////////////////////
// VirtualKeyboardController::Observer overrides:
void Keyboard::OnVirtualKeyboardStateChanged(bool enabled) {
if (device_configuration_delegate_)
device_configuration_delegate_->OnKeyboardTypeChanged(!enabled);
}
////////////////////////////////////////////////////////////////////////////////
// Keyboard, private:
......
......@@ -7,7 +7,8 @@
#include <vector>
#include "ash/wm/tablet_mode/tablet_mode_observer.h"
#include "ash/accessibility/accessibility_observer.h"
#include "ash/keyboard/virtual_keyboard_controller_observer.h"
#include "base/containers/flat_map.h"
#include "base/containers/flat_set.h"
#include "base/macros.h"
......@@ -15,7 +16,6 @@
#include "components/exo/keyboard_observer.h"
#include "components/exo/seat_observer.h"
#include "components/exo/surface_observer.h"
#include "ui/events/devices/input_device_event_observer.h"
#include "ui/events/event.h"
#include "ui/events/event_handler.h"
......@@ -33,10 +33,10 @@ class Surface;
// This class implements a client keyboard that represents one or more keyboard
// devices.
class Keyboard : public ui::EventHandler,
public ui::InputDeviceEventObserver,
public ash::TabletModeObserver,
public SurfaceObserver,
public SeatObserver {
public SeatObserver,
public ash::AccessibilityObserver,
public ash::VirtualKeyboardControllerObserver {
public:
Keyboard(KeyboardDelegate* delegate, Seat* seat);
~Keyboard() override;
......@@ -63,18 +63,16 @@ class Keyboard : public ui::EventHandler,
// Overridden from SurfaceObserver:
void OnSurfaceDestroying(Surface* surface) override;
// Overridden from ui::InputDeviceEventObserver:
void OnKeyboardDeviceConfigurationChanged() override;
// Overridden from ash::TabletModeObserver:
void OnTabletModeStarted() override;
void OnTabletModeEnding() override;
void OnTabletModeEnded() override;
// Overridden from SeatObserver:
void OnSurfaceFocusing(Surface* gaining_focus) override;
void OnSurfaceFocused(Surface* gained_focus) override;
// Overridden from AccessibilityObserver:
void OnAccessibilityStatusChanged() override;
// Overridden from VirtualKeyboardController::Observer
void OnVirtualKeyboardStateChanged(bool enabled) override;
private:
// Change keyboard focus to |surface|.
void SetFocus(Surface* surface);
......
......@@ -4,6 +4,7 @@
#include "components/exo/keyboard.h"
#include "ash/accessibility/accessibility_controller.h"
#include "ash/shell.h"
#include "ash/wm/tablet_mode/tablet_mode_controller.h"
#include "base/macros.h"
......@@ -305,10 +306,15 @@ TEST_F(KeyboardTest, OnKeyboardTypeChanged) {
ui::DeviceHotplugEventObserver* device_data_manager =
ui::DeviceDataManager::GetInstance();
ASSERT_TRUE(device_data_manager != nullptr);
// Make sure that DeviceDataManager has one external keyboard.
// Make sure that DeviceDataManager has one external keyboard...
const std::vector<ui::InputDevice> keyboards{
ui::InputDevice(2, ui::InputDeviceType::INPUT_DEVICE_USB, "keyboard")};
device_data_manager->OnKeyboardDevicesUpdated(keyboards);
// and a touch screen.
const std::vector<ui::TouchscreenDevice> touch_screen{
ui::TouchscreenDevice(3, ui::InputDeviceType::INPUT_DEVICE_INTERNAL,
"touch", gfx::Size(600, 400), 1)};
device_data_manager->OnTouchscreenDevicesUpdated(touch_screen);
ash::TabletModeController* tablet_mode_controller =
ash::Shell::Get()->tablet_mode_controller();
......@@ -329,7 +335,7 @@ TEST_F(KeyboardTest, OnKeyboardTypeChanged) {
device_data_manager->OnKeyboardDevicesUpdated(
std::vector<ui::InputDevice>({}));
// Re-adding keyboards calls OnKeyboardTypeChanged() with true;
// Re-adding keyboards calls OnKeyboardTypeChanged() with true.
EXPECT_CALL(configuration_delegate, OnKeyboardTypeChanged(true));
device_data_manager->OnKeyboardDevicesUpdated(keyboards);
......@@ -338,6 +344,50 @@ TEST_F(KeyboardTest, OnKeyboardTypeChanged) {
tablet_mode_controller->EnableTabletModeWindowManager(false);
}
TEST_F(KeyboardTest, OnKeyboardTypeChanged_AccessibilityKeyboard) {
std::unique_ptr<Surface> surface(new Surface);
std::unique_ptr<ShellSurface> shell_surface(new ShellSurface(surface.get()));
gfx::Size buffer_size(10, 10);
std::unique_ptr<Buffer> buffer(
new Buffer(exo_test_helper()->CreateGpuMemoryBuffer(buffer_size)));
surface->Attach(buffer.get());
surface->Commit();
aura::client::FocusClient* focus_client =
aura::client::GetFocusClient(ash::Shell::GetPrimaryRootWindow());
focus_client->FocusWindow(nullptr);
ui::DeviceHotplugEventObserver* device_data_manager =
ui::DeviceDataManager::GetInstance();
ASSERT_TRUE(device_data_manager != nullptr);
// Make sure that DeviceDataManager has one external keyboard.
const std::vector<ui::InputDevice> keyboards{
ui::InputDevice(2, ui::InputDeviceType::INPUT_DEVICE_USB, "keyboard")};
device_data_manager->OnKeyboardDevicesUpdated(keyboards);
MockKeyboardDelegate delegate;
Seat seat;
auto keyboard = std::make_unique<Keyboard>(&delegate, &seat);
MockKeyboardDeviceConfigurationDelegate configuration_delegate;
EXPECT_CALL(configuration_delegate, OnKeyboardTypeChanged(true));
keyboard->SetDeviceConfigurationDelegate(&configuration_delegate);
EXPECT_TRUE(keyboard->HasDeviceConfigurationDelegate());
ash::AccessibilityController* accessibility_controller =
ash::Shell::Get()->accessibility_controller();
// Enable a11y keyboard calls OnKeyboardTypeChanged() with false.
EXPECT_CALL(configuration_delegate, OnKeyboardTypeChanged(false));
accessibility_controller->SetVirtualKeyboardEnabled(true);
// Disable a11y keyboard calls OnKeyboardTypeChanged() with true.
EXPECT_CALL(configuration_delegate, OnKeyboardTypeChanged(true));
accessibility_controller->SetVirtualKeyboardEnabled(false);
keyboard.reset();
}
TEST_F(KeyboardTest, KeyboardObserver) {
MockKeyboardDelegate delegate;
Seat seat;
......
......@@ -4,6 +4,8 @@
#include "components/exo/wm_helper.h"
#include "ash/accessibility/accessibility_controller.h"
#include "ash/keyboard/virtual_keyboard_controller.h"
#include "ash/shell.h"
#include "ash/wm/tablet_mode/tablet_mode_controller.h"
#include "base/memory/singleton.h"
......@@ -13,7 +15,6 @@
#include "ui/display/manager/display_configurator.h"
#include "ui/display/manager/display_manager.h"
#include "ui/display/types/display_snapshot.h"
#include "ui/events/devices/input_device_manager.h"
#include "ui/wm/public/activation_client.h"
namespace exo {
......@@ -53,6 +54,15 @@ bool WMHelper::HasInstance() {
return !!g_instance;
}
void WMHelper::AddAccessibilityObserver(ash::AccessibilityObserver* observer) {
ash::Shell::Get()->accessibility_controller()->AddObserver(observer);
}
void WMHelper::RemoveAccessibilityObserver(
ash::AccessibilityObserver* observer) {
ash::Shell::Get()->accessibility_controller()->RemoveObserver(observer);
}
void WMHelper::AddActivationObserver(wm::ActivationChangeObserver* observer) {
ash::Shell::Get()->activation_client()->AddObserver(observer);
}
......@@ -79,14 +89,14 @@ void WMHelper::RemoveTabletModeObserver(ash::TabletModeObserver* observer) {
ash::Shell::Get()->tablet_mode_controller()->RemoveObserver(observer);
}
void WMHelper::AddInputDeviceEventObserver(
ui::InputDeviceEventObserver* observer) {
ui::InputDeviceManager::GetInstance()->AddObserver(observer);
void WMHelper::AddVirtualKeyboardControllerObserver(
ash::VirtualKeyboardControllerObserver* observer) {
ash::Shell::Get()->virtual_keyboard_controller()->AddObserver(observer);
}
void WMHelper::RemoveInputDeviceEventObserver(
ui::InputDeviceEventObserver* observer) {
ui::InputDeviceManager::GetInstance()->RemoveObserver(observer);
void WMHelper::RemoveVirtualKeyboardControllerObserver(
ash::VirtualKeyboardControllerObserver* observer) {
ash::Shell::Get()->virtual_keyboard_controller()->RemoveObserver(observer);
}
void WMHelper::AddDisplayConfigurationObserver(
......@@ -231,4 +241,10 @@ double WMHelper::GetDefaultDeviceScaleFactor() const {
return display_info.display_modes()[0].device_scale_factor();
}
bool WMHelper::IsAccessibilityKeyboardEnabled() const {
return ash::Shell::Get()
->accessibility_controller()
->IsVirtualKeyboardEnabled();
}
} // namespace exo
......@@ -15,7 +15,9 @@
#include "ui/compositor/compositor_vsync_manager.h"
namespace ash {
class AccessibilityObserver;
class TabletModeObserver;
class VirtualKeyboardControllerObserver;
}
namespace aura {
......@@ -38,7 +40,6 @@ class ManagedDisplayInfo;
namespace ui {
class EventHandler;
class DropTargetEvent;
class InputDeviceEventObserver;
} // namespace ui
namespace wm {
......@@ -70,14 +71,18 @@ class WMHelper : public aura::client::DragDropDelegate {
aura::Env* env() { return env_; }
void AddAccessibilityObserver(ash::AccessibilityObserver* observer);
void RemoveAccessibilityObserver(ash::AccessibilityObserver* observer);
void AddActivationObserver(wm::ActivationChangeObserver* observer);
void RemoveActivationObserver(wm::ActivationChangeObserver* observer);
void AddFocusObserver(aura::client::FocusChangeObserver* observer);
void RemoveFocusObserver(aura::client::FocusChangeObserver* observer);
void AddTabletModeObserver(ash::TabletModeObserver* observer);
void RemoveTabletModeObserver(ash::TabletModeObserver* observer);
void AddInputDeviceEventObserver(ui::InputDeviceEventObserver* observer);
void RemoveInputDeviceEventObserver(ui::InputDeviceEventObserver* observer);
void AddVirtualKeyboardControllerObserver(
ash::VirtualKeyboardControllerObserver* observer);
void RemoveVirtualKeyboardControllerObserver(
ash::VirtualKeyboardControllerObserver* observer);
void AddDisplayConfigurationObserver(
ash::WindowTreeHostManager::Observer* observer);
......@@ -105,6 +110,7 @@ class WMHelper : public aura::client::DragDropDelegate {
void RemovePostTargetHandler(ui::EventHandler* handler);
bool IsTabletModeWindowManagerEnabled() const;
double GetDefaultDeviceScaleFactor() const;
bool IsAccessibilityKeyboardEnabled() const;
// Overridden from aura::client::DragDropDelegate:
void OnDragEntered(const ui::DropTargetEvent& event) override;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment