blob: 4daa25f4f7f8144cb71a235d9cfbb858d0fa5497 [file] [log] [blame]
ben294d04b2015-10-15 01:23:331// Copyright 2015 The Chromium Authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
Scott Violet4c79b0d2017-11-17 21:47:135#include "ash/window_manager.h"
ben294d04b2015-10-15 01:23:336
avi703dbbf2015-12-22 01:46:287#include <stdint.h>
mostynb1aaf5062016-04-04 17:56:278
xiyuan317fdbe2017-05-31 15:02:029#include <limits>
Mitsuru Oshima04b54d02017-10-09 14:22:4510#include <memory>
dchenge48600452015-12-28 02:24:5011#include <utility>
avi703dbbf2015-12-22 01:46:2812
Scott Violet4c79b0d2017-11-17 21:47:1313#include "ash/accelerators/accelerator_handler.h"
14#include "ash/accelerators/accelerator_ids.h"
Michael Wasserman625b7382017-12-13 16:34:3215#include "ash/display/window_tree_host_manager.h"
James Cookb0bf8e82017-04-09 17:01:4416#include "ash/drag_drop/drag_image_view.h"
Scott Violet4c79b0d2017-11-17 21:47:1317#include "ash/event_matcher_util.h"
Michael Wasserman625b7382017-12-13 16:34:3218#include "ash/host/ash_window_tree_host.h"
sky494c6cbd2017-03-27 20:57:4819#include "ash/public/cpp/config.h"
erg19e1e2002017-02-24 23:24:1220#include "ash/public/cpp/shelf_types.h"
penghuange52cb192017-04-05 00:54:4021#include "ash/public/cpp/window_pin_type.h"
msw8329bfa32017-02-02 19:34:5322#include "ash/public/cpp/window_properties.h"
Elliot Glaysher47f02ca2017-09-23 02:08:0423#include "ash/public/cpp/window_state_type.h"
Elliot Glaysher247b7632017-10-25 03:02:0924#include "ash/public/interfaces/window_actions.mojom.h"
penghuange52cb192017-04-05 00:54:4025#include "ash/public/interfaces/window_pin_type.mojom.h"
Elliot Glaysherc1bfc6f92017-11-01 20:44:4826#include "ash/public/interfaces/window_properties.mojom.h"
Elliot Glaysher47f02ca2017-09-23 02:08:0427#include "ash/public/interfaces/window_state_type.mojom.h"
skyb6643832017-01-11 22:08:4528#include "ash/root_window_controller.h"
sky8a8ffd22017-01-19 15:55:2929#include "ash/root_window_settings.h"
James Cookb0bf8e82017-04-09 17:01:4430#include "ash/session/session_controller.h"
sky00f98a372017-01-11 06:03:4931#include "ash/shell.h"
Scott Violet4c79b0d2017-11-17 21:47:1332#include "ash/shell_delegate_mus.h"
skyabcae812017-01-18 17:01:3433#include "ash/shell_init_params.h"
Scott Violet4c79b0d2017-11-17 21:47:1334#include "ash/shell_port_mash.h"
35#include "ash/shell_port_mus.h"
Peng Huang87a65cd2017-10-06 15:21:4736#include "ash/wayland/wayland_server_controller.h"
skyfcf18b52016-12-06 03:53:5137#include "ash/wm/ash_focus_rules.h"
Scott Violet4c79b0d2017-11-17 21:47:1338#include "ash/wm/move_event_handler.h"
39#include "ash/wm/non_client_frame_controller.h"
40#include "ash/wm/property_util.h"
Elliot Glaysher247b7632017-10-25 03:02:0941#include "ash/wm/tablet_mode/tablet_mode_controller.h"
Scott Violet4c79b0d2017-11-17 21:47:1342#include "ash/wm/top_level_window_factory.h"
Elliot Glaysherb372ee52017-11-09 19:34:1343#include "ash/wm/window_properties.h"
James Cookb0bf8e82017-04-09 17:01:4444#include "ash/wm/window_state.h"
kylechara06c6ea42016-10-21 17:35:0445#include "services/service_manager/public/cpp/connector.h"
thanhph62cbfb832016-12-03 01:08:0346#include "services/ui/common/accelerator_util.h"
ben6b0453d12016-07-02 04:27:1947#include "services/ui/common/types.h"
sky83b1bb12017-04-24 20:29:2848#include "services/ui/public/cpp/input_devices/input_device_client.h"
ben6b0453d12016-07-02 04:27:1949#include "services/ui/public/cpp/property_type_converters.h"
ben06065b62016-11-16 06:29:5050#include "services/ui/public/interfaces/constants.mojom.h"
ben6b0453d12016-07-02 04:27:1951#include "services/ui/public/interfaces/window_manager.mojom.h"
moshayedi92b3b482017-03-21 20:27:4652#include "ui/aura/client/aura_constants.h"
skyfcf18b52016-12-06 03:53:5153#include "ui/aura/client/window_parenting_client.h"
54#include "ui/aura/env.h"
riajiangf6a5c392017-02-02 17:37:4855#include "ui/aura/mus/capture_synchronizer.h"
skyfcf18b52016-12-06 03:53:5156#include "ui/aura/mus/property_converter.h"
57#include "ui/aura/mus/window_tree_client.h"
58#include "ui/aura/mus/window_tree_host_mus.h"
59#include "ui/aura/window.h"
kylixrd61e45cf2017-01-30 19:52:5360#include "ui/base/class_property.h"
erg6ed29f62016-07-08 20:10:4061#include "ui/base/hit_test.h"
sky3e56abe2016-09-29 19:38:2162#include "ui/display/display_observer.h"
moshayedib1637da12016-06-13 15:32:4863#include "ui/events/mojo/event.mojom.h"
skya4477cb32017-01-04 05:04:3564#include "ui/views/mus/pointer_watcher_event_router.h"
skyfcf18b52016-12-06 03:53:5165#include "ui/wm/core/capture_controller.h"
sky5c71eb342017-02-15 19:39:2566#include "ui/wm/core/shadow_types.h"
Scott Violet0f803d052017-08-04 18:24:4267#include "ui/wm/core/window_animations.h"
skyfcf18b52016-12-06 03:53:5168#include "ui/wm/core/wm_state.h"
skyabcae812017-01-18 17:01:3469#include "ui/wm/public/activation_client.h"
skyd4ca12f2015-10-28 18:22:2670
msw5e048a72016-09-07 18:55:3071namespace ash {
skyfcf18b52016-12-06 03:53:5172
ergb9401c492017-03-24 17:14:1273struct WindowManager::DragState {
74 // An image representation of the contents of the current drag and drop
75 // clipboard.
76 std::unique_ptr<ash::DragImageView> view;
77
78 // The cursor offset of the dragged item.
79 gfx::Vector2d image_offset;
80};
81
skyfcf18b52016-12-06 03:53:5182// TODO: need to register OSExchangeDataProviderMus. http://crbug.com/665077.
sky494c6cbd2017-03-27 20:57:4883WindowManager::WindowManager(service_manager::Connector* connector,
skycfaad892017-04-28 20:52:5884 Config config,
85 bool show_primary_host_on_connect)
skyfcf18b52016-12-06 03:53:5186 : connector_(connector),
sky494c6cbd2017-03-27 20:57:4887 config_(config),
skycfaad892017-04-28 20:52:5888 show_primary_host_on_connect_(show_primary_host_on_connect),
Mitsuru Oshima04b54d02017-10-09 14:22:4589 wm_state_(std::make_unique<::wm::WMState>()),
90 property_converter_(std::make_unique<aura::PropertyConverter>()) {
mswe6975c72017-05-16 23:07:0591 property_converter_->RegisterPrimitiveProperty(
Elliot Glaysherb372ee52017-11-09 19:34:1392 kCanConsumeSystemKeysKey, ash::mojom::kCanConsumeSystemKeys_Property,
93 aura::PropertyConverter::CreateAcceptAnyValueCallback());
94 property_converter_->RegisterPrimitiveProperty(
James Cook2eed9872017-11-14 21:08:5495 aura::client::kDrawAttentionKey,
96 ui::mojom::WindowManager::kDrawAttention_Property,
97 aura::PropertyConverter::CreateAcceptAnyValueCallback());
98 property_converter_->RegisterPrimitiveProperty(
erg19e1e2002017-02-24 23:24:1299 kPanelAttachedKey, ui::mojom::WindowManager::kPanelAttached_Property,
100 aura::PropertyConverter::CreateAcceptAnyValueCallback());
mswe6975c72017-05-16 23:07:05101 property_converter_->RegisterPrimitiveProperty(
sky50261ac2016-12-07 17:14:52102 kRenderTitleAreaProperty,
erg19e1e2002017-02-24 23:24:12103 ui::mojom::WindowManager::kRenderParentTitleArea_Property,
104 aura::PropertyConverter::CreateAcceptAnyValueCallback());
mswe6975c72017-05-16 23:07:05105 property_converter_->RegisterPrimitiveProperty(
erg19e1e2002017-02-24 23:24:12106 kShelfItemTypeKey, ui::mojom::WindowManager::kShelfItemType_Property,
107 base::Bind(&IsValidShelfItemType));
mswe6975c72017-05-16 23:07:05108 property_converter_->RegisterPrimitiveProperty(
sky5c71eb342017-02-15 19:39:25109 ::wm::kShadowElevationKey,
erg19e1e2002017-02-24 23:24:12110 ui::mojom::WindowManager::kShadowElevation_Property,
Trent Apted280f4ff2018-02-07 07:11:53111 aura::PropertyConverter::CreateAcceptAnyValueCallback());
mswe6975c72017-05-16 23:07:05112 property_converter_->RegisterPrimitiveProperty(
Elliot Glaysher47f02ca2017-09-23 02:08:04113 kWindowStateTypeKey, mojom::kWindowStateType_Property,
114 base::Bind(&ash::IsValidWindowStateType));
115 property_converter_->RegisterPrimitiveProperty(
mswe6975c72017-05-16 23:07:05116 kWindowPinTypeKey, ash::mojom::kWindowPinType_Property,
117 base::Bind(&ash::IsValidWindowPinType));
Elliot Glaysherc1bfc6f92017-11-01 20:44:48118 property_converter_->RegisterPrimitiveProperty(
119 kWindowPositionManagedTypeKey,
120 ash::mojom::kWindowPositionManaged_Property,
121 aura::PropertyConverter::CreateAcceptAnyValueCallback());
mswe6975c72017-05-16 23:07:05122 property_converter_->RegisterStringProperty(
123 kShelfIDKey, ui::mojom::WindowManager::kShelfID_Property);
Maksim Sisova00b71f2018-02-22 10:43:24124 property_converter_->RegisterPrimitiveProperty(
125 kRestoreBoundsOverrideKey, ash::mojom::kRestoreBoundsOverride_Property,
126 aura::PropertyConverter::CreateAcceptAnyValueCallback());
127 property_converter_->RegisterPrimitiveProperty(
128 kRestoreWindowStateTypeOverrideKey,
129 ash::mojom::kRestoreWindowStateTypeOverride_Property,
130 base::BindRepeating(&ash::IsValidWindowStateType));
skyfcf18b52016-12-06 03:53:51131}
sadrul0a064b92016-04-22 17:36:50132
sky1cc69662016-06-17 23:59:35133WindowManager::~WindowManager() {
sky9636bee2016-09-06 18:09:32134 Shutdown();
sky00f98a372017-01-11 06:03:49135 ash::Shell::set_window_tree_client(nullptr);
skya8b222f2017-01-12 15:47:13136 ash::Shell::set_window_manager_client(nullptr);
sky1cc69662016-06-17 23:59:35137}
sky82083712016-06-06 18:17:32138
sky9636bee2016-09-06 18:09:32139void WindowManager::Init(
skyfcf18b52016-12-06 03:53:51140 std::unique_ptr<aura::WindowTreeClient> window_tree_client,
sky494c6cbd2017-03-27 20:57:48141 std::unique_ptr<ShellDelegate> shell_delegate) {
sky83b1bb12017-04-24 20:29:28142 // Only create InputDeviceClient in MASH mode. For MUS mode WindowManager is
143 // created by chrome, which creates InputDeviceClient.
Scott Violet361833fb2017-06-21 22:25:20144 if (config_ == Config::MASH) {
Mitsuru Oshima04b54d02017-10-09 14:22:45145 input_device_client_ = std::make_unique<ui::InputDeviceClient>();
Elliot Glaysher8e6b8462017-07-27 17:37:12146
147 // |connector_| can be nullptr in tests.
148 if (connector_) {
149 ui::mojom::InputDeviceServerPtr server;
150 connector_->BindInterface(ui::mojom::kServiceName, &server);
151 input_device_client_->Connect(std::move(server));
152 }
Scott Violet361833fb2017-06-21 22:25:20153 } else {
154 // In Config::MUS ash handles all drag and drop.
155 window_tree_client->DisableDragDropClient();
156 }
sky83b1bb12017-04-24 20:29:28157
skyfcf18b52016-12-06 03:53:51158 DCHECK(window_manager_client_);
sky1cc69662016-06-17 23:59:35159 DCHECK(!window_tree_client_);
sky9636bee2016-09-06 18:09:32160 window_tree_client_ = std::move(window_tree_client);
sky82083712016-06-06 18:17:32161
sky00f98a372017-01-11 06:03:49162 DCHECK_EQ(nullptr, ash::Shell::window_tree_client());
163 ash::Shell::set_window_tree_client(window_tree_client_.get());
164
James Cook3d788f52017-10-28 00:07:54165 // TODO(jamescook): Maybe not needed in Config::MUS?
skyfcf18b52016-12-06 03:53:51166 pointer_watcher_event_router_ =
Mitsuru Oshima04b54d02017-10-09 14:22:45167 std::make_unique<views::PointerWatcherEventRouter>(
skyfcf18b52016-12-06 03:53:51168 window_tree_client_.get());
sky1cbe94862016-08-12 19:48:17169
riajiangf6a5c392017-02-02 17:37:48170 // Notify PointerWatcherEventRouter and CaptureSynchronizer that the capture
171 // client has been set.
172 aura::client::CaptureClient* capture_client = wm_state_->capture_controller();
173 pointer_watcher_event_router_->AttachToCaptureClient(capture_client);
174 window_tree_client_->capture_synchronizer()->AttachToCaptureClient(
175 capture_client);
sky494c6cbd2017-03-27 20:57:48176
177 if (shell_delegate)
178 shell_delegate_ = std::move(shell_delegate);
Elliot Glaysherce740242017-07-17 19:09:17179
180 InitCursorOnKeyList();
sky494c6cbd2017-03-27 20:57:48181}
182
sky01c007b2017-04-28 15:48:46183void WindowManager::SetLostConnectionCallback(base::OnceClosure closure) {
184 lost_connection_callback_ = std::move(closure);
185}
186
sky494c6cbd2017-03-27 20:57:48187bool WindowManager::WaitForInitialDisplays() {
188 return window_manager_client_->WaitForInitialDisplays();
sky1cc69662016-06-17 23:59:35189}
190
sky853669a2016-07-22 18:43:12191bool WindowManager::GetNextAcceleratorNamespaceId(uint16_t* id) {
192 if (accelerator_handlers_.size() == std::numeric_limits<uint16_t>::max())
193 return false;
194 while (accelerator_handlers_.count(next_accelerator_namespace_id_) > 0)
195 ++next_accelerator_namespace_id_;
196 *id = next_accelerator_namespace_id_;
197 ++next_accelerator_namespace_id_;
198 return true;
199}
200
201void WindowManager::AddAcceleratorHandler(uint16_t id_namespace,
202 AcceleratorHandler* handler) {
203 DCHECK_EQ(0u, accelerator_handlers_.count(id_namespace));
204 accelerator_handlers_[id_namespace] = handler;
205}
206
207void WindowManager::RemoveAcceleratorHandler(uint16_t id_namespace) {
208 accelerator_handlers_.erase(id_namespace);
209}
210
kylechara06c6ea42016-10-21 17:35:04211display::mojom::DisplayController* WindowManager::GetDisplayController() {
212 return display_controller_ ? display_controller_.get() : nullptr;
213}
214
Scott Violet596bb46342017-06-21 14:43:13215void WindowManager::CreateShell() {
skyabcae812017-01-18 17:01:34216 DCHECK(!created_shell_);
217 created_shell_ = true;
218 ShellInitParams init_params;
James Cook3d788f52017-10-28 00:07:54219 if (config_ == Config::MUS) {
Scott Violetc8a1c6c2017-11-29 23:17:36220 init_params.shell_port = std::make_unique<ShellPortMus>(this);
James Cook3d788f52017-10-28 00:07:54221 } else {
Scott Violetc8a1c6c2017-11-29 23:17:36222 init_params.shell_port = std::make_unique<ShellPortMash>(
223 this, pointer_watcher_event_router_.get());
James Cook3d788f52017-10-28 00:07:54224 }
Scott Violetc8a1c6c2017-11-29 23:17:36225 init_params.delegate = shell_delegate_
226 ? std::move(shell_delegate_)
227 : std::make_unique<ShellDelegateMus>(connector_);
228 Shell::CreateInstance(std::move(init_params));
skyabcae812017-01-18 17:01:34229}
230
Elliot Glaysherce740242017-07-17 19:09:17231void WindowManager::InitCursorOnKeyList() {
232 DCHECK(window_manager_client_);
233 if (config_ == Config::MASH) {
234 // In Mash, we build a list of keys and send them to the window
235 // server. This controls which keys *don't* hide the cursors.
236
237 // TODO(erg): This needs to also check the case of the accessibility
238 // keyboard being shown, since clicking a key on the keyboard shouldn't
239 // hide the cursor.
240 std::vector<ui::mojom::EventMatcherPtr> cursor_key_list;
241 cursor_key_list.push_back(BuildKeyReleaseMatcher());
242 cursor_key_list.push_back(BuildAltMatcher());
243 cursor_key_list.push_back(BuildControlMatcher());
244
245 BuildKeyMatcherRange(ui::mojom::KeyboardCode::F1,
246 ui::mojom::KeyboardCode::F24, &cursor_key_list);
247 BuildKeyMatcherRange(ui::mojom::KeyboardCode::BROWSER_BACK,
248 ui::mojom::KeyboardCode::MEDIA_LAUNCH_APP2,
249 &cursor_key_list);
250 BuildKeyMatcherList(
251 {ui::mojom::KeyboardCode::SHIFT, ui::mojom::KeyboardCode::CONTROL,
252 ui::mojom::KeyboardCode::MENU,
253 ui::mojom::KeyboardCode::LWIN, // Search key == VKEY_LWIN.
254 ui::mojom::KeyboardCode::WLAN, ui::mojom::KeyboardCode::POWER,
255 ui::mojom::KeyboardCode::BRIGHTNESS_DOWN,
256 ui::mojom::KeyboardCode::BRIGHTNESS_UP,
257 ui::mojom::KeyboardCode::KBD_BRIGHTNESS_DOWN,
258 ui::mojom::KeyboardCode::KBD_BRIGHTNESS_UP},
259 &cursor_key_list);
260
261 window_manager_client_->SetKeyEventsThatDontHideCursor(
262 std::move(cursor_key_list));
263 }
264}
265
sky27717092017-05-26 19:04:06266void WindowManager::InstallFrameDecorationValues() {
267 ui::mojom::FrameDecorationValuesPtr frame_decoration_values =
268 ui::mojom::FrameDecorationValues::New();
269 const gfx::Insets client_area_insets =
270 NonClientFrameController::GetPreferredClientAreaInsets();
271 frame_decoration_values->normal_client_area_insets = client_area_insets;
272 frame_decoration_values->maximized_client_area_insets = client_area_insets;
273 frame_decoration_values->max_title_bar_button_width =
274 NonClientFrameController::GetMaxTitleBarButtonWidth();
275 window_manager_client_->SetFrameDecorationValues(
276 std::move(frame_decoration_values));
277}
278
sky9636bee2016-09-06 18:09:32279void WindowManager::Shutdown() {
280 if (!window_tree_client_)
281 return;
282
riajiangf6a5c392017-02-02 17:37:48283 aura::client::CaptureClient* capture_client = wm_state_->capture_controller();
284 pointer_watcher_event_router_->DetachFromCaptureClient(capture_client);
285 window_tree_client_->capture_synchronizer()->DetachFromCaptureClient(
286 capture_client);
287
skyabcae812017-01-18 17:01:34288 Shell::DeleteInstance();
sky9636bee2016-09-06 18:09:32289
sky9636bee2016-09-06 18:09:32290 pointer_watcher_event_router_.reset();
291
292 window_tree_client_.reset();
293 window_manager_client_ = nullptr;
294}
295
skyfcf18b52016-12-06 03:53:51296void WindowManager::OnEmbed(
297 std::unique_ptr<aura::WindowTreeHostMus> window_tree_host) {
sky1cc69662016-06-17 23:59:35298 // WindowManager should never see this, instead OnWmNewDisplay() is called.
299 NOTREACHED();
300}
301
sky247a6062016-12-08 16:45:14302void WindowManager::OnEmbedRootDestroyed(
303 aura::WindowTreeHostMus* window_tree_host) {
sky9636bee2016-09-06 18:09:32304 // WindowManager should never see this.
305 NOTREACHED();
306}
sky1cc69662016-06-17 23:59:35307
skyfcf18b52016-12-06 03:53:51308void WindowManager::OnLostConnection(aura::WindowTreeClient* client) {
sky9636bee2016-09-06 18:09:32309 DCHECK_EQ(client, window_tree_client_.get());
sky01c007b2017-04-28 15:48:46310 if (!lost_connection_callback_.is_null()) {
311 base::ResetAndReturn(&lost_connection_callback_).Run();
312 return;
313 }
sky9636bee2016-09-06 18:09:32314 Shutdown();
Scott Violet6eda33e2017-11-14 23:53:37315 // TODO(sky): this case should trigger shutting down WindowManagerService too.
sky1cc69662016-06-17 23:59:35316}
317
riajiang13661fe2016-08-09 17:51:57318void WindowManager::OnPointerEventObserved(const ui::PointerEvent& event,
skyfcf18b52016-12-06 03:53:51319 aura::Window* target) {
Elliot Glaysherd26fedc2017-12-11 19:16:37320 pointer_watcher_event_router_->OnPointerEventObserved(event, target);
sadruleaa1be22015-11-30 23:30:48321}
322
skyfcf18b52016-12-06 03:53:51323aura::PropertyConverter* WindowManager::GetPropertyConverter() {
324 return property_converter_.get();
325}
326
327void WindowManager::SetWindowManagerClient(aura::WindowManagerClient* client) {
skyf5ece4e2016-01-26 19:40:36328 window_manager_client_ = client;
skya8b222f2017-01-12 15:47:13329 ash::Shell::set_window_manager_client(client);
skybbcf04eb2015-10-15 23:07:56330}
skyd4ca12f2015-10-28 18:22:26331
skycfaad892017-04-28 20:52:58332void WindowManager::OnWmConnected() {
Scott Violeteff431f92017-08-15 23:00:47333 // InstallFrameDecorationValues() must be called before the shell is created,
334 // otherwise Mus attempts to notify clients with no frame decorations, which
335 // triggers validation errors.
336 InstallFrameDecorationValues();
Scott Violet596bb46342017-06-21 14:43:13337 CreateShell();
skycfaad892017-04-28 20:52:58338 if (show_primary_host_on_connect_)
339 Shell::GetPrimaryRootWindow()->GetHost()->Show();
Peng Huang87a65cd2017-10-06 15:21:47340
341 // We only create controller in the ash process for mash.
342 if (Shell::GetAshConfig() == Config::MASH)
343 wayland_server_controller_ = WaylandServerController::CreateIfNecessary();
skycfaad892017-04-28 20:52:58344}
skyfef30212017-04-19 00:41:23345
Sadrul Habib Chowdhury55cd40ff2017-11-28 17:18:01346void WindowManager::OnWmAcceleratedWidgetAvailableForDisplay(
347 int64_t display_id,
348 gfx::AcceleratedWidget widget) {
Michael Wasserman625b7382017-12-13 16:34:32349 WindowTreeHostManager* manager = Shell::Get()->window_tree_host_manager();
350 AshWindowTreeHost* host =
351 manager->GetAshWindowTreeHostForDisplayId(display_id);
352 // The display may have been destroyed before getting this async callback.
353 if (host && host->AsWindowTreeHost()) {
354 static_cast<aura::WindowTreeHostMus*>(host->AsWindowTreeHost())
355 ->OverrideAcceleratedWidget(widget);
Sadrul Habib Chowdhury55cd40ff2017-11-28 17:18:01356 }
357}
358
fsamuel69875b52017-03-27 23:15:19359void WindowManager::OnWmSetBounds(aura::Window* window,
360 const gfx::Rect& bounds) {
sky383d818f2016-05-19 22:34:02361 // TODO(sky): this indirectly sets bounds, which is against what
362 // OnWmSetBounds() recommends doing. Remove that restriction, or fix this.
varkhac8621dd2017-05-31 19:09:01363 window->SetBounds(bounds);
sky6905d4c2015-11-26 01:53:21364}
365
sky7a35dfa2016-02-01 21:37:28366bool WindowManager::OnWmSetProperty(
skyfcf18b52016-12-06 03:53:51367 aura::Window* window,
sky6905d4c2015-11-26 01:53:21368 const std::string& name,
mostynb1aaf5062016-04-04 17:56:27369 std::unique_ptr<std::vector<uint8_t>>* new_data) {
sky5c71eb342017-02-15 19:39:25370 if (property_converter_->IsTransportNameRegistered(name))
371 return true;
372 DVLOG(1) << "unknown property changed, ignoring " << name;
373 return false;
sky6905d4c2015-11-26 01:53:21374}
375
moshayedi92b3b482017-03-21 20:27:46376void WindowManager::OnWmSetModalType(aura::Window* window, ui::ModalType type) {
377 ui::ModalType old_type = window->GetProperty(aura::client::kModalKey);
378 if (type == old_type)
379 return;
380
381 window->SetProperty(aura::client::kModalKey, type);
Scott Violet65326efd2017-07-21 00:09:56382 // Assume the client has positioned the window in the right container and
383 // don't attempt to change the parent. This is currently true for Chrome
384 // code, but likely there should be checks. Adding checks is complicated by
385 // the fact that assumptions in GetSystemModalContainer() are not always
386 // valid for Chrome code. In particular Chrome code may create system modal
387 // dialogs without a transient parent that Chrome wants shown on the lock
388 // screen.
moshayedi92b3b482017-03-21 20:27:46389}
390
moshayedic17142e2017-01-26 21:50:39391void WindowManager::OnWmSetCanFocus(aura::Window* window, bool can_focus) {
392 NonClientFrameController* non_client_frame_controller =
393 NonClientFrameController::Get(window);
394 if (non_client_frame_controller)
395 non_client_frame_controller->set_can_activate(can_focus);
396}
397
skyfcf18b52016-12-06 03:53:51398aura::Window* WindowManager::OnWmCreateTopLevelWindow(
399 ui::mojom::WindowType window_type,
skyadfb92372016-01-07 17:34:24400 std::map<std::string, std::vector<uint8_t>>* properties) {
skyb87f0a12016-12-06 20:45:49401 if (window_type == ui::mojom::WindowType::UNKNOWN) {
402 LOG(WARNING) << "Request to create top level of unknown type, failing";
403 return nullptr;
404 }
405
sky8a8ffd22017-01-19 15:55:29406 return CreateAndParentTopLevelWindow(this, window_type, properties);
skyadfb92372016-01-07 17:34:24407}
408
ben3d0b3182016-05-25 20:37:14409void WindowManager::OnWmClientJankinessChanged(
skyfcf18b52016-12-06 03:53:51410 const std::set<aura::Window*>& client_windows,
ben3d0b3182016-05-25 20:37:14411 bool janky) {
vmpstreb900a12016-06-29 02:22:28412 for (auto* window : client_windows)
skyfcf18b52016-12-06 03:53:51413 window->SetProperty(kWindowIsJanky, janky);
ben3d0b3182016-05-25 20:37:14414}
415
ergb9401c492017-03-24 17:14:12416void WindowManager::OnWmBuildDragImage(const gfx::Point& screen_location,
417 const SkBitmap& drag_image,
418 const gfx::Vector2d& drag_image_offset,
419 ui::mojom::PointerKind source) {
420 if (drag_image.isNull())
421 return;
422
423 // TODO(erg): Get the right display for this drag image. Right now, none of
424 // the drag drop code is multidisplay aware.
Scott Violet596bb46342017-06-21 14:43:13425 aura::Window* root_window = Shell::GetPrimaryRootWindow();
ergb9401c492017-03-24 17:14:12426
427 // TODO(erg): SkBitmap is the wrong data type for the drag image; we should
428 // be passing ImageSkias once http://crbug.com/655874 is implemented.
429
ergb9401c492017-03-24 17:14:12430 ui::DragDropTypes::DragEventSource ui_source =
431 source == ui::mojom::PointerKind::MOUSE
432 ? ui::DragDropTypes::DRAG_EVENT_SOURCE_MOUSE
433 : ui::DragDropTypes::DRAG_EVENT_SOURCE_TOUCH;
434 std::unique_ptr<DragImageView> drag_view =
Mitsuru Oshima04b54d02017-10-09 14:22:45435 std::make_unique<DragImageView>(root_window, ui_source);
ergb9401c492017-03-24 17:14:12436 drag_view->SetImage(gfx::ImageSkia::CreateFrom1xBitmap(drag_image));
437 gfx::Size size = drag_view->GetPreferredSize();
438 gfx::Rect drag_image_bounds(screen_location - drag_image_offset, size);
439 drag_view->SetBoundsInScreen(drag_image_bounds);
440 drag_view->SetWidgetVisible(true);
441
Mitsuru Oshima04b54d02017-10-09 14:22:45442 drag_state_ = std::make_unique<DragState>();
ergb9401c492017-03-24 17:14:12443 drag_state_->view = std::move(drag_view);
444 drag_state_->image_offset = drag_image_offset;
445}
446
447void WindowManager::OnWmMoveDragImage(const gfx::Point& screen_location) {
448 if (drag_state_) {
449 drag_state_->view->SetScreenPosition(screen_location -
450 drag_state_->image_offset);
451 }
452}
453
454void WindowManager::OnWmDestroyDragImage() {
455 drag_state_.reset();
456}
457
skyfcf18b52016-12-06 03:53:51458void WindowManager::OnWmWillCreateDisplay(const display::Display& display) {
Scott Violet596bb46342017-06-21 14:43:13459 // Ash connects such that |automatically_create_display_roots| is false, which
460 // means this should never be hit.
461 NOTREACHED();
skyffa8df22016-02-02 05:47:34462}
463
skyfcf18b52016-12-06 03:53:51464void WindowManager::OnWmNewDisplay(
465 std::unique_ptr<aura::WindowTreeHostMus> window_tree_host,
466 const display::Display& display) {
Scott Violet596bb46342017-06-21 14:43:13467 // Ash connects such that |automatically_create_display_roots| is false, which
468 // means this should never be hit.
469 NOTREACHED();
skyfcf18b52016-12-06 03:53:51470}
471
472void WindowManager::OnWmDisplayRemoved(
473 aura::WindowTreeHostMus* window_tree_host) {
Scott Violet596bb46342017-06-21 14:43:13474 // Ash connects such that |automatically_create_display_roots| is false, which
475 // means this should never be hit.
476 NOTREACHED();
sky54ff2cce2016-09-20 02:44:41477}
478
kylechara06c6ea42016-10-21 17:35:04479void WindowManager::OnWmDisplayModified(const display::Display& display) {
Scott Violet596bb46342017-06-21 14:43:13480 // TODO(sky): this shouldn't be called as we're passing false for
481 // |automatically_create_display_roots|, but it currently is. Update mus.
kylechara06c6ea42016-10-21 17:35:04482}
483
erg6d0134e2016-07-07 00:41:13484void WindowManager::OnWmPerformMoveLoop(
skyfcf18b52016-12-06 03:53:51485 aura::Window* window,
skye0aeea282016-07-27 22:26:09486 ui::mojom::MoveLoopSource source,
erg6d0134e2016-07-07 00:41:13487 const gfx::Point& cursor_location,
488 const base::Callback<void(bool)>& on_done) {
skycd9d4ae2017-05-25 19:38:33489 MoveEventHandler* handler = MoveEventHandler::GetForWindow(window);
erg6ed29f62016-07-08 20:10:40490 if (!handler) {
491 on_done.Run(false);
492 return;
493 }
494
495 DCHECK(!handler->IsDragInProgress());
Thiago Farina3b086a02017-05-30 22:32:50496 ::wm::WindowMoveSource aura_source =
skye0aeea282016-07-27 22:26:09497 source == ui::mojom::MoveLoopSource::MOUSE
Thiago Farina3b086a02017-05-30 22:32:50498 ? ::wm::WINDOW_MOVE_SOURCE_MOUSE
499 : ::wm::WINDOW_MOVE_SOURCE_TOUCH;
erg6ed29f62016-07-08 20:10:40500 handler->AttemptToStartDrag(cursor_location, HTCAPTION, aura_source, on_done);
erg6d0134e2016-07-07 00:41:13501}
502
skyfcf18b52016-12-06 03:53:51503void WindowManager::OnWmCancelMoveLoop(aura::Window* window) {
skycd9d4ae2017-05-25 19:38:33504 MoveEventHandler* handler = MoveEventHandler::GetForWindow(window);
erg6ed29f62016-07-08 20:10:40505 if (handler)
506 handler->RevertDrag();
erg6d0134e2016-07-07 00:41:13507}
508
skyc0c862a2017-03-22 15:14:16509ui::mojom::EventResult WindowManager::OnAccelerator(
510 uint32_t id,
511 const ui::Event& event,
512 std::unordered_map<std::string, std::vector<uint8_t>>* properties) {
sky853669a2016-07-22 18:43:12513 auto iter = accelerator_handlers_.find(GetAcceleratorNamespaceId(id));
514 if (iter == accelerator_handlers_.end())
515 return ui::mojom::EventResult::HANDLED;
erg6ed29f62016-07-08 20:10:40516
skyc0c862a2017-03-22 15:14:16517 return iter->second->OnAccelerator(id, event, properties);
sky76d46662016-07-08 18:43:01518}
519
Elliot Glaysher08063f72017-07-29 00:24:06520void WindowManager::OnCursorTouchVisibleChanged(bool enabled) {
Scott Violetfd1f2652017-10-31 19:53:38521 // Not applicable to Config::MUS.
522 if (config_ == Config::MASH)
523 ShellPortMash::Get()->OnCursorTouchVisibleChanged(enabled);
Elliot Glaysher08063f72017-07-29 00:24:06524}
525
skyfcf18b52016-12-06 03:53:51526void WindowManager::OnWmSetClientArea(
527 aura::Window* window,
528 const gfx::Insets& insets,
529 const std::vector<gfx::Rect>& additional_client_areas) {
530 NonClientFrameController* non_client_frame_controller =
531 NonClientFrameController::Get(window);
532 if (!non_client_frame_controller)
533 return;
534 non_client_frame_controller->SetClientArea(insets, additional_client_areas);
535}
536
erg02ba4e22017-01-13 21:13:48537bool WindowManager::IsWindowActive(aura::Window* window) {
skycb4be5b2017-04-06 17:52:45538 return Shell::Get()->activation_client()->GetActiveWindow() == window;
erg02ba4e22017-01-13 21:13:48539}
540
541void WindowManager::OnWmDeactivateWindow(aura::Window* window) {
skycb4be5b2017-04-06 17:52:45542 Shell::Get()->activation_client()->DeactivateWindow(window);
erg02ba4e22017-01-13 21:13:48543}
544
Elliot Glaysher247b7632017-10-25 03:02:09545void WindowManager::OnWmPerformAction(aura::Window* window,
546 const std::string& action) {
547 if (action == mojom::kAddWindowToTabletMode)
548 ash::Shell::Get()->tablet_mode_controller()->AddWindow(window);
549}
550
Scott Violet0f803d052017-08-04 18:24:42551void WindowManager::OnEventBlockedByModalWindow(aura::Window* window) {
552 AnimateWindow(window, ::wm::WINDOW_ANIMATION_TYPE_BOUNCE);
553}
554
sky002ba4a2016-06-03 00:56:11555} // namespace ash