Commit 53303949 authored by Scott Violet's avatar Scott Violet Committed by Commit Bot

chromeos: wires up can-focus

There are a couple of issues addressed here:
. kFocusable_InitProperty was not wired up correctly.
. Ash created top-levels were not picking up the value set by clients

To fix these I'm adding kCanFocus. ws2 sets this from calls by clients to
WindowTree::SetCanFocus(). Ash uses this property as well if the client
supplies kFocusable_InitProperty. I think kFocusable_InitProperty should
go away. That'll be easier once we get rid of --mash.

I'm also forking the TopLevelWindowFactory tests. I moved the existing
ones into TopLevelWindowFactoryMash (these only run with --mash). I also
made the tests work in classic mode with ws2. I added a new file for this
that is built in ash_unittests.

BUG=842301
TEST=covered by tests

Change-Id: I016ed612e7ab1d7bc1cdc4840c3aa9271078ab9e
Reviewed-on: https://chromium-review.googlesource.com/1086151
Commit-Queue: Scott Violet <sky@chromium.org>
Reviewed-by: default avatarJames Cook <jamescook@chromium.org>
Cr-Commit-Position: refs/heads/master@{#564646}
parent d47abb70
...@@ -1894,6 +1894,7 @@ test("ash_unittests") { ...@@ -1894,6 +1894,7 @@ test("ash_unittests") {
"wm/tablet_mode/accelerometer_test_data_literals.cc", "wm/tablet_mode/accelerometer_test_data_literals.cc",
"wm/tablet_mode/tablet_mode_controller_unittest.cc", "wm/tablet_mode/tablet_mode_controller_unittest.cc",
"wm/tablet_mode/tablet_mode_window_manager_unittest.cc", "wm/tablet_mode/tablet_mode_window_manager_unittest.cc",
"wm/top_level_window_factory_unittest.cc",
"wm/toplevel_window_event_handler_unittest.cc", "wm/toplevel_window_event_handler_unittest.cc",
"wm/video_detector_unittest.cc", "wm/video_detector_unittest.cc",
"wm/window_animations_unittest.cc", "wm/window_animations_unittest.cc",
...@@ -2380,7 +2381,7 @@ source_set("mash_unittests") { ...@@ -2380,7 +2381,7 @@ source_set("mash_unittests") {
"display/display_synchronizer_unittest.cc", "display/display_synchronizer_unittest.cc",
"window_manager_unittest.cc", "window_manager_unittest.cc",
"wm/non_client_frame_controller_unittest.cc", "wm/non_client_frame_controller_unittest.cc",
"wm/top_level_window_factory_unittest.cc", "wm/top_level_window_factory_mash_unittest.cc",
] ]
deps = [ deps = [
......
...@@ -11,6 +11,7 @@ ...@@ -11,6 +11,7 @@
#include "ash/wm/property_util.h" #include "ash/wm/property_util.h"
#include "ash/wm/window_state.h" #include "ash/wm/window_state.h"
#include "services/ui/public/interfaces/window_tree_constants.mojom.h" #include "services/ui/public/interfaces/window_tree_constants.mojom.h"
#include "services/ui/ws2/window_properties.h"
#include "ui/aura/client/aura_constants.h" #include "ui/aura/client/aura_constants.h"
#include "ui/aura/client/transient_window_client.h" #include "ui/aura/client/transient_window_client.h"
#include "ui/aura/mus/property_converter.h" #include "ui/aura/mus/property_converter.h"
...@@ -133,6 +134,10 @@ void DetachedTitleAreaRendererForClient::Detach() { ...@@ -133,6 +134,10 @@ void DetachedTitleAreaRendererForClient::Detach() {
widget_->SetContentsView(new views::View()); widget_->SetContentsView(new views::View());
} }
bool DetachedTitleAreaRendererForClient::CanActivate() const {
return widget_->GetNativeView()->GetProperty(ui::ws2::kCanFocus);
}
views::Widget* DetachedTitleAreaRendererForClient::GetWidget() { views::Widget* DetachedTitleAreaRendererForClient::GetWidget() {
return widget_; return widget_;
} }
......
...@@ -89,6 +89,7 @@ class DetachedTitleAreaRendererForClient : public views::WidgetDelegate { ...@@ -89,6 +89,7 @@ class DetachedTitleAreaRendererForClient : public views::WidgetDelegate {
views::Widget* widget() { return widget_; } views::Widget* widget() { return widget_; }
// views::WidgetDelegate: // views::WidgetDelegate:
bool CanActivate() const override;
views::Widget* GetWidget() override; views::Widget* GetWidget() override;
const views::Widget* GetWidget() const override; const views::Widget* GetWidget() const override;
void DeleteDelegate() override; void DeleteDelegate() override;
......
...@@ -298,23 +298,10 @@ std::unique_ptr<aura::Window> AshTestBase::CreateTestWindow( ...@@ -298,23 +298,10 @@ std::unique_ptr<aura::Window> AshTestBase::CreateTestWindow(
mojo::ConvertTo<std::vector<uint8_t>>( mojo::ConvertTo<std::vector<uint8_t>>(
static_cast<int32_t>(mus_window_type)); static_cast<int32_t>(mus_window_type));
if (!window_tree_client_) {
// Lazily create a single client.
window_tree_client_ = std::make_unique<ui::ws2::TestWindowTreeClient>();
window_service_client_ =
Shell::Get()
->window_service_owner()
->window_service()
->CreateWindowServiceClient(window_tree_client_.get());
window_service_client_->InitFromFactory();
client_test_helper_ =
std::make_unique<ui::ws2::WindowServiceClientTestHelper>(
window_service_client_.get());
}
// WindowServiceClientTestHelper maps 0 to a unique id. // WindowServiceClientTestHelper maps 0 to a unique id.
const ui::Id window_id = 0; std::unique_ptr<aura::Window> window(
std::unique_ptr<aura::Window> window(client_test_helper_->NewTopLevelWindow( GetWindowServiceClientTestHelper()->NewTopLevelWindow(
window_id, mojo::MapToFlatMap(std::move(properties)))); mojo::MapToFlatMap(std::move(properties))));
window->set_id(shell_window_id); window->set_id(shell_window_id);
window->Show(); window->Show();
return window; return window;
...@@ -556,6 +543,24 @@ display::Display AshTestBase::GetSecondaryDisplay() { ...@@ -556,6 +543,24 @@ display::Display AshTestBase::GetSecondaryDisplay() {
return ash_test_helper_->GetSecondaryDisplay(); return ash_test_helper_->GetSecondaryDisplay();
} }
ui::ws2::WindowServiceClientTestHelper*
AshTestBase::GetWindowServiceClientTestHelper() {
if (!window_tree_client_) {
// Lazily create a single client.
window_tree_client_ = std::make_unique<ui::ws2::TestWindowTreeClient>();
window_service_client_ =
Shell::Get()
->window_service_owner()
->window_service()
->CreateWindowServiceClient(window_tree_client_.get());
window_service_client_->InitFromFactory();
client_test_helper_ =
std::make_unique<ui::ws2::WindowServiceClientTestHelper>(
window_service_client_.get());
}
return client_test_helper_.get();
}
std::unique_ptr<aura::Window> AshTestBase::CreateTestWindowMash( std::unique_ptr<aura::Window> AshTestBase::CreateTestWindowMash(
ui::mojom::WindowType window_type, ui::mojom::WindowType window_type,
int shell_window_id, int shell_window_id,
......
...@@ -240,6 +240,9 @@ class AshTestBase : public testing::Test, ...@@ -240,6 +240,9 @@ class AshTestBase : public testing::Test,
display::Display GetPrimaryDisplay(); display::Display GetPrimaryDisplay();
display::Display GetSecondaryDisplay(); display::Display GetSecondaryDisplay();
// Returns the WindowServiceClientTestHelper, creating if necessary.
ui::ws2::WindowServiceClientTestHelper* GetWindowServiceClientTestHelper();
private: private:
std::unique_ptr<aura::Window> CreateTestWindowMash( std::unique_ptr<aura::Window> CreateTestWindowMash(
ui::mojom::WindowType window_type, ui::mojom::WindowType window_type,
......
...@@ -24,6 +24,7 @@ ...@@ -24,6 +24,7 @@
#include "base/macros.h" #include "base/macros.h"
#include "base/strings/utf_string_conversions.h" #include "base/strings/utf_string_conversions.h"
#include "services/ui/public/interfaces/window_manager.mojom.h" #include "services/ui/public/interfaces/window_manager.mojom.h"
#include "services/ui/ws2/window_properties.h"
#include "ui/aura/client/aura_constants.h" #include "ui/aura/client/aura_constants.h"
#include "ui/aura/client/transient_window_client.h" #include "ui/aura/client/transient_window_client.h"
#include "ui/aura/mus/property_converter.h" #include "ui/aura/mus/property_converter.h"
...@@ -388,6 +389,12 @@ bool NonClientFrameController::CanMinimize() const { ...@@ -388,6 +389,12 @@ bool NonClientFrameController::CanMinimize() const {
ui::mojom::kResizeBehaviorCanMinimize) != 0; ui::mojom::kResizeBehaviorCanMinimize) != 0;
} }
bool NonClientFrameController::CanActivate() const {
// kCanFocus is used for both focus and activation.
return window_ && window_->GetProperty(ui::ws2::kCanFocus) &&
views::WidgetDelegate::CanActivate();
}
bool NonClientFrameController::ShouldShowWindowTitle() const { bool NonClientFrameController::ShouldShowWindowTitle() const {
return window_ && window_->GetProperty(kWindowTitleShownKey); return window_ && window_->GetProperty(kWindowTitleShownKey);
} }
......
...@@ -88,6 +88,7 @@ class ASH_EXPORT NonClientFrameController ...@@ -88,6 +88,7 @@ class ASH_EXPORT NonClientFrameController
bool CanResize() const override; bool CanResize() const override;
bool CanMaximize() const override; bool CanMaximize() const override;
bool CanMinimize() const override; bool CanMinimize() const override;
bool CanActivate() const override;
bool ShouldShowWindowTitle() const override; bool ShouldShowWindowTitle() const override;
views::ClientView* CreateClientView(views::Widget* widget) override; views::ClientView* CreateClientView(views::Widget* widget) override;
......
...@@ -19,6 +19,8 @@ ...@@ -19,6 +19,8 @@
#include "services/ui/public/cpp/property_type_converters.h" #include "services/ui/public/cpp/property_type_converters.h"
#include "services/ui/public/interfaces/window_manager.mojom.h" #include "services/ui/public/interfaces/window_manager.mojom.h"
#include "services/ui/public/interfaces/window_tree_constants.mojom.h" #include "services/ui/public/interfaces/window_tree_constants.mojom.h"
#include "services/ui/ws2/window_delegate_impl.h"
#include "services/ui/ws2/window_properties.h"
#include "ui/aura/client/aura_constants.h" #include "ui/aura/client/aura_constants.h"
#include "ui/aura/mus/property_converter.h" #include "ui/aura/mus/property_converter.h"
#include "ui/aura/mus/property_utils.h" #include "ui/aura/mus/property_utils.h"
...@@ -170,7 +172,12 @@ aura::Window* CreateAndParentTopLevelWindowInRoot( ...@@ -170,7 +172,12 @@ aura::Window* CreateAndParentTopLevelWindowInRoot(
return renderer->widget()->GetNativeView(); return renderer->widget()->GetNativeView();
} }
aura::Window* window = new aura::Window(nullptr); // WindowDelegateImpl() deletes itself when the associated window is
// destroyed.
ui::ws2::WindowDelegateImpl* window_delegate =
new ui::ws2::WindowDelegateImpl();
aura::Window* window = new aura::Window(window_delegate);
window_delegate->set_window(window);
aura::SetWindowType(window, window_type); aura::SetWindowType(window, window_type);
window->SetProperty(aura::client::kEmbedType, window->SetProperty(aura::client::kEmbedType,
aura::client::WindowEmbedType::TOP_LEVEL_IN_WM); aura::client::WindowEmbedType::TOP_LEVEL_IN_WM);
...@@ -199,6 +206,9 @@ aura::Window* CreateAndParentTopLevelWindow( ...@@ -199,6 +206,9 @@ aura::Window* CreateAndParentTopLevelWindow(
ui::mojom::WindowType window_type, ui::mojom::WindowType window_type,
aura::PropertyConverter* property_converter, aura::PropertyConverter* property_converter,
std::map<std::string, std::vector<uint8_t>>* properties) { std::map<std::string, std::vector<uint8_t>>* properties) {
if (window_type == ui::mojom::WindowType::UNKNOWN)
return nullptr; // Clients must supply a valid type.
RootWindowController* root_window_controller = RootWindowController* root_window_controller =
GetRootWindowControllerForNewTopLevelWindow(properties); GetRootWindowControllerForNewTopLevelWindow(properties);
aura::Window* window = CreateAndParentTopLevelWindowInRoot( aura::Window* window = CreateAndParentTopLevelWindowInRoot(
...@@ -216,6 +226,7 @@ aura::Window* CreateAndParentTopLevelWindow( ...@@ -216,6 +226,7 @@ aura::Window* CreateAndParentTopLevelWindow(
properties->erase(ignored_by_shelf_iter); properties->erase(ignored_by_shelf_iter);
} }
// TODO: kFocusable_InitProperty should be removed. http://crbug.com/837713.
auto focusable_iter = auto focusable_iter =
properties->find(ui::mojom::WindowManager::kFocusable_InitProperty); properties->find(ui::mojom::WindowManager::kFocusable_InitProperty);
if (focusable_iter != properties->end()) { if (focusable_iter != properties->end()) {
...@@ -225,6 +236,7 @@ aura::Window* CreateAndParentTopLevelWindow( ...@@ -225,6 +236,7 @@ aura::Window* CreateAndParentTopLevelWindow(
window_manager->window_tree_client()->SetCanFocus(window, can_focus); window_manager->window_tree_client()->SetCanFocus(window, can_focus);
NonClientFrameController* non_client_frame_controller = NonClientFrameController* non_client_frame_controller =
NonClientFrameController::Get(window); NonClientFrameController::Get(window);
window->SetProperty(ui::ws2::kCanFocus, can_focus);
if (non_client_frame_controller) if (non_client_frame_controller)
non_client_frame_controller->set_can_activate(can_focus); non_client_frame_controller->set_can_activate(can_focus);
// No need to persist this value. // No need to persist this value.
......
...@@ -29,7 +29,8 @@ namespace ash { ...@@ -29,7 +29,8 @@ namespace ash {
class WindowManager; class WindowManager;
// Creates and parents a new top-level window and returns it. The returned // Creates and parents a new top-level window and returns it. The returned
// aura::Window is owned by its parent. // aura::Window is owned by its parent. A value of null is returned if invalid
// poarameters are supplied.
// TODO(ws): Refine this for the Window Service as-a-library (no WindowManager). // TODO(ws): Refine this for the Window Service as-a-library (no WindowManager).
ASH_EXPORT aura::Window* CreateAndParentTopLevelWindow( ASH_EXPORT aura::Window* CreateAndParentTopLevelWindow(
WindowManager* window_manager, WindowManager* window_manager,
......
// Copyright 2016 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.
#include "ash/wm/top_level_window_factory.h"
#include <stdint.h>
#include <map>
#include <string>
#include <vector>
#include "ash/shell.h"
#include "ash/test/ash_test_base.h"
#include "ash/test/ash_test_helper.h"
#include "ash/window_manager.h"
#include "ash/window_manager_service.h"
#include "ash/wm/window_properties.h"
#include "services/ui/public/cpp/property_type_converters.h"
#include "ui/aura/mus/property_converter.h"
#include "ui/aura/window.h"
#include "ui/display/screen.h"
#include "ui/gfx/geometry/rect.h"
#include "ui/gfx/test/gfx_util.h"
#include "ui/wm/core/window_util.h"
namespace ash {
namespace {
int64_t GetDisplayId(aura::Window* window) {
return display::Screen::GetScreen()->GetDisplayNearestWindow(window).id();
}
aura::Window* CreateFullscreenTestWindow(WindowManager* window_manager,
int64_t display_id) {
std::map<std::string, std::vector<uint8_t>> properties;
properties[ui::mojom::WindowManager::kShowState_Property] =
mojo::ConvertTo<std::vector<uint8_t>>(
static_cast<aura::PropertyConverter::PrimitiveType>(
ui::mojom::ShowState::FULLSCREEN));
if (display_id != display::kInvalidDisplayId) {
properties[ui::mojom::WindowManager::kDisplayId_InitProperty] =
mojo::ConvertTo<std::vector<uint8_t>>(display_id);
}
aura::Window* window = CreateAndParentTopLevelWindow(
window_manager, ui::mojom::WindowType::WINDOW,
window_manager->property_converter(), &properties);
window->Show();
return window;
}
} // namespace
using TopLevelWindowFactoryMashTest = AshTestBase;
TEST_F(TopLevelWindowFactoryMashTest, CreateFullscreenWindow) {
std::unique_ptr<aura::Window> window = CreateTestWindow();
::wm::SetWindowFullscreen(window.get(), true);
aura::Window* root_window = Shell::GetPrimaryRootWindow();
EXPECT_EQ(root_window->bounds(), window->bounds());
}
using TopLevelWindowFactoryMashWmTest = AshTestBase;
TEST_F(TopLevelWindowFactoryMashWmTest, IsWindowShownInCorrectDisplay) {
UpdateDisplay("400x400,400x400");
EXPECT_NE(GetPrimaryDisplay().id(), GetSecondaryDisplay().id());
WindowManager* window_manager =
ash_test_helper()->window_manager_service()->window_manager();
std::unique_ptr<aura::Window> window_primary_display(
CreateFullscreenTestWindow(window_manager, GetPrimaryDisplay().id()));
std::unique_ptr<aura::Window> window_secondary_display(
CreateFullscreenTestWindow(window_manager, GetSecondaryDisplay().id()));
EXPECT_EQ(GetPrimaryDisplay().id(),
GetDisplayId(window_primary_display.get()));
EXPECT_EQ(GetSecondaryDisplay().id(),
GetDisplayId(window_secondary_display.get()));
}
using TopLevelWindowFactoryMashTest2 = AshTestBase;
TEST_F(TopLevelWindowFactoryMashTest2, TopLevelNotShownOnCreate) {
std::map<std::string, std::vector<uint8_t>> properties;
auto* window_manager =
ash_test_helper()->window_manager_service()->window_manager();
std::unique_ptr<aura::Window> window(CreateAndParentTopLevelWindow(
window_manager, ui::mojom::WindowType::WINDOW,
window_manager->property_converter(), &properties));
ASSERT_TRUE(window);
EXPECT_FALSE(window->IsVisible());
}
TEST_F(TopLevelWindowFactoryMashTest2, CreateTopLevelWindow) {
const gfx::Rect bounds(1, 2, 124, 345);
std::map<std::string, std::vector<uint8_t>> properties;
properties[ui::mojom::WindowManager::kBounds_InitProperty] =
mojo::ConvertTo<std::vector<uint8_t>>(bounds);
properties[ui::mojom::WindowManager::kResizeBehavior_Property] =
mojo::ConvertTo<std::vector<uint8_t>>(
static_cast<aura::PropertyConverter::PrimitiveType>(
ui::mojom::kResizeBehaviorCanResize |
ui::mojom::kResizeBehaviorCanMaximize |
ui::mojom::kResizeBehaviorCanMinimize));
WindowManager* window_manager =
ash_test_helper()->window_manager_service()->window_manager();
// |window| is owned by its parent.
aura::Window* window = CreateAndParentTopLevelWindow(
window_manager, ui::mojom::WindowType::WINDOW,
window_manager->property_converter(), &properties);
ASSERT_TRUE(window->parent());
EXPECT_EQ(kShellWindowId_DefaultContainer, window->parent()->id());
EXPECT_EQ(bounds, window->bounds());
EXPECT_EQ(WidgetCreationType::FOR_CLIENT,
window->GetProperty(kWidgetCreationTypeKey));
}
} // namespace ash
...@@ -16,7 +16,9 @@ ...@@ -16,7 +16,9 @@
#include "ash/window_manager.h" #include "ash/window_manager.h"
#include "ash/window_manager_service.h" #include "ash/window_manager_service.h"
#include "ash/wm/window_properties.h" #include "ash/wm/window_properties.h"
#include "mojo/public/cpp/bindings/map.h"
#include "services/ui/public/cpp/property_type_converters.h" #include "services/ui/public/cpp/property_type_converters.h"
#include "services/ui/ws2/window_service_client_test_helper.h"
#include "ui/aura/mus/property_converter.h" #include "ui/aura/mus/property_converter.h"
#include "ui/aura/window.h" #include "ui/aura/window.h"
#include "ui/display/screen.h" #include "ui/display/screen.h"
...@@ -32,27 +34,36 @@ int64_t GetDisplayId(aura::Window* window) { ...@@ -32,27 +34,36 @@ int64_t GetDisplayId(aura::Window* window) {
return display::Screen::GetScreen()->GetDisplayNearestWindow(window).id(); return display::Screen::GetScreen()->GetDisplayNearestWindow(window).id();
} }
aura::Window* CreateFullscreenTestWindow(WindowManager* window_manager,
int64_t display_id) {
std::map<std::string, std::vector<uint8_t>> properties;
properties[ui::mojom::WindowManager::kShowState_Property] =
mojo::ConvertTo<std::vector<uint8_t>>(
static_cast<aura::PropertyConverter::PrimitiveType>(
ui::mojom::ShowState::FULLSCREEN));
if (display_id != display::kInvalidDisplayId) {
properties[ui::mojom::WindowManager::kDisplayId_InitProperty] =
mojo::ConvertTo<std::vector<uint8_t>>(display_id);
}
aura::Window* window = CreateAndParentTopLevelWindow(
window_manager, ui::mojom::WindowType::WINDOW,
window_manager->property_converter(), &properties);
window->Show();
return window;
}
} // namespace } // namespace
using TopLevelWindowFactoryTest = AshTestBase; class TopLevelWindowFactoryTest : public AshTestBase {
public:
TopLevelWindowFactoryTest() = default;
~TopLevelWindowFactoryTest() override = default;
aura::Window* CreateFullscreenTestWindow(int64_t display_id) {
std::map<std::string, std::vector<uint8_t>> properties;
properties[ui::mojom::WindowManager::kShowState_Property] =
mojo::ConvertTo<std::vector<uint8_t>>(
static_cast<aura::PropertyConverter::PrimitiveType>(
ui::mojom::ShowState::FULLSCREEN));
if (display_id != display::kInvalidDisplayId) {
properties[ui::mojom::WindowManager::kDisplayId_InitProperty] =
mojo::ConvertTo<std::vector<uint8_t>>(display_id);
}
properties[ui::mojom::WindowManager::kWindowType_InitProperty] =
mojo::ConvertTo<std::vector<uint8_t>>(
static_cast<int32_t>(ui::mojom::WindowType::WINDOW));
aura::Window* window =
GetWindowServiceClientTestHelper()->NewTopLevelWindow(
mojo::MapToFlatMap(std::move(properties)));
window->Show();
return window;
}
private:
DISALLOW_COPY_AND_ASSIGN(TopLevelWindowFactoryTest);
};
TEST_F(TopLevelWindowFactoryTest, CreateFullscreenWindow) { TEST_F(TopLevelWindowFactoryTest, CreateFullscreenWindow) {
std::unique_ptr<aura::Window> window = CreateTestWindow(); std::unique_ptr<aura::Window> window = CreateTestWindow();
...@@ -61,19 +72,14 @@ TEST_F(TopLevelWindowFactoryTest, CreateFullscreenWindow) { ...@@ -61,19 +72,14 @@ TEST_F(TopLevelWindowFactoryTest, CreateFullscreenWindow) {
EXPECT_EQ(root_window->bounds(), window->bounds()); EXPECT_EQ(root_window->bounds(), window->bounds());
} }
using TopLevelWindowFactoryWmTest = AshTestBase; TEST_F(TopLevelWindowFactoryTest, IsWindowShownInCorrectDisplay) {
TEST_F(TopLevelWindowFactoryWmTest, IsWindowShownInCorrectDisplay) {
UpdateDisplay("400x400,400x400"); UpdateDisplay("400x400,400x400");
EXPECT_NE(GetPrimaryDisplay().id(), GetSecondaryDisplay().id()); EXPECT_NE(GetPrimaryDisplay().id(), GetSecondaryDisplay().id());
WindowManager* window_manager =
ash_test_helper()->window_manager_service()->window_manager();
std::unique_ptr<aura::Window> window_primary_display( std::unique_ptr<aura::Window> window_primary_display(
CreateFullscreenTestWindow(window_manager, GetPrimaryDisplay().id())); CreateFullscreenTestWindow(GetPrimaryDisplay().id()));
std::unique_ptr<aura::Window> window_secondary_display( std::unique_ptr<aura::Window> window_secondary_display(
CreateFullscreenTestWindow(window_manager, GetSecondaryDisplay().id())); CreateFullscreenTestWindow(GetSecondaryDisplay().id()));
EXPECT_EQ(GetPrimaryDisplay().id(), EXPECT_EQ(GetPrimaryDisplay().id(),
GetDisplayId(window_primary_display.get())); GetDisplayId(window_primary_display.get()));
...@@ -81,20 +87,11 @@ TEST_F(TopLevelWindowFactoryWmTest, IsWindowShownInCorrectDisplay) { ...@@ -81,20 +87,11 @@ TEST_F(TopLevelWindowFactoryWmTest, IsWindowShownInCorrectDisplay) {
GetDisplayId(window_secondary_display.get())); GetDisplayId(window_secondary_display.get()));
} }
using TopLevelWindowFactoryAshTest = AshTestBase; TEST_F(TopLevelWindowFactoryTest, UnknownWindowTypeReturnsNull) {
EXPECT_FALSE(GetWindowServiceClientTestHelper()->NewTopLevelWindow());
TEST_F(TopLevelWindowFactoryAshTest, TopLevelNotShownOnCreate) {
std::map<std::string, std::vector<uint8_t>> properties;
auto* window_manager =
ash_test_helper()->window_manager_service()->window_manager();
std::unique_ptr<aura::Window> window(CreateAndParentTopLevelWindow(
window_manager, ui::mojom::WindowType::WINDOW,
window_manager->property_converter(), &properties));
ASSERT_TRUE(window);
EXPECT_FALSE(window->IsVisible());
} }
TEST_F(TopLevelWindowFactoryAshTest, CreateTopLevelWindow) { TEST_F(TopLevelWindowFactoryTest, CreateTopLevelWindow) {
const gfx::Rect bounds(1, 2, 124, 345); const gfx::Rect bounds(1, 2, 124, 345);
std::map<std::string, std::vector<uint8_t>> properties; std::map<std::string, std::vector<uint8_t>> properties;
properties[ui::mojom::WindowManager::kBounds_InitProperty] = properties[ui::mojom::WindowManager::kBounds_InitProperty] =
...@@ -105,17 +102,49 @@ TEST_F(TopLevelWindowFactoryAshTest, CreateTopLevelWindow) { ...@@ -105,17 +102,49 @@ TEST_F(TopLevelWindowFactoryAshTest, CreateTopLevelWindow) {
ui::mojom::kResizeBehaviorCanResize | ui::mojom::kResizeBehaviorCanResize |
ui::mojom::kResizeBehaviorCanMaximize | ui::mojom::kResizeBehaviorCanMaximize |
ui::mojom::kResizeBehaviorCanMinimize)); ui::mojom::kResizeBehaviorCanMinimize));
WindowManager* window_manager = properties[ui::mojom::WindowManager::kWindowType_InitProperty] =
ash_test_helper()->window_manager_service()->window_manager(); mojo::ConvertTo<std::vector<uint8_t>>(
// |window| is owned by its parent. static_cast<int32_t>(ui::mojom::WindowType::WINDOW));
aura::Window* window = CreateAndParentTopLevelWindow( aura::Window* window = GetWindowServiceClientTestHelper()->NewTopLevelWindow(
window_manager, ui::mojom::WindowType::WINDOW, mojo::MapToFlatMap(std::move(properties)));
window_manager->property_converter(), &properties);
ASSERT_TRUE(window->parent()); ASSERT_TRUE(window->parent());
EXPECT_EQ(kShellWindowId_DefaultContainer, window->parent()->id()); EXPECT_EQ(kShellWindowId_DefaultContainer, window->parent()->id());
EXPECT_EQ(bounds, window->bounds()); EXPECT_EQ(bounds, window->bounds());
EXPECT_EQ(WidgetCreationType::FOR_CLIENT, EXPECT_EQ(WidgetCreationType::FOR_CLIENT,
window->GetProperty(kWidgetCreationTypeKey)); window->GetProperty(kWidgetCreationTypeKey));
EXPECT_FALSE(window->IsVisible());
}
TEST_F(TopLevelWindowFactoryTest, CreateUnfocusableTopLevelWindow) {
std::map<std::string, std::vector<uint8_t>> properties;
properties[ui::mojom::WindowManager::kFocusable_InitProperty] =
mojo::ConvertTo<std::vector<uint8_t>>(false);
properties[ui::mojom::WindowManager::kWindowType_InitProperty] =
mojo::ConvertTo<std::vector<uint8_t>>(
static_cast<int32_t>(ui::mojom::WindowType::WINDOW));
aura::Window* window = GetWindowServiceClientTestHelper()->NewTopLevelWindow(
mojo::MapToFlatMap(std::move(properties)));
ASSERT_TRUE(window);
window->Show();
// The window should not be focusable as kFocusable_InitProperty was supplied
// with a value of false.
EXPECT_FALSE(window->CanFocus());
}
TEST_F(TopLevelWindowFactoryTest, CreateUnfocusablePopupWindow) {
std::map<std::string, std::vector<uint8_t>> properties;
properties[ui::mojom::WindowManager::kFocusable_InitProperty] =
mojo::ConvertTo<std::vector<uint8_t>>(false);
properties[ui::mojom::WindowManager::kWindowType_InitProperty] =
mojo::ConvertTo<std::vector<uint8_t>>(
static_cast<int32_t>(ui::mojom::WindowType::POPUP));
aura::Window* window = GetWindowServiceClientTestHelper()->NewTopLevelWindow(
mojo::MapToFlatMap(std::move(properties)));
ASSERT_TRUE(window);
window->Show();
// The window should not be focusable as kFocusable_InitProperty was supplied
// with a value of false.
EXPECT_FALSE(window->CanFocus());
} }
} // namespace ash } // namespace ash
...@@ -17,6 +17,8 @@ component("lib") { ...@@ -17,6 +17,8 @@ component("lib") {
public = [ public = [
"gpu_support.h", "gpu_support.h",
"ids.h", "ids.h",
"window_delegate_impl.h",
"window_properties.h",
"window_service.h", "window_service.h",
"window_service_client.h", "window_service_client.h",
"window_service_client_binding.h", "window_service_client_binding.h",
...@@ -41,9 +43,9 @@ component("lib") { ...@@ -41,9 +43,9 @@ component("lib") {
"screen_provider.cc", "screen_provider.cc",
"screen_provider.h", "screen_provider.h",
"window_delegate_impl.cc", "window_delegate_impl.cc",
"window_delegate_impl.h",
"window_host_frame_sink_client.cc", "window_host_frame_sink_client.cc",
"window_host_frame_sink_client.h", "window_host_frame_sink_client.h",
"window_properties.cc",
"window_service.cc", "window_service.cc",
"window_service_client.cc", "window_service_client.cc",
"window_service_client_binding.cc", "window_service_client_binding.cc",
......
...@@ -47,9 +47,6 @@ class COMPONENT_EXPORT(WINDOW_SERVICE) ClientWindow { ...@@ -47,9 +47,6 @@ class COMPONENT_EXPORT(WINDOW_SERVICE) ClientWindow {
aura::Window* window() { return window_; } aura::Window* window() { return window_; }
void set_can_focus(bool value) { can_focus_ = value; }
bool can_focus() const { return can_focus_; }
// Returns the ClientWindow associated with a window, null if not created yet. // Returns the ClientWindow associated with a window, null if not created yet.
static ClientWindow* GetMayBeNull(aura::Window* window) { static ClientWindow* GetMayBeNull(aura::Window* window) {
return const_cast<ClientWindow*>( return const_cast<ClientWindow*>(
...@@ -163,11 +160,6 @@ class COMPONENT_EXPORT(WINDOW_SERVICE) ClientWindow { ...@@ -163,11 +160,6 @@ class COMPONENT_EXPORT(WINDOW_SERVICE) ClientWindow {
// See |capture_owner_| for details. // See |capture_owner_| for details.
WindowServiceClient* focus_owner_ = nullptr; WindowServiceClient* focus_owner_ = nullptr;
// True if the window is allowed to receive focus.
// TODO(sky): provide way for client code to make use of this. It's needed
// when client code creates the top-level. http://crbug.com/837703.
bool can_focus_ = true;
base::Optional<viz::LocalSurfaceId> local_surface_id_; base::Optional<viz::LocalSurfaceId> local_surface_id_;
DISALLOW_COPY_AND_ASSIGN(ClientWindow); DISALLOW_COPY_AND_ASSIGN(ClientWindow);
......
...@@ -7,8 +7,10 @@ ...@@ -7,8 +7,10 @@
#include "services/ui/ws2/client_change.h" #include "services/ui/ws2/client_change.h"
#include "services/ui/ws2/client_change_tracker.h" #include "services/ui/ws2/client_change_tracker.h"
#include "services/ui/ws2/client_window.h" #include "services/ui/ws2/client_window.h"
#include "services/ui/ws2/window_properties.h"
#include "services/ui/ws2/window_service.h" #include "services/ui/ws2/window_service.h"
#include "services/ui/ws2/window_service_client.h" #include "services/ui/ws2/window_service_client.h"
#include "services/ui/ws2/window_service_delegate.h"
#include "ui/aura/client/focus_client.h" #include "ui/aura/client/focus_client.h"
namespace ui { namespace ui {
...@@ -63,7 +65,7 @@ bool FocusHandler::SetFocus(aura::Window* window) { ...@@ -63,7 +65,7 @@ bool FocusHandler::SetFocus(aura::Window* window) {
void FocusHandler::SetCanFocus(aura::Window* window, bool can_focus) { void FocusHandler::SetCanFocus(aura::Window* window, bool can_focus) {
if (window && (window_service_client_->IsClientCreatedWindow(window) || if (window && (window_service_client_->IsClientCreatedWindow(window) ||
window_service_client_->IsClientRootWindow(window))) { window_service_client_->IsClientRootWindow(window))) {
ClientWindow::GetMayBeNull(window)->set_can_focus(can_focus); window->SetProperty(kCanFocus, can_focus);
} else { } else {
DVLOG(1) << "SetCanFocus failed (invalid or unknown window)"; DVLOG(1) << "SetCanFocus failed (invalid or unknown window)";
} }
......
...@@ -4,7 +4,7 @@ ...@@ -4,7 +4,7 @@
#include "services/ui/ws2/window_delegate_impl.h" #include "services/ui/ws2/window_delegate_impl.h"
#include "services/ui/ws2/client_window.h" #include "services/ui/ws2/window_properties.h"
#include "ui/aura/window.h" #include "ui/aura/window.h"
#include "ui/base/cursor/cursor.h" #include "ui/base/cursor/cursor.h"
#include "ui/base/hit_test.h" #include "ui/base/hit_test.h"
...@@ -41,7 +41,7 @@ bool WindowDelegateImpl::ShouldDescendIntoChildForEventHandling( ...@@ -41,7 +41,7 @@ bool WindowDelegateImpl::ShouldDescendIntoChildForEventHandling(
} }
bool WindowDelegateImpl::CanFocus() { bool WindowDelegateImpl::CanFocus() {
return ClientWindow::GetMayBeNull(window_)->can_focus(); return window_->GetProperty(kCanFocus);
} }
void WindowDelegateImpl::OnCaptureLost() {} void WindowDelegateImpl::OnCaptureLost() {}
......
...@@ -5,6 +5,7 @@ ...@@ -5,6 +5,7 @@
#ifndef SERVICES_UI_WS2_WINDOW_DELEGATE_IMPL_H_ #ifndef SERVICES_UI_WS2_WINDOW_DELEGATE_IMPL_H_
#define SERVICES_UI_WS2_WINDOW_DELEGATE_IMPL_H_ #define SERVICES_UI_WS2_WINDOW_DELEGATE_IMPL_H_
#include "base/component_export.h"
#include "ui/aura/window_delegate.h" #include "ui/aura/window_delegate.h"
namespace ui { namespace ui {
...@@ -13,7 +14,8 @@ namespace ws2 { ...@@ -13,7 +14,8 @@ namespace ws2 {
// The aura::WindowDelegate implementation used for non-top-level windows // The aura::WindowDelegate implementation used for non-top-level windows
// created by the WindowService. // created by the WindowService.
// WindowDelegateImpl deletes itself when the associated window is deleted. // WindowDelegateImpl deletes itself when the associated window is deleted.
class WindowDelegateImpl : public aura::WindowDelegate { class COMPONENT_EXPORT(WINDOW_SERVICE) WindowDelegateImpl
: public aura::WindowDelegate {
public: public:
WindowDelegateImpl(); WindowDelegateImpl();
......
// 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.
#include "services/ui/ws2/window_properties.h"
#include "ui/aura/window.h"
namespace ui {
namespace ws2 {
DEFINE_UI_CLASS_PROPERTY_KEY(bool, kCanFocus, true);
} // namespace ws2
} // namespace ui
// 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 SERVICES_UI_WS2_WINDOW_PROPERTIES_H_
#define SERVICES_UI_WS2_WINDOW_PROPERTIES_H_
#include "base/component_export.h"
#include "ui/base/class_property.h"
namespace aura {
template <typename T>
using WindowProperty = ui::ClassProperty<T>;
} // namespace aura
namespace ui {
namespace ws2 {
// This property is set from WindowTree::SetCanFocus(). The value of this
// property influeces activation as well. In particular, if this is false and
// set on a top-level, then the top-level can not be activated.
COMPONENT_EXPORT(WINDOW_SERVICE)
extern const aura::WindowProperty<bool>* const kCanFocus;
} // namespace ws2
} // namespace ui
#endif // SERVICES_UI_WS2_WINDOW_PROPERTIES_H_
...@@ -54,6 +54,11 @@ aura::Window* WindowServiceClientTestHelper::NewTopLevelWindow( ...@@ -54,6 +54,11 @@ aura::Window* WindowServiceClientTestHelper::NewTopLevelWindow(
window_service_client_->MakeClientWindowId(transport_window_id)); window_service_client_->MakeClientWindowId(transport_window_id));
} }
aura::Window* WindowServiceClientTestHelper::NewTopLevelWindow(
const base::flat_map<std::string, std::vector<uint8_t>>& properties) {
return NewTopLevelWindow(0u, properties);
}
bool WindowServiceClientTestHelper::SetCapture(aura::Window* window) { bool WindowServiceClientTestHelper::SetCapture(aura::Window* window) {
return window_service_client_->SetCaptureImpl( return window_service_client_->SetCaptureImpl(
ClientWindowIdForWindow(window)); ClientWindowIdForWindow(window));
......
...@@ -55,6 +55,8 @@ class WindowServiceClientTestHelper { ...@@ -55,6 +55,8 @@ class WindowServiceClientTestHelper {
aura::Window* NewTopLevelWindow( aura::Window* NewTopLevelWindow(
Id transport_window_id = 0, Id transport_window_id = 0,
base::flat_map<std::string, std::vector<uint8_t>> properties = {}); base::flat_map<std::string, std::vector<uint8_t>> properties = {});
aura::Window* NewTopLevelWindow(
const base::flat_map<std::string, std::vector<uint8_t>>& properties);
bool SetCapture(aura::Window* window); bool SetCapture(aura::Window* window);
bool ReleaseCapture(aura::Window* window); bool ReleaseCapture(aura::Window* window);
bool SetWindowBounds( bool SetWindowBounds(
......
...@@ -28,6 +28,10 @@ class COMPONENT_EXPORT(WINDOW_SERVICE) WindowServiceDelegate { ...@@ -28,6 +28,10 @@ class COMPONENT_EXPORT(WINDOW_SERVICE) WindowServiceDelegate {
// A client requested a new top-level window. Implementations should create a // A client requested a new top-level window. Implementations should create a
// new window, parenting it in the appropriate container. Return null to // new window, parenting it in the appropriate container. Return null to
// reject the request. // reject the request.
// NOTE: it is recommended that when clients create a new window they use
// WindowDelegateImpl as the WindowDelegate of the Window (this must be done
// by the WindowServiceDelegate, as the Window's delegate can not be changed
// after creation).
virtual std::unique_ptr<aura::Window> NewTopLevel( virtual std::unique_ptr<aura::Window> NewTopLevel(
aura::PropertyConverter* property_converter, aura::PropertyConverter* property_converter,
const base::flat_map<std::string, std::vector<uint8_t>>& properties) = 0; const base::flat_map<std::string, std::vector<uint8_t>>& properties) = 0;
......
...@@ -249,6 +249,9 @@ ...@@ -249,6 +249,9 @@
# TODO: Needs CursorManager. http://crbug.com/631103 # TODO: Needs CursorManager. http://crbug.com/631103
-TooltipControllerTest.HideTooltipWhenCursorHidden -TooltipControllerTest.HideTooltipWhenCursorHidden
# These tests are not applicable to mash.
-TopLevelWindowFactoryTest.*
# TODO: Touch HUD. http://crbug.com/698032 # TODO: Touch HUD. http://crbug.com/698032
-TouchHudDebugTest.DualDisplays -TouchHudDebugTest.DualDisplays
-TouchHudDebugTest.Headless -TouchHudDebugTest.Headless
......
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