Commit 227733e3 authored by skuhne's avatar skuhne Committed by Commit bot

Adding functions to the window_list_provider for accessing the activities

window list

As discussed - added the window/activity order management functions
to the WindowListProvider and changed the use cases (at least partially).
There are still more things to do, but we might want to do that either
 a. incrementally or
 b. as a separate issue since the associated BUG(388085) has nothing to
    do with this.
Note: This is more work - especially because the code in question is being
worked on actively by others.

BUG=407103
TEST=athena_unittest.SimpleChecks, athena_unittest.TestWindowOrderingFunctions

Review URL: https://codereview.chromium.org/480293003

Cr-Commit-Position: refs/heads/master@{#294103}
parent a1a1d99b
...@@ -107,6 +107,7 @@ ...@@ -107,6 +107,7 @@
'wm/overview_toolbar.cc', 'wm/overview_toolbar.cc',
'wm/overview_toolbar.h', 'wm/overview_toolbar.h',
'wm/public/window_list_provider.h', 'wm/public/window_list_provider.h',
'wm/public/window_list_provider_observer.h',
'wm/public/window_manager.h', 'wm/public/window_manager.h',
'wm/public/window_manager_observer.h', 'wm/public/window_manager_observer.h',
'wm/split_view_controller.cc', 'wm/split_view_controller.cc',
......
...@@ -4,6 +4,7 @@ include_rules = [ ...@@ -4,6 +4,7 @@ include_rules = [
"+athena/home/public", "+athena/home/public",
"+athena/input/public", "+athena/input/public",
"+athena/resource_manager/public", "+athena/resource_manager/public",
"+athena/wm/public",
"+components/renderer_context_menu", "+components/renderer_context_menu",
"+components/web_modal", "+components/web_modal",
"+content/public", "+content/public",
......
...@@ -7,6 +7,8 @@ ...@@ -7,6 +7,8 @@
#include "athena/activity/public/activity_manager.h" #include "athena/activity/public/activity_manager.h"
#include "athena/content/app_activity_registry.h" #include "athena/content/app_activity_registry.h"
#include "athena/content/public/app_registry.h" #include "athena/content/public/app_registry.h"
#include "athena/wm/public/window_list_provider.h"
#include "athena/wm/public/window_manager.h"
#include "content/public/browser/web_contents.h" #include "content/public/browser/web_contents.h"
#include "ui/aura/window.h" #include "ui/aura/window.h"
#include "ui/views/controls/webview/webview.h" #include "ui/views/controls/webview/webview.h"
...@@ -87,11 +89,12 @@ void AppActivity::Init() { ...@@ -87,11 +89,12 @@ void AppActivity::Init() {
DCHECK(app_activity_registry_); DCHECK(app_activity_registry_);
Activity* app_proxy = app_activity_registry_->unloaded_activity_proxy(); Activity* app_proxy = app_activity_registry_->unloaded_activity_proxy();
if (app_proxy) { if (app_proxy) {
// TODO(skuhne): This should call the WindowListProvider to re-arrange.
// Note: At this time the |AppActivity| did not get registered to the // Note: At this time the |AppActivity| did not get registered to the
// |ResourceManager| - so we can move it around if needed. // |ResourceManager| - so we can move it around if needed.
aura::Window* proxy_window = app_proxy->GetWindow(); WindowListProvider* window_list_provider =
proxy_window->parent()->StackChildBelow(GetWindow(), proxy_window); WindowManager::GetInstance()->GetWindowListProvider();
window_list_provider->StackWindowFrontOf(app_proxy->GetWindow(),
GetWindow());
Activity::Delete(app_proxy); Activity::Delete(app_proxy);
// With the removal the object, the proxy should be deleted. // With the removal the object, the proxy should be deleted.
DCHECK(!app_activity_registry_->unloaded_activity_proxy()); DCHECK(!app_activity_registry_->unloaded_activity_proxy());
......
...@@ -5,6 +5,8 @@ ...@@ -5,6 +5,8 @@
#include "athena/content/app_activity_proxy.h" #include "athena/content/app_activity_proxy.h"
#include "athena/content/app_activity_registry.h" #include "athena/content/app_activity_registry.h"
#include "athena/wm/public/window_list_provider.h"
#include "athena/wm/public/window_manager.h"
#include "ui/aura/window.h" #include "ui/aura/window.h"
#include "ui/views/view.h" #include "ui/views/view.h"
#include "ui/views/widget/widget.h" #include "ui/views/widget/widget.h"
...@@ -58,10 +60,10 @@ aura::Window* AppActivityProxy::GetWindow() { ...@@ -58,10 +60,10 @@ aura::Window* AppActivityProxy::GetWindow() {
void AppActivityProxy::Init() { void AppActivityProxy::Init() {
DCHECK(replaced_activity_); DCHECK(replaced_activity_);
// TODO(skuhne): This should call the WindowListProvider to re-arrange. WindowListProvider* window_list_provider =
// At this point we can move the Activity to its proper Activity location. WindowManager::GetInstance()->GetWindowListProvider();
aura::Window* relative_window = replaced_activity_->GetWindow(); window_list_provider->StackWindowBehindTo(GetWindow(),
relative_window->parent()->StackChildBelow(GetWindow(), relative_window); replaced_activity_->GetWindow());
// We moved. // We moved.
replaced_activity_ = NULL; replaced_activity_ = NULL;
} }
......
...@@ -10,6 +10,8 @@ ...@@ -10,6 +10,8 @@
#include "athena/content/public/app_registry.h" #include "athena/content/public/app_registry.h"
#include "athena/extensions/public/extensions_delegate.h" #include "athena/extensions/public/extensions_delegate.h"
#include "athena/resource_manager/public/resource_manager.h" #include "athena/resource_manager/public/resource_manager.h"
#include "athena/wm/public/window_list_provider.h"
#include "athena/wm/public/window_manager.h"
#include "ui/aura/window.h" #include "ui/aura/window.h"
#include "ui/views/view.h" #include "ui/views/view.h"
#include "ui/views/widget/widget.h" #include "ui/views/widget/widget.h"
...@@ -103,9 +105,10 @@ void AppActivityRegistry::RestartApplication(AppActivityProxy* proxy) { ...@@ -103,9 +105,10 @@ void AppActivityRegistry::RestartApplication(AppActivityProxy* proxy) {
AppActivity* AppActivityRegistry::GetMruActivity() { AppActivity* AppActivityRegistry::GetMruActivity() {
DCHECK(activity_list_.size()); DCHECK(activity_list_.size());
// TODO(skuhne): This should be a query into the window manager. WindowListProvider* window_list_provider =
WindowManager::GetInstance()->GetWindowListProvider();
const aura::Window::Windows children = const aura::Window::Windows children =
activity_list_[0]->GetWindow()->parent()->children(); window_list_provider->GetWindowList();
// Find the first window in the container which is part of the application. // Find the first window in the container which is part of the application.
for (aura::Window::Windows::const_iterator child_iterator = children.begin(); for (aura::Window::Windows::const_iterator child_iterator = children.begin();
child_iterator != children.end(); ++child_iterator) { child_iterator != children.end(); ++child_iterator) {
......
...@@ -12,12 +12,13 @@ ...@@ -12,12 +12,13 @@
#include "athena/activity/public/activity_manager_observer.h" #include "athena/activity/public/activity_manager_observer.h"
#include "athena/resource_manager/memory_pressure_notifier.h" #include "athena/resource_manager/memory_pressure_notifier.h"
#include "athena/resource_manager/public/resource_manager_delegate.h" #include "athena/resource_manager/public/resource_manager_delegate.h"
#include "athena/wm/public/window_list_provider.h"
#include "athena/wm/public/window_list_provider_observer.h"
#include "athena/wm/public/window_manager.h" #include "athena/wm/public/window_manager.h"
#include "athena/wm/public/window_manager_observer.h" #include "athena/wm/public/window_manager_observer.h"
#include "base/logging.h" #include "base/logging.h"
#include "base/memory/scoped_ptr.h" #include "base/memory/scoped_ptr.h"
#include "ui/aura/window.h" #include "ui/aura/window.h"
#include "ui/aura/window_observer.h"
namespace athena { namespace athena {
...@@ -25,7 +26,7 @@ class ResourceManagerImpl : public ResourceManager, ...@@ -25,7 +26,7 @@ class ResourceManagerImpl : public ResourceManager,
public WindowManagerObserver, public WindowManagerObserver,
public ActivityManagerObserver, public ActivityManagerObserver,
public MemoryPressureObserver, public MemoryPressureObserver,
public aura::WindowObserver { public WindowListProviderObserver {
public: public:
ResourceManagerImpl(ResourceManagerDelegate* delegate); ResourceManagerImpl(ResourceManagerDelegate* delegate);
virtual ~ResourceManagerImpl(); virtual ~ResourceManagerImpl();
...@@ -63,8 +64,8 @@ class ResourceManagerImpl : public ResourceManager, ...@@ -63,8 +64,8 @@ class ResourceManagerImpl : public ResourceManager,
MemoryPressureObserver::MemoryPressure pressure) OVERRIDE; MemoryPressureObserver::MemoryPressure pressure) OVERRIDE;
virtual ResourceManagerDelegate* GetDelegate() OVERRIDE; virtual ResourceManagerDelegate* GetDelegate() OVERRIDE;
// aura::WindowObserver: // WindowListProviderObserver:
virtual void OnWindowStackingChanged(aura::Window* window) OVERRIDE; virtual void OnWindowStackingChanged() OVERRIDE;
private: private:
// Manage the resources for our activities. // Manage the resources for our activities.
...@@ -128,11 +129,13 @@ ResourceManagerImpl::ResourceManagerImpl(ResourceManagerDelegate* delegate) ...@@ -128,11 +129,13 @@ ResourceManagerImpl::ResourceManagerImpl(ResourceManagerDelegate* delegate)
in_overview_mode_(false), in_overview_mode_(false),
in_splitview_mode_(false) { in_splitview_mode_(false) {
WindowManager::GetInstance()->AddObserver(this); WindowManager::GetInstance()->AddObserver(this);
WindowManager::GetInstance()->GetWindowListProvider()->AddObserver(this);
ActivityManager::Get()->AddObserver(this); ActivityManager::Get()->AddObserver(this);
} }
ResourceManagerImpl::~ResourceManagerImpl() { ResourceManagerImpl::~ResourceManagerImpl() {
ActivityManager::Get()->RemoveObserver(this); ActivityManager::Get()->RemoveObserver(this);
WindowManager::GetInstance()->GetWindowListProvider()->RemoveObserver(this);
WindowManager::GetInstance()->RemoveObserver(this); WindowManager::GetInstance()->RemoveObserver(this);
while (!activity_list_.empty()) while (!activity_list_.empty())
...@@ -154,12 +157,10 @@ void ResourceManagerImpl::OnActivityStarted(Activity* activity) { ...@@ -154,12 +157,10 @@ void ResourceManagerImpl::OnActivityStarted(Activity* activity) {
ManageResource(); ManageResource();
// Remember that the activity order has changed. // Remember that the activity order has changed.
activity_order_changed_ = true; activity_order_changed_ = true;
activity->GetWindow()->AddObserver(this);
} }
void ResourceManagerImpl::OnActivityEnding(Activity* activity) { void ResourceManagerImpl::OnActivityEnding(Activity* activity) {
DCHECK(activity->GetWindow()); DCHECK(activity->GetWindow());
activity->GetWindow()->RemoveObserver(this);
// Remove the activity from the list again. // Remove the activity from the list again.
std::vector<Activity*>::iterator it = std::vector<Activity*>::iterator it =
std::find(activity_list_.begin(), activity_list_.end(), activity); std::find(activity_list_.begin(), activity_list_.end(), activity);
...@@ -192,9 +193,14 @@ void ResourceManagerImpl::OnSplitViewModeExit() { ...@@ -192,9 +193,14 @@ void ResourceManagerImpl::OnSplitViewModeExit() {
in_splitview_mode_ = false; in_splitview_mode_ = false;
} }
void ResourceManagerImpl::OnWindowStackingChanged(aura::Window* window) { void ResourceManagerImpl::OnWindowStackingChanged() {
// TODO(skuhne): This needs to be changed to some WindowListProvider observer // TODO(skuhne): This needs to be changed to some WindowListProvider observer
// if we decouple window order from activity order. // if we decouple window order from activity order.
activity_order_changed_ = true;
if (pause_) {
queued_command_ = true;
return;
}
// No need to do anything while being in overview mode. // No need to do anything while being in overview mode.
if (in_overview_mode_) if (in_overview_mode_)
......
...@@ -10,13 +10,42 @@ ...@@ -10,13 +10,42 @@
namespace athena { namespace athena {
class WindowListProviderObserver;
// Interface for an ordered list of aura::Window objects. // Interface for an ordered list of aura::Window objects.
// Note that lists returned by GetCurrentWindowList() will not change if any of
// the other member functions will be called later.
class ATHENA_EXPORT WindowListProvider { class ATHENA_EXPORT WindowListProvider {
public: public:
virtual ~WindowListProvider() {} virtual ~WindowListProvider() {}
// Returns an ordered list of windows. // Adding/removing an observer to status changes.
virtual void AddObserver(WindowListProviderObserver* observer) = 0;
virtual void RemoveObserver(WindowListProviderObserver* observer) = 0;
// Returns an ordered list of the current window configuration.
virtual aura::Window::Windows GetWindowList() const = 0; virtual aura::Window::Windows GetWindowList() const = 0;
// Returns true if the |window| is part of the list.
virtual bool IsWindowInList(aura::Window* window) const = 0;
// Returns true if the given window is a window which can be handled by the
// WindowListProvider.
virtual bool IsValidWindow(aura::Window* window) const = 0;
// Moves a given |window| to the front of all windows of the window list.
// Note: The window has to be in the list already.
virtual void MoveToFront(aura::Window* window) = 0;
// Stacks a given |window| in direct front of a |reference_window|.
// Note: The |window| and |reference_window| has to be in the list already.
virtual void StackWindowFrontOf(aura::Window* window,
aura::Window* reference_window) = 0;
// Stacks a given |window| directly behind a |reference_window|.
// Note: The |window| and |reference_window| has to be in the list already.
virtual void StackWindowBehindTo(aura::Window* window,
aura::Window* reference_window) = 0;
}; };
} // namespace athena } // namespace athena
......
// Copyright 2014 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 ATHENA_WM_PUBLIC_WINDOW_LIST_PROVIDER_OBSERVER_H_
#define ATHENA_WM_PUBLIC_WINDOW_LIST_PROVIDER_OBSERVER_H_
#include "athena/athena_export.h"
namespace athena {
// An observer to window list changes like e.g. stacking order has changed.
class ATHENA_EXPORT WindowListProviderObserver {
public:
virtual ~WindowListProviderObserver() {}
// The Window stacking has changed.
virtual void OnWindowStackingChanged() = 0;
};
} // namespace athena
#endif // ATHENA_WM_PUBLIC_WINDOW_LIST_PROVIDER_OBSERVER_H_
...@@ -9,6 +9,7 @@ ...@@ -9,6 +9,7 @@
namespace athena { namespace athena {
class WindowListProvider;
class WindowManagerObserver; class WindowManagerObserver;
// Manages the application, web windows. // Manages the application, web windows.
...@@ -30,6 +31,10 @@ class ATHENA_EXPORT WindowManager { ...@@ -30,6 +31,10 @@ class ATHENA_EXPORT WindowManager {
virtual void RemoveObserver(WindowManagerObserver* observer) = 0; virtual void RemoveObserver(WindowManagerObserver* observer) = 0;
virtual void ToggleSplitViewForTest() = 0; virtual void ToggleSplitViewForTest() = 0;
// This returns the window list provider of the current MRU order of windows.
// The ownership remains with the WindowManager.
virtual WindowListProvider* GetWindowListProvider() = 0;
}; };
} // namespace athena } // namespace athena
......
...@@ -97,11 +97,15 @@ void SplitViewController::ActivateSplitMode(aura::Window* left, ...@@ -97,11 +97,15 @@ void SplitViewController::ActivateSplitMode(aura::Window* left,
SetState(ACTIVE); SetState(ACTIVE);
if (right_window_ != right) { if (right_window_ != right) {
right_window_ = right; right_window_ = right;
container_->StackChildAtTop(right_window_); // Since the |window_list_provider_| controls directly the order of windows,
// it needs to change the window order accordingly.
window_list_provider_->MoveToFront(right_window_);
} }
if (left_window_ != left) { if (left_window_ != left) {
left_window_ = left; left_window_ = left;
container_->StackChildAtTop(left_window_); // Since the |window_list_provider_| controls directly the order of windows,
// it needs to change the window order accordingly.
window_list_provider_->MoveToFront(left_window_);
} }
UpdateLayout(true); UpdateLayout(true);
} }
......
...@@ -4,6 +4,7 @@ ...@@ -4,6 +4,7 @@
#include "athena/wm/window_list_provider_impl.h" #include "athena/wm/window_list_provider_impl.h"
#include "athena/wm/public/window_list_provider_observer.h"
#include "ui/aura/window.h" #include "ui/aura/window.h"
namespace athena { namespace athena {
...@@ -11,9 +12,28 @@ namespace athena { ...@@ -11,9 +12,28 @@ namespace athena {
WindowListProviderImpl::WindowListProviderImpl(aura::Window* container) WindowListProviderImpl::WindowListProviderImpl(aura::Window* container)
: container_(container) { : container_(container) {
CHECK(container_); CHECK(container_);
container_->AddObserver(this);
} }
WindowListProviderImpl::~WindowListProviderImpl() { WindowListProviderImpl::~WindowListProviderImpl() {
// Remove all remaining window observers.
const aura::Window::Windows& container_children = container_->children();
for (aura::Window::Windows::const_iterator iter = container_children.begin();
iter != container_children.end();
++iter) {
if (IsValidWindow(*iter))
(*iter)->RemoveObserver(this);
}
container_->RemoveObserver(this);
}
void WindowListProviderImpl::AddObserver(WindowListProviderObserver* observer) {
observers_.AddObserver(observer);
}
void WindowListProviderImpl::RemoveObserver(
WindowListProviderObserver* observer) {
observers_.RemoveObserver(observer);
} }
aura::Window::Windows WindowListProviderImpl::GetWindowList() const { aura::Window::Windows WindowListProviderImpl::GetWindowList() const {
...@@ -22,10 +42,65 @@ aura::Window::Windows WindowListProviderImpl::GetWindowList() const { ...@@ -22,10 +42,65 @@ aura::Window::Windows WindowListProviderImpl::GetWindowList() const {
for (aura::Window::Windows::const_iterator iter = container_children.begin(); for (aura::Window::Windows::const_iterator iter = container_children.begin();
iter != container_children.end(); iter != container_children.end();
++iter) { ++iter) {
if ((*iter)->type() == ui::wm::WINDOW_TYPE_NORMAL) if (IsValidWindow(*iter))
list.push_back(*iter); list.push_back(*iter);
} }
return list; return list;
} }
bool WindowListProviderImpl::IsWindowInList(aura::Window* window) const {
return window->parent() == container_ && IsValidWindow(window);
}
bool WindowListProviderImpl::IsValidWindow(aura::Window* window) const {
return window->type() == ui::wm::WINDOW_TYPE_NORMAL;
}
void WindowListProviderImpl::MoveToFront(aura::Window* window) {
DCHECK(IsWindowInList(window));
container_->StackChildAtTop(window);
}
void WindowListProviderImpl::StackWindowFrontOf(
aura::Window* window,
aura::Window* reference_window) {
DCHECK_NE(window, reference_window);
DCHECK(IsWindowInList(window));
DCHECK(IsWindowInList(reference_window));
container_->StackChildAbove(window, reference_window);
}
void WindowListProviderImpl::StackWindowBehindTo(
aura::Window* window,
aura::Window* reference_window) {
DCHECK_NE(window, reference_window);
DCHECK(IsWindowInList(window));
DCHECK(IsWindowInList(reference_window));
container_->StackChildBelow(window, reference_window);
}
void WindowListProviderImpl::OnWindowAdded(aura::Window* window) {
if (!IsValidWindow(window) || window->parent() != container_)
return;
DCHECK(IsWindowInList(window));
window->AddObserver(this);
}
void WindowListProviderImpl::OnWillRemoveWindow(aura::Window* window) {
if (!IsValidWindow(window) || window->parent() != container_)
return;
DCHECK(IsWindowInList(window));
window->RemoveObserver(this);
}
void WindowListProviderImpl::OnWindowStackingChanged(aura::Window* window) {
if (window == container_)
return;
DCHECK(IsWindowInList(window));
// Inform our listeners that the stacking has been changed.
FOR_EACH_OBSERVER(WindowListProviderObserver,
observers_,
OnWindowStackingChanged());
}
} // namespace athena } // namespace athena
...@@ -6,21 +6,40 @@ ...@@ -6,21 +6,40 @@
#define ATHENA_WM_WINDOW_LIST_PROVIDER_IMPL_H_ #define ATHENA_WM_WINDOW_LIST_PROVIDER_IMPL_H_
#include "athena/wm/public/window_list_provider.h" #include "athena/wm/public/window_list_provider.h"
#include "ui/aura/window_observer.h"
namespace athena { namespace athena {
class WindowListProviderObserver;
// This implementation of the WindowListProviderImpl uses the same order as in // This implementation of the WindowListProviderImpl uses the same order as in
// the container window's stacking order. // the container window's stacking order.
class ATHENA_EXPORT WindowListProviderImpl : public WindowListProvider { class ATHENA_EXPORT WindowListProviderImpl : public WindowListProvider,
public aura::WindowObserver {
public: public:
explicit WindowListProviderImpl(aura::Window* container); explicit WindowListProviderImpl(aura::Window* container);
virtual ~WindowListProviderImpl(); virtual ~WindowListProviderImpl();
private: private:
// WindowListProvider: // WindowListProvider:
virtual void AddObserver(WindowListProviderObserver* observer) OVERRIDE;
virtual void RemoveObserver(WindowListProviderObserver* observer) OVERRIDE;
virtual aura::Window::Windows GetWindowList() const OVERRIDE; virtual aura::Window::Windows GetWindowList() const OVERRIDE;
virtual bool IsWindowInList(aura::Window* window) const OVERRIDE;
virtual bool IsValidWindow(aura::Window* window) const OVERRIDE;
virtual void MoveToFront(aura::Window* window) OVERRIDE;
virtual void StackWindowFrontOf(aura::Window* window,
aura::Window*reference_window) OVERRIDE;
virtual void StackWindowBehindTo(aura::Window* window,
aura::Window*reference_window) OVERRIDE;
// aura::WindowObserver:
virtual void OnWindowAdded(aura::Window* new_window) OVERRIDE;
virtual void OnWillRemoveWindow(aura::Window* old_window) OVERRIDE;
virtual void OnWindowStackingChanged(aura::Window* window) OVERRIDE;
aura::Window* container_; aura::Window* container_;
ObserverList<WindowListProviderObserver> observers_;
DISALLOW_COPY_AND_ASSIGN(WindowListProviderImpl); DISALLOW_COPY_AND_ASSIGN(WindowListProviderImpl);
}; };
......
...@@ -7,6 +7,7 @@ ...@@ -7,6 +7,7 @@
#include <algorithm> #include <algorithm>
#include "athena/test/athena_test_base.h" #include "athena/test/athena_test_base.h"
#include "athena/wm/public/window_list_provider_observer.h"
#include "ui/aura/test/test_window_delegate.h" #include "ui/aura/test/test_window_delegate.h"
#include "ui/aura/window.h" #include "ui/aura/window.h"
...@@ -28,6 +29,56 @@ scoped_ptr<aura::Window> CreateWindow(aura::WindowDelegate* delegate, ...@@ -28,6 +29,56 @@ scoped_ptr<aura::Window> CreateWindow(aura::WindowDelegate* delegate,
return window.Pass(); return window.Pass();
} }
// Return a string which defines the order of windows in |now| using the indices
// of |original|. The string will then have the lowest/oldest window on the left
// and the highest / newest on the right.
std::string GetWindowOrder(const aura::Window::Windows& original,
const aura::Window::Windows& now) {
if (original.size() != now.size())
return "size has changed.";
std::string output;
for (aura::Window::Windows::const_iterator it = now.begin();
it != now.end(); ++it) {
for (size_t i = 0; i < original.size(); i++) {
if ((*it) == original[i]) {
output += (output.size() ? " " : std::string()) +
std::to_string(i + 1);
break;
}
}
}
return output;
}
class WindowListObserver : public WindowListProviderObserver {
public:
explicit WindowListObserver(WindowListProvider* provider)
: calls_(0),
provider_(provider) {
provider_->AddObserver(this);
}
virtual ~WindowListObserver() {
provider_->RemoveObserver(this);
}
int calls() const { return calls_; }
// WindowListProviderObserver:
virtual void OnWindowStackingChanged() OVERRIDE {
calls_++;
}
private:
// The number of calls to the observer.
int calls_;
// The associated WindowListProvider which is observed.
WindowListProvider* provider_;
DISALLOW_COPY_AND_ASSIGN(WindowListObserver);
};
} // namespace } // namespace
typedef test::AthenaTestBase WindowListProviderImplTest; typedef test::AthenaTestBase WindowListProviderImplTest;
...@@ -58,6 +109,7 @@ TEST_F(WindowListProviderImplTest, StackingOrder) { ...@@ -58,6 +109,7 @@ TEST_F(WindowListProviderImplTest, StackingOrder) {
EXPECT_EQ(first.get(), container->children().back()); EXPECT_EQ(first.get(), container->children().back());
} }
// Tests that only normal windows of the associated container will be listed.
TEST_F(WindowListProviderImplTest, ListContainsOnlyNormalWindows) { TEST_F(WindowListProviderImplTest, ListContainsOnlyNormalWindows) {
aura::test::TestWindowDelegate delegate; aura::test::TestWindowDelegate delegate;
scoped_ptr<aura::Window> container(new aura::Window(&delegate)); scoped_ptr<aura::Window> container(new aura::Window(&delegate));
...@@ -76,6 +128,7 @@ TEST_F(WindowListProviderImplTest, ListContainsOnlyNormalWindows) { ...@@ -76,6 +128,7 @@ TEST_F(WindowListProviderImplTest, ListContainsOnlyNormalWindows) {
scoped_ptr<WindowListProvider> list_provider( scoped_ptr<WindowListProvider> list_provider(
new WindowListProviderImpl(container.get())); new WindowListProviderImpl(container.get()));
const aura::Window::Windows list = list_provider->GetWindowList(); const aura::Window::Windows list = list_provider->GetWindowList();
EXPECT_EQ(list.end(), std::find(list.begin(), list.end(), second.get())); EXPECT_EQ(list.end(), std::find(list.begin(), list.end(), second.get()));
EXPECT_EQ(list.end(), std::find(list.begin(), list.end(), fourth.get())); EXPECT_EQ(list.end(), std::find(list.begin(), list.end(), fourth.get()));
...@@ -83,4 +136,114 @@ TEST_F(WindowListProviderImplTest, ListContainsOnlyNormalWindows) { ...@@ -83,4 +136,114 @@ TEST_F(WindowListProviderImplTest, ListContainsOnlyNormalWindows) {
EXPECT_NE(list.end(), std::find(list.begin(), list.end(), third.get())); EXPECT_NE(list.end(), std::find(list.begin(), list.end(), third.get()));
} }
// Testing that IsValidWidow, IsWindowInList and AddWindow work as expected.
TEST_F(WindowListProviderImplTest, SimpleChecks) {
aura::test::TestWindowDelegate delegate;
scoped_ptr<aura::Window> container(new aura::Window(&delegate));
scoped_ptr<aura::Window> normal_window =
CreateWindow(&delegate, ui::wm::WINDOW_TYPE_NORMAL);
scoped_ptr<aura::Window> popup_window =
CreateWindow(&delegate, ui::wm::WINDOW_TYPE_POPUP);
scoped_ptr<aura::Window> menu_window =
CreateWindow(&delegate, ui::wm::WINDOW_TYPE_MENU);
scoped_ptr<WindowListProvider> list_provider(
new WindowListProviderImpl(container.get()));
// Check which windows are valid and which are not.
EXPECT_TRUE(list_provider->IsValidWindow(normal_window.get()));
EXPECT_FALSE(list_provider->IsValidWindow(popup_window.get()));
EXPECT_FALSE(list_provider->IsValidWindow(menu_window.get()));
// Check that no window is currently in the list.
EXPECT_FALSE(list_provider->IsWindowInList(normal_window.get()));
EXPECT_FALSE(list_provider->IsWindowInList(popup_window.get()));
EXPECT_FALSE(list_provider->IsWindowInList(menu_window.get()));
// Check that adding the window will add it to the list.
container->AddChild(normal_window.get());
EXPECT_TRUE(list_provider->IsWindowInList(normal_window.get()));
}
// Testing that window ordering functions work as expected.
TEST_F(WindowListProviderImplTest, TestWindowOrderingFunctions) {
aura::test::TestWindowDelegate delegate;
scoped_ptr<aura::Window> container(new aura::Window(&delegate));
scoped_ptr<aura::Window> window1 =
CreateWindow(&delegate, ui::wm::WINDOW_TYPE_NORMAL);
scoped_ptr<aura::Window> window2 =
CreateWindow(&delegate, ui::wm::WINDOW_TYPE_NORMAL);
scoped_ptr<aura::Window> window3 =
CreateWindow(&delegate, ui::wm::WINDOW_TYPE_NORMAL);
scoped_ptr<WindowListProvider> list_provider(
new WindowListProviderImpl(container.get()));
scoped_ptr<WindowListObserver> observer(
new WindowListObserver(list_provider.get()));
EXPECT_FALSE(list_provider->IsWindowInList(window1.get()));
EXPECT_FALSE(list_provider->IsWindowInList(window2.get()));
EXPECT_FALSE(list_provider->IsWindowInList(window3.get()));
// Add the windows.
container->AddChild(window1.get());
container->AddChild(window2.get());
container->AddChild(window3.get());
aura::Window::Windows original_order = list_provider->GetWindowList();
ASSERT_EQ(3U, original_order.size());
EXPECT_EQ(original_order[0], window1.get());
EXPECT_EQ(original_order[1], window2.get());
EXPECT_EQ(original_order[2], window3.get());
EXPECT_EQ(0, observer.get()->calls());
// Move 2 to the front.
list_provider->MoveToFront(window2.get());
EXPECT_EQ("1 3 2", GetWindowOrder(original_order,
list_provider->GetWindowList()));
EXPECT_EQ(1, observer->calls());
// Move 2 to the front again. Should not change anything.
list_provider->MoveToFront(window2.get());
EXPECT_EQ("1 3 2", GetWindowOrder(original_order,
list_provider->GetWindowList()));
EXPECT_EQ(1, observer->calls());
// Move 1 (from the back) in front of 3.
list_provider->StackWindowFrontOf(window1.get(), window3.get());
EXPECT_EQ("3 1 2", GetWindowOrder(original_order,
list_provider->GetWindowList()));
EXPECT_EQ(2, observer->calls());
// Move 2 (from the front) in front of 3.
list_provider->StackWindowFrontOf(window2.get(), window3.get());
EXPECT_EQ("3 2 1", GetWindowOrder(original_order,
list_provider->GetWindowList()));
EXPECT_EQ(3, observer->calls());
// Move 1 (from the front) behind 3.
list_provider->StackWindowBehindTo(window1.get(), window3.get());
EXPECT_EQ("1 3 2", GetWindowOrder(original_order,
list_provider->GetWindowList()));
EXPECT_EQ(4, observer->calls());
// Move 1 (from the back) in front of 2.
list_provider->StackWindowFrontOf(window1.get(), window2.get());
EXPECT_EQ("3 2 1", GetWindowOrder(original_order,
list_provider->GetWindowList()));
EXPECT_EQ(5, observer->calls());
// Test that no change should also report no call.
list_provider->StackWindowFrontOf(window1.get(), window2.get());
EXPECT_EQ("3 2 1", GetWindowOrder(original_order,
list_provider->GetWindowList()));
EXPECT_EQ(5, observer->calls());
list_provider->StackWindowBehindTo(window2.get(), window1.get());
EXPECT_EQ("3 2 1", GetWindowOrder(original_order,
list_provider->GetWindowList()));
EXPECT_EQ(5, observer->calls());
}
} // namespace athena } // namespace athena
...@@ -184,11 +184,8 @@ void WindowManagerImpl::SetInOverview(bool active) { ...@@ -184,11 +184,8 @@ void WindowManagerImpl::SetInOverview(bool active) {
if (active) { if (active) {
FOR_EACH_OBSERVER(WindowManagerObserver, observers_, OnOverviewModeEnter()); FOR_EACH_OBSERVER(WindowManagerObserver, observers_, OnOverviewModeEnter());
// Re-stack all windows in the order defined by window_list_provider_. // Note: The window_list_provider_ resembles the exact window list of the
aura::Window::Windows window_list = window_list_provider_->GetWindowList(); // container, so no re-stacking is required before showing the OverviewMode.
aura::Window::Windows::iterator it;
for (it = window_list.begin(); it != window_list.end(); ++it)
container_->StackChildAtTop(*it);
overview_ = WindowOverviewMode::Create( overview_ = WindowOverviewMode::Create(
container_.get(), window_list_provider_.get(), container_.get(), window_list_provider_.get(),
split_view_controller_.get(), this); split_view_controller_.get(), this);
...@@ -221,6 +218,10 @@ void WindowManagerImpl::ToggleSplitViewForTest() { ...@@ -221,6 +218,10 @@ void WindowManagerImpl::ToggleSplitViewForTest() {
ToggleSplitview(); ToggleSplitview();
} }
WindowListProvider* WindowManagerImpl::GetWindowListProvider() {
return window_list_provider_.get();
}
void WindowManagerImpl::OnSelectWindow(aura::Window* window) { void WindowManagerImpl::OnSelectWindow(aura::Window* window) {
if (split_view_controller_->IsSplitViewModeActive()) { if (split_view_controller_->IsSplitViewModeActive()) {
split_view_controller_->DeactivateSplitMode(); split_view_controller_->DeactivateSplitMode();
......
...@@ -62,6 +62,7 @@ class WindowManagerImpl : public WindowManager, ...@@ -62,6 +62,7 @@ class WindowManagerImpl : public WindowManager,
virtual void AddObserver(WindowManagerObserver* observer) OVERRIDE; virtual void AddObserver(WindowManagerObserver* observer) OVERRIDE;
virtual void RemoveObserver(WindowManagerObserver* observer) OVERRIDE; virtual void RemoveObserver(WindowManagerObserver* observer) OVERRIDE;
virtual void ToggleSplitViewForTest() OVERRIDE; virtual void ToggleSplitViewForTest() OVERRIDE;
virtual WindowListProvider* GetWindowListProvider() OVERRIDE;
// WindowOverviewModeDelegate: // WindowOverviewModeDelegate:
virtual void OnSelectWindow(aura::Window* window) OVERRIDE; virtual void OnSelectWindow(aura::Window* window) OVERRIDE;
......
...@@ -162,9 +162,6 @@ TEST_F(WindowManagerTest, BezelGestureToSwitchBetweenWindows) { ...@@ -162,9 +162,6 @@ TEST_F(WindowManagerTest, BezelGestureToSwitchBetweenWindows) {
EXPECT_TRUE(wm::IsActiveWindow(second.get())); EXPECT_TRUE(wm::IsActiveWindow(second.get()));
EXPECT_EQ(second.get(), EXPECT_EQ(second.get(),
wm_api.GetWindowListProvider()->GetWindowList().back()); wm_api.GetWindowListProvider()->GetWindowList().back());
EXPECT_FALSE(first->IsVisible());
EXPECT_TRUE(second->IsVisible());
EXPECT_FALSE(third->IsVisible());
} }
TEST_F(WindowManagerTest, TitleDragSwitchBetweenWindows) { TEST_F(WindowManagerTest, TitleDragSwitchBetweenWindows) {
......
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