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
3 // found in the LICENSE file.
5 #include "ash/shelf/shelf_window_watcher.h"
7 #include "ash/ash_switches.h"
8 #include "ash/shelf/shelf_item_types.h"
9 #include "ash/shelf/shelf_model.h"
10 #include "ash/shelf/shelf_util.h"
11 #include "ash/shell.h"
12 #include "ash/shell_window_ids.h"
13 #include "ash/test/ash_test_base.h"
14 #include "ash/test/shell_test_api.h"
15 #include "ash/wm/window_resizer.h"
16 #include "ash/wm/window_state.h"
17 #include "ash/wm/window_util.h"
18 #include "base/command_line.h"
19 #include "ui/aura/client/aura_constants.h"
20 #include "ui/aura/window.h"
21 #include "ui/base/hit_test.h"
25 class ShelfWindowWatcherTest
: public test::AshTestBase
{
27 ShelfWindowWatcherTest() : model_(NULL
) {}
28 ~ShelfWindowWatcherTest() override
{}
30 void SetUp() override
{
31 test::AshTestBase::SetUp();
32 model_
= test::ShellTestApi(Shell::GetInstance()).shelf_model();
35 void TearDown() override
{
37 test::AshTestBase::TearDown();
40 ShelfID
CreateShelfItem(aura::Window
* window
) {
41 ShelfID id
= model_
->next_id();
42 ShelfItemDetails item_details
;
43 item_details
.type
= TYPE_PLATFORM_APP
;
44 SetShelfItemDetailsForWindow(window
, item_details
);
52 DISALLOW_COPY_AND_ASSIGN(ShelfWindowWatcherTest
);
55 TEST_F(ShelfWindowWatcherTest
, CreateAndRemoveShelfItem
) {
56 // ShelfModel only has an APP_LIST item.
57 EXPECT_EQ(1, model_
->item_count());
59 scoped_ptr
<aura::Window
> w1(CreateTestWindowInShellWithId(0));
60 scoped_ptr
<aura::Window
> w2(CreateTestWindowInShellWithId(0));
62 // Create a ShelfItem for w1.
63 ShelfID id_w1
= CreateShelfItem(w1
.get());
64 EXPECT_EQ(2, model_
->item_count());
66 int index_w1
= model_
->ItemIndexByID(id_w1
);
67 EXPECT_EQ(STATUS_RUNNING
, model_
->items()[index_w1
].status
);
69 // Create a ShelfItem for w2.
70 ShelfID id_w2
= CreateShelfItem(w2
.get());
71 EXPECT_EQ(3, model_
->item_count());
73 int index_w2
= model_
->ItemIndexByID(id_w2
);
74 EXPECT_EQ(STATUS_RUNNING
, model_
->items()[index_w2
].status
);
76 // ShelfItem is removed when assoicated window is destroyed.
77 ClearShelfItemDetailsForWindow(w1
.get());
78 EXPECT_EQ(2, model_
->item_count());
79 ClearShelfItemDetailsForWindow(w2
.get());
80 EXPECT_EQ(1, model_
->item_count());
81 // Clears twice doesn't do anything.
82 ClearShelfItemDetailsForWindow(w2
.get());
83 EXPECT_EQ(1, model_
->item_count());
87 TEST_F(ShelfWindowWatcherTest
, ActivateWindow
) {
88 // ShelfModel only have APP_LIST item.
89 EXPECT_EQ(1, model_
->item_count());
90 scoped_ptr
<aura::Window
> w1(CreateTestWindowInShellWithId(0));
91 scoped_ptr
<aura::Window
> w2(CreateTestWindowInShellWithId(0));
93 // Create a ShelfItem for w1.
94 ShelfID id_w1
= CreateShelfItem(w1
.get());
95 EXPECT_EQ(2, model_
->item_count());
96 int index_w1
= model_
->ItemIndexByID(id_w1
);
97 EXPECT_EQ(STATUS_RUNNING
, model_
->items()[index_w1
].status
);
99 // Create a ShelfItem for w2.
100 ShelfID id_w2
= CreateShelfItem(w2
.get());
101 EXPECT_EQ(3, model_
->item_count());
102 int index_w2
= model_
->ItemIndexByID(id_w2
);
103 EXPECT_EQ(STATUS_RUNNING
, model_
->items()[index_w1
].status
);
104 EXPECT_EQ(STATUS_RUNNING
, model_
->items()[index_w2
].status
);
106 // ShelfItem for w1 is active when w1 is activated.
107 wm::ActivateWindow(w1
.get());
108 EXPECT_EQ(STATUS_ACTIVE
, model_
->items()[index_w1
].status
);
110 // ShelfItem for w2 is active state when w2 is activated.
111 wm::ActivateWindow(w2
.get());
112 EXPECT_EQ(STATUS_RUNNING
, model_
->items()[index_w1
].status
);
113 EXPECT_EQ(STATUS_ACTIVE
, model_
->items()[index_w2
].status
);
116 TEST_F(ShelfWindowWatcherTest
, UpdateWindowProperty
) {
117 // ShelfModel only has an APP_LIST item.
118 EXPECT_EQ(1, model_
->item_count());
120 scoped_ptr
<aura::Window
> window(CreateTestWindowInShellWithId(0));
122 // Create a ShelfItem for |window|.
123 ShelfID id
= CreateShelfItem(window
.get());
124 EXPECT_EQ(2, model_
->item_count());
126 int index
= model_
->ItemIndexByID(id
);
127 EXPECT_EQ(STATUS_RUNNING
, model_
->items()[index
].status
);
129 // Update ShelfItem for |window|.
130 ShelfItemDetails details
;
131 details
.type
= TYPE_PLATFORM_APP
;
133 SetShelfItemDetailsForWindow(window
.get(), details
);
134 // No new item is created after updating a launcher item.
135 EXPECT_EQ(2, model_
->item_count());
136 // index and id are not changed after updating a launcher item.
137 EXPECT_EQ(index
, model_
->ItemIndexByID(id
));
138 EXPECT_EQ(id
, model_
->items()[index
].id
);
141 TEST_F(ShelfWindowWatcherTest
, MaximizeAndRestoreWindow
) {
142 // ShelfModel only has an APP_LIST item.
143 EXPECT_EQ(1, model_
->item_count());
145 scoped_ptr
<aura::Window
> window(CreateTestWindowInShellWithId(0));
146 wm::WindowState
* window_state
= wm::GetWindowState(window
.get());
148 // Create a ShelfItem for |window|.
149 ShelfID id
= CreateShelfItem(window
.get());
150 EXPECT_EQ(2, model_
->item_count());
152 int index
= model_
->ItemIndexByID(id
);
153 EXPECT_EQ(STATUS_RUNNING
, model_
->items()[index
].status
);
155 // Maximize window |window|.
156 EXPECT_FALSE(window_state
->IsMaximized());
157 window_state
->Maximize();
158 EXPECT_TRUE(window_state
->IsMaximized());
159 // No new item is created after maximizing a window |window|.
160 EXPECT_EQ(2, model_
->item_count());
161 // index and id are not changed after maximizing a window |window|.
162 EXPECT_EQ(index
, model_
->ItemIndexByID(id
));
163 EXPECT_EQ(id
, model_
->items()[index
].id
);
165 // Restore window |window|.
166 window_state
->Restore();
167 EXPECT_FALSE(window_state
->IsMaximized());
168 // No new item is created after restoring a window |window|.
169 EXPECT_EQ(2, model_
->item_count());
170 // Index and id are not changed after maximizing a window |window|.
171 EXPECT_EQ(index
, model_
->ItemIndexByID(id
));
172 EXPECT_EQ(id
, model_
->items()[index
].id
);
175 // Check that an item is removed when its associated Window is re-parented.
176 TEST_F(ShelfWindowWatcherTest
, ReparentWindow
) {
177 // ShelfModel only has an APP_LIST item.
178 EXPECT_EQ(1, model_
->item_count());
180 scoped_ptr
<aura::Window
> window(CreateTestWindowInShellWithId(0));
181 window
->set_owned_by_parent(false);
183 // Create a ShelfItem for |window|.
184 ShelfID id
= CreateShelfItem(window
.get());
185 EXPECT_EQ(2, model_
->item_count());
187 int index
= model_
->ItemIndexByID(id
);
188 EXPECT_EQ(STATUS_RUNNING
, model_
->items()[index
].status
);
190 aura::Window
* root_window
= window
->GetRootWindow();
191 aura::Window
* default_container
= Shell::GetContainer(
193 kShellWindowId_DefaultContainer
);
194 EXPECT_EQ(default_container
, window
->parent());
196 aura::Window
* new_parent
= Shell::GetContainer(
198 kShellWindowId_PanelContainer
);
200 // Check |window|'s item is removed when it is re-parented to |new_parent|
201 // which is not default container.
202 new_parent
->AddChild(window
.get());
203 EXPECT_EQ(1, model_
->item_count());
205 // Check |window|'s item is added when it is re-parented to
206 // |default_container|.
207 default_container
->AddChild(window
.get());
208 EXPECT_EQ(2, model_
->item_count());
211 // Check |window|'s item is not changed during the dragging.
212 // TODO(simonhong): Add a test for removing a Window during the dragging.
213 TEST_F(ShelfWindowWatcherTest
, DragWindow
) {
214 // ShelfModel only has an APP_LIST item.
215 EXPECT_EQ(1, model_
->item_count());
217 scoped_ptr
<aura::Window
> window(CreateTestWindowInShellWithId(0));
219 // Create a ShelfItem for |window|.
220 ShelfID id
= CreateShelfItem(window
.get());
221 EXPECT_EQ(2, model_
->item_count());
223 int index
= model_
->ItemIndexByID(id
);
224 EXPECT_EQ(STATUS_RUNNING
, model_
->items()[index
].status
);
226 // Simulate dragging of |window| and check its item is not changed.
227 scoped_ptr
<WindowResizer
> resizer(
228 CreateWindowResizer(window
.get(),
231 aura::client::WINDOW_MOVE_SOURCE_MOUSE
));
232 ASSERT_TRUE(resizer
.get());
233 resizer
->Drag(gfx::Point(50, 50), 0);
234 resizer
->CompleteDrag();
236 //Index and id are not changed after dragging a |window|.
237 EXPECT_EQ(index
, model_
->ItemIndexByID(id
));
238 EXPECT_EQ(id
, model_
->items()[index
].id
);
241 // Check |window|'s item is removed when it is re-parented not to default
242 // container during the dragging.
243 TEST_F(ShelfWindowWatcherTest
, ReparentWindowDuringTheDragging
) {
244 // ShelfModel only has an APP_LIST item.
245 EXPECT_EQ(1, model_
->item_count());
247 scoped_ptr
<aura::Window
> window(CreateTestWindowInShellWithId(0));
248 window
->set_owned_by_parent(false);
250 // Create a ShelfItem for |window|.
251 ShelfID id
= CreateShelfItem(window
.get());
252 EXPECT_EQ(2, model_
->item_count());
253 int index
= model_
->ItemIndexByID(id
);
254 EXPECT_EQ(STATUS_RUNNING
, model_
->items()[index
].status
);
256 aura::Window
* root_window
= window
->GetRootWindow();
257 aura::Window
* default_container
= Shell::GetContainer(
259 kShellWindowId_DefaultContainer
);
260 EXPECT_EQ(default_container
, window
->parent());
262 aura::Window
* new_parent
= Shell::GetContainer(
264 kShellWindowId_PanelContainer
);
266 // Simulate re-parenting to |new_parent| during the dragging.
268 scoped_ptr
<WindowResizer
> resizer(
269 CreateWindowResizer(window
.get(),
272 aura::client::WINDOW_MOVE_SOURCE_MOUSE
));
273 ASSERT_TRUE(resizer
.get());
274 resizer
->Drag(gfx::Point(50, 50), 0);
275 resizer
->CompleteDrag();
276 EXPECT_EQ(2, model_
->item_count());
278 // Item should be removed when |window| is re-parented not to default
279 // container before fininshing the dragging.
280 EXPECT_TRUE(wm::GetWindowState(window
.get())->is_dragged());
281 new_parent
->AddChild(window
.get());
282 EXPECT_EQ(1, model_
->item_count());
284 EXPECT_FALSE(wm::GetWindowState(window
.get())->is_dragged());
285 EXPECT_EQ(1, model_
->item_count());