Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(698)

Side by Side Diff: ash/common/wm/window_positioning_utils.cc

Issue 2344783002: Wires up WmWindowMus::SetBoundsInScreen() (Closed)
Patch Set: feedback2 Created 4 years, 3 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « ash/common/wm/window_positioning_utils.h ('k') | ash/common/wm_root_window_controller.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2016 The Chromium Authors. All rights reserved. 1 // Copyright 2016 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "ash/common/wm/window_positioning_utils.h" 5 #include "ash/common/wm/window_positioning_utils.h"
6 6
7 #include <algorithm> 7 #include <algorithm>
8 8
9 #include "ash/common/wm/system_modal_container_layout_manager.h"
9 #include "ash/common/wm/window_state.h" 10 #include "ash/common/wm/window_state.h"
10 #include "ash/common/wm/wm_event.h" 11 #include "ash/common/wm/wm_event.h"
11 #include "ash/common/wm/wm_screen_util.h" 12 #include "ash/common/wm/wm_screen_util.h"
13 #include "ash/common/wm_lookup.h"
14 #include "ash/common/wm_root_window_controller.h"
15 #include "ash/common/wm_shell.h"
12 #include "ash/common/wm_window.h" 16 #include "ash/common/wm_window.h"
17 #include "ash/common/wm_window_tracker.h"
18 #include "ui/display/display.h"
13 #include "ui/gfx/geometry/rect.h" 19 #include "ui/gfx/geometry/rect.h"
14 #include "ui/gfx/geometry/size.h" 20 #include "ui/gfx/geometry/size.h"
15 21
16 namespace ash { 22 namespace ash {
17 namespace wm { 23 namespace wm {
18 24
19 namespace { 25 namespace {
20 26
21 // Returns the default width of a snapped window. 27 // Returns the default width of a snapped window.
22 int GetDefaultSnappedWindowWidth(WmWindow* window) { 28 int GetDefaultSnappedWindowWidth(WmWindow* window) {
23 const float kSnappedWidthWorkspaceRatio = 0.5f; 29 const float kSnappedWidthWorkspaceRatio = 0.5f;
24 30
25 int work_area_width = GetDisplayWorkAreaBoundsInParent(window).width(); 31 int work_area_width = GetDisplayWorkAreaBoundsInParent(window).width();
26 int min_width = window->GetMinimumSize().width(); 32 int min_width = window->GetMinimumSize().width();
27 int ideal_width = 33 int ideal_width =
28 static_cast<int>(work_area_width * kSnappedWidthWorkspaceRatio); 34 static_cast<int>(work_area_width * kSnappedWidthWorkspaceRatio);
29 return std::min(work_area_width, std::max(ideal_width, min_width)); 35 return std::min(work_area_width, std::max(ideal_width, min_width));
30 } 36 }
31 37
38 // Return true if the window or one of its ancestor returns true from
39 // IsLockedToRoot().
40 bool IsWindowOrAncestorLockedToRoot(const WmWindow* window) {
41 return window && (window->IsLockedToRoot() ||
42 IsWindowOrAncestorLockedToRoot(window->GetParent()));
43 }
44
45 // Move all transient children to |dst_root|, including the ones in
46 // the child windows and transient children of the transient children.
47 void MoveAllTransientChildrenToNewRoot(const display::Display& display,
48 WmWindow* window) {
49 WmWindow* dst_root = WmLookup::Get()
50 ->GetRootWindowControllerWithDisplayId(display.id())
51 ->GetWindow();
52 for (WmWindow* transient_child : window->GetTransientChildren()) {
53 const int container_id = transient_child->GetParent()->GetShellWindowId();
54 DCHECK_GE(container_id, 0);
55 WmWindow* container = dst_root->GetChildByShellWindowId(container_id);
56 const gfx::Rect transient_child_bounds_in_screen =
57 transient_child->GetBoundsInScreen();
58 container->AddChild(transient_child);
59 transient_child->SetBoundsInScreen(transient_child_bounds_in_screen,
60 display);
61
62 // Transient children may have transient children.
63 MoveAllTransientChildrenToNewRoot(display, transient_child);
64 }
65 // Move transient children of the child windows if any.
66 for (WmWindow* child : window->GetChildren())
67 MoveAllTransientChildrenToNewRoot(display, child);
68 }
69
32 } // namespace 70 } // namespace
33 71
34 void AdjustBoundsSmallerThan(const gfx::Size& max_size, gfx::Rect* bounds) { 72 void AdjustBoundsSmallerThan(const gfx::Size& max_size, gfx::Rect* bounds) {
35 bounds->set_width(std::min(bounds->width(), max_size.width())); 73 bounds->set_width(std::min(bounds->width(), max_size.width()));
36 bounds->set_height(std::min(bounds->height(), max_size.height())); 74 bounds->set_height(std::min(bounds->height(), max_size.height()));
37 } 75 }
38 76
39 void AdjustBoundsToEnsureWindowVisibility(const gfx::Rect& visible_area, 77 void AdjustBoundsToEnsureWindowVisibility(const gfx::Rect& visible_area,
40 int min_width, 78 int min_width,
41 int min_height, 79 int min_height,
(...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after
80 int width = GetDefaultSnappedWindowWidth(window); 118 int width = GetDefaultSnappedWindowWidth(window);
81 return gfx::Rect(work_area_in_parent.right() - width, work_area_in_parent.y(), 119 return gfx::Rect(work_area_in_parent.right() - width, work_area_in_parent.y(),
82 width, work_area_in_parent.height()); 120 width, work_area_in_parent.height());
83 } 121 }
84 122
85 void CenterWindow(WmWindow* window) { 123 void CenterWindow(WmWindow* window) {
86 WMEvent event(WM_EVENT_CENTER); 124 WMEvent event(WM_EVENT_CENTER);
87 window->GetWindowState()->OnWMEvent(&event); 125 window->GetWindowState()->OnWMEvent(&event);
88 } 126 }
89 127
128 void SetBoundsInScreen(WmWindow* window,
129 const gfx::Rect& bounds_in_screen,
130 const display::Display& display) {
131 DCHECK_NE(display::Display::kInvalidDisplayID, display.id());
132 // Don't move a window to other root window if:
133 // a) the window is a transient window. It moves when its
134 // transient parent moves.
135 // b) if the window or its ancestor has IsLockedToRoot(). It's intentionally
136 // kept in the same root window even if the bounds is outside of the
137 // display.
138 if (!window->GetTransientParent() &&
139 !IsWindowOrAncestorLockedToRoot(window)) {
140 WmRootWindowController* dst_root_window_controller =
141 WmLookup::Get()->GetRootWindowControllerWithDisplayId(display.id());
142 DCHECK(dst_root_window_controller);
143 WmWindow* dst_root = dst_root_window_controller->GetWindow();
144 DCHECK(dst_root);
145 WmWindow* dst_container = nullptr;
146 if (dst_root != window->GetRootWindow()) {
147 int container_id = window->GetParent()->GetShellWindowId();
148 // All containers that uses screen coordinates must have valid window ids.
149 DCHECK_GE(container_id, 0);
150 // Don't move modal background.
151 if (!SystemModalContainerLayoutManager::IsModalBackground(window))
152 dst_container = dst_root->GetChildByShellWindowId(container_id);
153 }
154
155 if (dst_container && window->GetParent() != dst_container) {
156 WmWindow* focused = WmShell::Get()->GetFocusedWindow();
157 WmWindow* active = WmShell::Get()->GetActiveWindow();
158
159 WmWindowTracker tracker;
160 if (focused)
161 tracker.Add(focused);
162 if (active && focused != active)
163 tracker.Add(active);
164
165 gfx::Point origin = bounds_in_screen.origin();
166 const gfx::Point display_origin = display.bounds().origin();
167 origin.Offset(-display_origin.x(), -display_origin.y());
168 gfx::Rect new_bounds = gfx::Rect(origin, bounds_in_screen.size());
169
170 // Set new bounds now so that the container's layout manager can adjust
171 // the bounds if necessary.
172 window->SetBounds(new_bounds);
173
174 dst_container->AddChild(window);
175
176 MoveAllTransientChildrenToNewRoot(display, window);
177
178 // Restore focused/active window.
179 if (tracker.Contains(focused)) {
180 focused->SetFocused();
181 WmShell::Get()->set_root_window_for_new_windows(
182 focused->GetRootWindow());
183 } else if (tracker.Contains(active)) {
184 active->Activate();
185 }
186 // TODO(oshima): We should not have to update the bounds again
187 // below in theory, but we currently do need as there is a code
188 // that assumes that the bounds will never be overridden by the
189 // layout mananger. We should have more explicit control how
190 // constraints are applied by the layout manager.
191 }
192 }
193 gfx::Point origin(bounds_in_screen.origin());
194 const gfx::Point display_origin =
195 window->GetDisplayNearestWindow().bounds().origin();
196 origin.Offset(-display_origin.x(), -display_origin.y());
197 window->SetBounds(gfx::Rect(origin, bounds_in_screen.size()));
198 }
199
90 } // namespace wm 200 } // namespace wm
91 } // namespace ash 201 } // namespace ash
OLDNEW
« no previous file with comments | « ash/common/wm/window_positioning_utils.h ('k') | ash/common/wm_root_window_controller.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698