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

Side by Side Diff: ash/wm/overview/window_selector.cc

Issue 280423008: Merge WindowOverview into WindowSelector (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Fixed nits, comments, namespace Created 6 years, 7 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
OLDNEW
1 // Copyright 2013 The Chromium Authors. All rights reserved. 1 // Copyright 2013 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/wm/overview/window_selector.h" 5 #include "ash/wm/overview/window_selector.h"
6 6
7 #include <algorithm> 7 #include <algorithm>
8 8
9 #include "ash/accessibility_delegate.h"
9 #include "ash/ash_switches.h" 10 #include "ash/ash_switches.h"
11 #include "ash/metrics/user_metrics_recorder.h"
10 #include "ash/root_window_controller.h" 12 #include "ash/root_window_controller.h"
13 #include "ash/screen_util.h"
11 #include "ash/shell.h" 14 #include "ash/shell.h"
15 #include "ash/shell_window_ids.h"
12 #include "ash/switchable_windows.h" 16 #include "ash/switchable_windows.h"
13 #include "ash/wm/overview/window_overview.h" 17 #include "ash/wm/overview/scoped_transform_overview_window.h"
14 #include "ash/wm/overview/window_selector_delegate.h" 18 #include "ash/wm/overview/window_selector_delegate.h"
19 #include "ash/wm/overview/window_selector_item.h"
15 #include "ash/wm/overview/window_selector_panels.h" 20 #include "ash/wm/overview/window_selector_panels.h"
16 #include "ash/wm/overview/window_selector_window.h" 21 #include "ash/wm/overview/window_selector_window.h"
17 #include "ash/wm/window_state.h" 22 #include "ash/wm/window_state.h"
18 #include "base/auto_reset.h" 23 #include "base/auto_reset.h"
19 #include "base/command_line.h" 24 #include "base/command_line.h"
20 #include "base/metrics/histogram.h" 25 #include "base/metrics/histogram.h"
21 #include "base/strings/string_number_conversions.h" 26 #include "base/strings/string_number_conversions.h"
27 #include "third_party/skia/include/core/SkColor.h"
28 #include "ui/aura/client/cursor_client.h"
22 #include "ui/aura/client/focus_client.h" 29 #include "ui/aura/client/focus_client.h"
23 #include "ui/aura/window.h" 30 #include "ui/aura/window.h"
31 #include "ui/aura/window_event_dispatcher.h"
24 #include "ui/aura/window_observer.h" 32 #include "ui/aura/window_observer.h"
33 #include "ui/compositor/layer_animation_observer.h"
34 #include "ui/compositor/scoped_layer_animation_settings.h"
35 #include "ui/events/event.h"
36 #include "ui/gfx/screen.h"
37 #include "ui/views/background.h"
38 #include "ui/views/widget/widget.h"
25 #include "ui/wm/core/window_util.h" 39 #include "ui/wm/core/window_util.h"
26 #include "ui/wm/public/activation_client.h" 40 #include "ui/wm/public/activation_client.h"
27 41
28 namespace ash { 42 namespace ash {
29 43
30 namespace { 44 namespace {
31 45
32 // A comparator for locating a given selectable window. 46 // Conceptually the window overview is a table or grid of cells having this
47 // fixed aspect ratio. The number of columns is determined by maximizing the
48 // area of them based on the number of windows.
49 const float kCardAspectRatio = 4.0f / 3.0f;
50
51 // In the conceptual overview table, the window margin is the space reserved
52 // around the window within the cell. This margin does not overlap so the
53 // closest distance between adjacent windows will be twice this amount.
54 const int kWindowMargin = 30;
55
56 // The minimum number of cards along the major axis (i.e. horizontally on a
57 // landscape orientation).
58 const int kMinCardsMajor = 3;
59
60 // The duration of transition animations on the overview selector.
61 const int kOverviewSelectorTransitionMilliseconds = 100;
62
63 // The color and opacity of the overview selector.
64 const SkColor kWindowOverviewSelectionColor = SK_ColorBLACK;
65 const float kWindowOverviewSelectionOpacity = 0.5f;
66
67 // The padding or amount of the window selector widget visible around the edges
68 // of the currently selected window.
69 const int kWindowOverviewSelectionPadding = 25;
70
71 // A comparator for locating a given target window.
33 struct WindowSelectorItemComparator 72 struct WindowSelectorItemComparator
34 : public std::unary_function<WindowSelectorItem*, bool> { 73 : public std::unary_function<WindowSelectorItem*, bool> {
35 explicit WindowSelectorItemComparator(const aura::Window* window) 74 explicit WindowSelectorItemComparator(const aura::Window* target_window)
36 : window_(window) { 75 : target(target_window) {
37 } 76 }
38 77
39 bool operator()(WindowSelectorItem* window) const { 78 bool operator()(WindowSelectorItem* window) const {
40 return window->HasSelectableWindow(window_); 79 return window->TargetedWindow(target) != NULL;
41 } 80 }
42 81
43 const aura::Window* window_; 82 const aura::Window* target;
44 }; 83 };
45 84
85 // An observer which holds onto the passed widget until the animation is
86 // complete.
87 class CleanupWidgetAfterAnimationObserver : public ui::LayerAnimationObserver {
88 public:
89 explicit CleanupWidgetAfterAnimationObserver(
90 scoped_ptr<views::Widget> widget);
91
92 // ui::LayerAnimationObserver:
93 virtual void OnLayerAnimationEnded(
94 ui::LayerAnimationSequence* sequence) OVERRIDE;
95 virtual void OnLayerAnimationAborted(
96 ui::LayerAnimationSequence* sequence) OVERRIDE;
97 virtual void OnLayerAnimationScheduled(
98 ui::LayerAnimationSequence* sequence) OVERRIDE;
99
100 private:
101 virtual ~CleanupWidgetAfterAnimationObserver();
102
103 scoped_ptr<views::Widget> widget_;
104
105 DISALLOW_COPY_AND_ASSIGN(CleanupWidgetAfterAnimationObserver);
106 };
107
108 CleanupWidgetAfterAnimationObserver::CleanupWidgetAfterAnimationObserver(
109 scoped_ptr<views::Widget> widget)
110 : widget_(widget.Pass()) {
111 widget_->GetNativeWindow()->layer()->GetAnimator()->AddObserver(this);
112 }
113
114 CleanupWidgetAfterAnimationObserver::~CleanupWidgetAfterAnimationObserver() {
115 widget_->GetNativeWindow()->layer()->GetAnimator()->RemoveObserver(this);
116 }
117
118 void CleanupWidgetAfterAnimationObserver::OnLayerAnimationEnded(
119 ui::LayerAnimationSequence* sequence) {
120 delete this;
121 }
122
123 void CleanupWidgetAfterAnimationObserver::OnLayerAnimationAborted(
124 ui::LayerAnimationSequence* sequence) {
125 delete this;
126 }
127
128 void CleanupWidgetAfterAnimationObserver::OnLayerAnimationScheduled(
129 ui::LayerAnimationSequence* sequence) {
130 }
131
46 // A comparator for locating a selectable window given a targeted window. 132 // A comparator for locating a selectable window given a targeted window.
47 struct WindowSelectorItemTargetComparator 133 struct WindowSelectorItemTargetComparator
48 : public std::unary_function<WindowSelectorItem*, bool> { 134 : public std::unary_function<WindowSelectorItem*, bool> {
49 explicit WindowSelectorItemTargetComparator(const aura::Window* target_window) 135 explicit WindowSelectorItemTargetComparator(const aura::Window* target_window)
50 : target(target_window) { 136 : target(target_window) {
51 } 137 }
52 138
53 bool operator()(WindowSelectorItem* window) const { 139 bool operator()(WindowSelectorItem* window) const {
54 return window->TargetedWindow(target) != NULL; 140 return window->TargetedWindow(target) != NULL;
55 } 141 }
(...skipping 83 matching lines...) Expand 10 before | Expand all | Expand 10 after
139 kSwitchableWindowContainerIds[i]); 225 kSwitchableWindowContainerIds[i]);
140 container->AddObserver(this); 226 container->AddObserver(this);
141 observed_windows_.insert(container); 227 observed_windows_.insert(container);
142 } 228 }
143 } 229 }
144 230
145 StartOverview(); 231 StartOverview();
146 } 232 }
147 233
148 WindowSelector::~WindowSelector() { 234 WindowSelector::~WindowSelector() {
235 ash::Shell* shell = ash::Shell::GetInstance();
236
149 ResetFocusRestoreWindow(true); 237 ResetFocusRestoreWindow(true);
150 for (std::set<aura::Window*>::iterator iter = observed_windows_.begin(); 238 for (std::set<aura::Window*>::iterator iter = observed_windows_.begin();
151 iter != observed_windows_.end(); ++iter) { 239 iter != observed_windows_.end(); ++iter) {
152 (*iter)->RemoveObserver(this); 240 (*iter)->RemoveObserver(this);
153 } 241 }
154 Shell::GetInstance()->activation_client()->RemoveObserver(this); 242 shell->activation_client()->RemoveObserver(this);
155 aura::Window::Windows root_windows = Shell::GetAllRootWindows(); 243 aura::Window::Windows root_windows = Shell::GetAllRootWindows();
156 window_overview_.reset(); 244
245 const aura::WindowTracker::Windows hidden_windows(hidden_windows_.windows());
246 for (aura::WindowTracker::Windows::const_iterator iter =
247 hidden_windows.begin(); iter != hidden_windows.end(); ++iter) {
248 ui::ScopedLayerAnimationSettings settings(
249 (*iter)->layer()->GetAnimator());
250 settings.SetTransitionDuration(base::TimeDelta::FromMilliseconds(
251 ScopedTransformOverviewWindow::kTransitionMilliseconds));
252 settings.SetPreemptionStrategy(
253 ui::LayerAnimator::IMMEDIATELY_ANIMATE_TO_NEW_TARGET);
254 (*iter)->layer()->SetOpacity(1);
255 (*iter)->Show();
256 }
257
258 if (cursor_client_)
259 cursor_client_->UnlockCursor();
260 shell->RemovePreTargetHandler(this);
261 shell->GetScreen()->RemoveObserver(this);
262 UMA_HISTOGRAM_MEDIUM_TIMES(
263 "Ash.WindowSelector.TimeInOverview",
264 base::Time::Now() - overview_start_time_);
265
266 // TODO(nsatragno): Change this to OnOverviewModeEnded and move it to when
267 // everything is done.
268 shell->OnOverviewModeEnding();
269
157 // Clearing the window list resets the ignored_by_shelf flag on the windows. 270 // Clearing the window list resets the ignored_by_shelf flag on the windows.
158 windows_.clear(); 271 windows_.clear();
159 UpdateShelfVisibility(); 272 UpdateShelfVisibility();
160 } 273 }
161 274
162 void WindowSelector::SelectWindow(aura::Window* window) { 275 void WindowSelector::SelectWindow(aura::Window* window) {
163 ResetFocusRestoreWindow(false); 276 ResetFocusRestoreWindow(false);
164 ScopedVector<WindowSelectorItem>::iterator iter = 277 ScopedVector<WindowSelectorItem>::iterator iter =
165 std::find_if(windows_.begin(), windows_.end(), 278 std::find_if(windows_.begin(), windows_.end(),
166 WindowSelectorItemTargetComparator(window)); 279 WindowSelectorItemTargetComparator(window));
167 DCHECK(iter != windows_.end()); 280 DCHECK(iter != windows_.end());
168 // The selected window should not be minimized when window selection is 281 // The selected window should not be minimized when window selection is
169 // ended. 282 // ended.
170 (*iter)->RestoreWindowOnExit(window); 283 (*iter)->RestoreWindowOnExit(window);
171 delegate_->OnWindowSelected(window); 284 delegate_->OnWindowSelected(window);
172 } 285 }
173 286
174 void WindowSelector::CancelSelection() { 287 void WindowSelector::CancelSelection() {
175 delegate_->OnSelectionCanceled(); 288 delegate_->OnSelectionCanceled();
176 } 289 }
177 290
291 void WindowSelector::OnKeyEvent(ui::KeyEvent* event) {
292 if (GetTargetedWindow(static_cast<aura::Window*>(event->target())))
293 event->StopPropagation();
294 if (event->type() != ui::ET_KEY_PRESSED)
295 return;
296
297 if (event->key_code() == ui::VKEY_ESCAPE)
298 CancelSelection();
299 }
300
301 void WindowSelector::OnMouseEvent(ui::MouseEvent* event) {
302 aura::Window* target = GetEventTarget(event);
303 if (!target)
304 return;
305
306 event->SetHandled();
307 if (event->type() != ui::ET_MOUSE_RELEASED)
308 return;
309
310 SelectWindow(target);
311 }
312
313 void WindowSelector::OnScrollEvent(ui::ScrollEvent* event) {
314 // Set the handled flag to prevent delivering scroll events to the window but
315 // still allowing other pretarget handlers to process the scroll event.
316 if (GetTargetedWindow(static_cast<aura::Window*>(event->target())))
317 event->SetHandled();
318 }
319
320 void WindowSelector::OnTouchEvent(ui::TouchEvent* event) {
321 // Existing touches should be allowed to continue. This prevents getting
322 // stuck in a gesture or with pressed fingers being tracked elsewhere.
323 if (event->type() != ui::ET_TOUCH_PRESSED)
324 return;
325
326 aura::Window* target = GetEventTarget(event);
327 if (!target)
328 return;
329
330 // TODO(flackr): StopPropogation prevents generation of gesture events.
331 // We should find a better way to prevent events from being delivered to
332 // the window, perhaps a transparent window in front of the target window
333 // or using EventClientImpl::CanProcessEventsWithinSubtree and then a tap
334 // gesture could be used to activate the window.
335 event->SetHandled();
336 SelectWindow(target);
337 }
338
339 void WindowSelector::OnDisplayBoundsChanged(const gfx::Display& display) {
340 PositionWindows(/* animate */ false);
341 }
342
343 void WindowSelector::OnDisplayAdded(const gfx::Display& display) {
344 }
345
346 void WindowSelector::OnDisplayRemoved(const gfx::Display& display) {
347 }
348
178 void WindowSelector::OnWindowAdded(aura::Window* new_window) { 349 void WindowSelector::OnWindowAdded(aura::Window* new_window) {
179 if (new_window->type() != ui::wm::WINDOW_TYPE_NORMAL && 350 if (new_window->type() != ui::wm::WINDOW_TYPE_NORMAL &&
180 new_window->type() != ui::wm::WINDOW_TYPE_PANEL) { 351 new_window->type() != ui::wm::WINDOW_TYPE_PANEL) {
181 return; 352 return;
182 } 353 }
183 354
184 for (size_t i = 0; i < kSwitchableWindowContainerIdsLength; ++i) { 355 for (size_t i = 0; i < kSwitchableWindowContainerIdsLength; ++i) {
185 if (new_window->parent()->id() == kSwitchableWindowContainerIds[i] && 356 if (new_window->parent()->id() == kSwitchableWindowContainerIds[i] &&
186 !::wm::GetTransientParent(new_window)) { 357 !::wm::GetTransientParent(new_window)) {
187 // The new window is in one of the switchable containers, abort overview. 358 // The new window is in one of the switchable containers, abort overview.
(...skipping 20 matching lines...) Expand all
208 // If there are still windows in this selector entry then the overview is 379 // If there are still windows in this selector entry then the overview is
209 // still active and the active selection remains the same. 380 // still active and the active selection remains the same.
210 if (!(*iter)->empty()) 381 if (!(*iter)->empty())
211 return; 382 return;
212 383
213 windows_.erase(iter); 384 windows_.erase(iter);
214 if (windows_.empty()) { 385 if (windows_.empty()) {
215 CancelSelection(); 386 CancelSelection();
216 return; 387 return;
217 } 388 }
218 if (window_overview_) 389 PositionWindows(true);
219 window_overview_->OnWindowsChanged();
220 } 390 }
221 391
222 void WindowSelector::OnWindowBoundsChanged(aura::Window* window, 392 void WindowSelector::OnWindowBoundsChanged(aura::Window* window,
223 const gfx::Rect& old_bounds, 393 const gfx::Rect& old_bounds,
224 const gfx::Rect& new_bounds) { 394 const gfx::Rect& new_bounds) {
225 if (!window_overview_)
226 return;
227
228 ScopedVector<WindowSelectorItem>::iterator iter = 395 ScopedVector<WindowSelectorItem>::iterator iter =
229 std::find_if(windows_.begin(), windows_.end(), 396 std::find_if(windows_.begin(), windows_.end(),
230 WindowSelectorItemTargetComparator(window)); 397 WindowSelectorItemTargetComparator(window));
231 if (iter == windows_.end()) 398 if (iter == windows_.end())
232 return; 399 return;
233 400
234 // Immediately finish any active bounds animation. 401 // Immediately finish any active bounds animation.
235 window->layer()->GetAnimator()->StopAnimatingProperty( 402 window->layer()->GetAnimator()->StopAnimatingProperty(
236 ui::LayerAnimationElement::BOUNDS); 403 ui::LayerAnimationElement::BOUNDS);
237 404
(...skipping 13 matching lines...) Expand all
251 void WindowSelector::OnAttemptToReactivateWindow(aura::Window* request_active, 418 void WindowSelector::OnAttemptToReactivateWindow(aura::Window* request_active,
252 aura::Window* actual_active) { 419 aura::Window* actual_active) {
253 if (ignore_activations_) 420 if (ignore_activations_)
254 return; 421 return;
255 // Don't restore focus on exit if a window was just activated. 422 // Don't restore focus on exit if a window was just activated.
256 ResetFocusRestoreWindow(false); 423 ResetFocusRestoreWindow(false);
257 CancelSelection(); 424 CancelSelection();
258 } 425 }
259 426
260 void WindowSelector::StartOverview() { 427 void WindowSelector::StartOverview() {
261 DCHECK(!window_overview_);
262 // Remove focus from active window before entering overview. 428 // Remove focus from active window before entering overview.
263 aura::client::GetFocusClient( 429 aura::client::GetFocusClient(
264 Shell::GetPrimaryRootWindow())->FocusWindow(NULL); 430 Shell::GetPrimaryRootWindow())->FocusWindow(NULL);
265 431
266 window_overview_.reset(new WindowOverview(this, &windows_)); 432 Shell* shell = Shell::GetInstance();
433 shell->OnOverviewModeStarting();
434
435 for (WindowSelectorItemList::iterator iter = windows_.begin();
436 iter != windows_.end(); ++iter) {
437 (*iter)->PrepareForOverview();
438 }
439 PositionWindows(/* animate */ true);
440 DCHECK(!windows_.empty());
441 cursor_client_ = aura::client::GetCursorClient(
442 windows_.front()->GetRootWindow());
443 if (cursor_client_) {
444 cursor_client_->SetCursor(ui::kCursorPointer);
445 cursor_client_->ShowCursor();
446 // TODO(flackr): Only prevent cursor changes for windows in the overview.
447 // This will be easier to do without exposing the overview mode code if the
448 // cursor changes are moved to ToplevelWindowEventHandler::HandleMouseMoved
449 // as suggested there.
450 cursor_client_->LockCursor();
451 }
452 shell->PrependPreTargetHandler(this);
453 shell->GetScreen()->AddObserver(this);
454 shell->metrics()->RecordUserMetricsAction(UMA_WINDOW_OVERVIEW);
455 HideAndTrackNonOverviewWindows();
456 // Send an a11y alert.
457 shell->accessibility_delegate()->TriggerAccessibilityAlert(
458 A11Y_ALERT_WINDOW_OVERVIEW_MODE_ENTERED);
459
267 UpdateShelfVisibility(); 460 UpdateShelfVisibility();
268 } 461 }
269 462
463 void WindowSelector::PositionWindows(bool animate) {
464 aura::Window::Windows root_window_list = Shell::GetAllRootWindows();
465 for (size_t i = 0; i < root_window_list.size(); ++i)
466 PositionWindowsFromRoot(root_window_list[i], animate);
467 }
468
469 void WindowSelector::PositionWindowsFromRoot(aura::Window* root_window,
470 bool animate) {
471 std::vector<WindowSelectorItem*> windows;
472 for (WindowSelectorItemList::iterator iter = windows_.begin();
473 iter != windows_.end(); ++iter) {
474 if ((*iter)->GetRootWindow() == root_window)
475 windows.push_back(*iter);
476 }
477
478 if (windows.empty())
479 return;
480
481 gfx::Size window_size;
482 gfx::Rect total_bounds = ScreenUtil::ConvertRectToScreen(
483 root_window,
484 ScreenUtil::GetDisplayWorkAreaBoundsInParent(
485 Shell::GetContainer(root_window, kShellWindowId_DefaultContainer)));
486
487 // Find the minimum number of windows per row that will fit all of the
488 // windows on screen.
489 size_t columns = std::max(
490 total_bounds.width() > total_bounds.height() ? kMinCardsMajor : 1,
491 static_cast<int>(ceil(sqrt(total_bounds.width() * windows.size() /
492 (kCardAspectRatio * total_bounds.height())))));
493 size_t rows = ((windows.size() + columns - 1) / columns);
494 window_size.set_width(std::min(
495 static_cast<int>(total_bounds.width() / columns),
496 static_cast<int>(total_bounds.height() * kCardAspectRatio / rows)));
497 window_size.set_height(window_size.width() / kCardAspectRatio);
498
499 // Calculate the X and Y offsets necessary to center the grid.
500 int x_offset = total_bounds.x() + ((windows.size() >= columns ? 0 :
501 (columns - windows.size()) * window_size.width()) +
502 (total_bounds.width() - columns * window_size.width())) / 2;
503 int y_offset = total_bounds.y() + (total_bounds.height() -
504 rows * window_size.height()) / 2;
505 for (size_t i = 0; i < windows.size(); ++i) {
506 gfx::Transform transform;
507 int column = i % columns;
508 int row = i / columns;
509 gfx::Rect target_bounds(window_size.width() * column + x_offset,
510 window_size.height() * row + y_offset,
511 window_size.width(),
512 window_size.height());
513 target_bounds.Inset(kWindowMargin, kWindowMargin);
514 windows[i]->SetBounds(root_window, target_bounds, animate);
515 }
516 }
517
518 void WindowSelector::HideAndTrackNonOverviewWindows() {
519 // Add the windows to hidden_windows first so that if any are destroyed
520 // while hiding them they are tracked.
521 aura::Window::Windows root_windows = Shell::GetAllRootWindows();
522 for (aura::Window::Windows::const_iterator root_iter = root_windows.begin();
523 root_iter != root_windows.end(); ++root_iter) {
524 for (size_t i = 0; i < kSwitchableWindowContainerIdsLength; ++i) {
525 aura::Window* container = Shell::GetContainer(*root_iter,
526 kSwitchableWindowContainerIds[i]);
527 for (aura::Window::Windows::const_iterator iter =
528 container->children().begin(); iter != container->children().end();
529 ++iter) {
530 if (GetTargetedWindow(*iter) || !(*iter)->IsVisible())
531 continue;
532 hidden_windows_.Add(*iter);
533 }
534 }
535 }
536
537 // Copy the window list as it can change during iteration.
538 const aura::WindowTracker::Windows hidden_windows(hidden_windows_.windows());
539 for (aura::WindowTracker::Windows::const_iterator iter =
540 hidden_windows.begin(); iter != hidden_windows.end(); ++iter) {
541 if (!hidden_windows_.Contains(*iter))
542 continue;
543 ui::ScopedLayerAnimationSettings settings(
544 (*iter)->layer()->GetAnimator());
545 settings.SetTransitionDuration(base::TimeDelta::FromMilliseconds(
546 ScopedTransformOverviewWindow::kTransitionMilliseconds));
547 settings.SetPreemptionStrategy(
548 ui::LayerAnimator::IMMEDIATELY_ANIMATE_TO_NEW_TARGET);
549 (*iter)->Hide();
550 // Hiding the window can result in it being destroyed.
551 if (!hidden_windows_.Contains(*iter))
552 continue;
553 (*iter)->layer()->SetOpacity(0);
554 }
555 }
556
270 void WindowSelector::ResetFocusRestoreWindow(bool focus) { 557 void WindowSelector::ResetFocusRestoreWindow(bool focus) {
271 if (!restore_focus_window_) 558 if (!restore_focus_window_)
272 return; 559 return;
273 if (focus) { 560 if (focus) {
274 base::AutoReset<bool> restoring_focus(&ignore_activations_, true); 561 base::AutoReset<bool> restoring_focus(&ignore_activations_, true);
275 restore_focus_window_->Focus(); 562 restore_focus_window_->Focus();
276 } 563 }
277 // If the window is in the observed_windows_ list it needs to continue to be 564 // If the window is in the observed_windows_ list it needs to continue to be
278 // observed. 565 // observed.
279 if (observed_windows_.find(restore_focus_window_) == 566 if (observed_windows_.find(restore_focus_window_) ==
280 observed_windows_.end()) { 567 observed_windows_.end()) {
281 restore_focus_window_->RemoveObserver(this); 568 restore_focus_window_->RemoveObserver(this);
282 } 569 }
283 restore_focus_window_ = NULL; 570 restore_focus_window_ = NULL;
284 } 571 }
285 572
573 aura::Window* WindowSelector::GetEventTarget(ui::LocatedEvent* event) {
574 aura::Window* target = static_cast<aura::Window*>(event->target());
575 // If the target window doesn't actually contain the event location (i.e.
576 // mouse down over the window and mouse up elsewhere) then do not select the
577 // window.
578 if (!target->ContainsPoint(event->location()))
579 return NULL;
580
581 return GetTargetedWindow(target);
582 }
583
584 aura::Window* WindowSelector::GetTargetedWindow(aura::Window* window) {
585 for (WindowSelectorItemList::iterator iter = windows_.begin();
586 iter != windows_.end(); ++iter) {
587 aura::Window* selected = (*iter)->TargetedWindow(window);
588 if (selected)
589 return selected;
590 }
591 return NULL;
592 }
593
286 } // namespace ash 594 } // namespace ash
OLDNEW
« ash/wm/overview/window_selector.h ('K') | « ash/wm/overview/window_selector.h ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698