blob: b9ddf5c88fd4efa483b852696f65ac7d88392f6f [file] [log] [blame]
Bryce Lee840c5662017-04-13 10:02:51 -07001/*
2 * Copyright (C) 2017 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License
15 */
16
17package com.android.server.am;
18
Wale Ogunwale7e1f5f52017-10-18 15:19:59 -070019import static android.app.WindowConfiguration.ACTIVITY_TYPE_ASSISTANT;
20import static android.app.WindowConfiguration.ACTIVITY_TYPE_HOME;
Wale Ogunwale04a05ac2017-09-17 21:35:02 -070021import static android.app.WindowConfiguration.ACTIVITY_TYPE_STANDARD;
22import static android.app.WindowConfiguration.WINDOWING_MODE_FULLSCREEN;
Wale Ogunwale7e1f5f52017-10-18 15:19:59 -070023import static android.app.WindowConfiguration.WINDOWING_MODE_PINNED;
24import static android.app.WindowConfiguration.WINDOWING_MODE_SPLIT_SCREEN_PRIMARY;
25import static android.app.WindowConfiguration.WINDOWING_MODE_SPLIT_SCREEN_SECONDARY;
Bryce Lee18d51592017-10-25 10:22:19 -070026
Bryce Leeb0f993f2018-03-02 15:38:01 -080027import static com.android.server.am.ActivityStack.ActivityState.DESTROYED;
28import static com.android.server.am.ActivityStack.ActivityState.DESTROYING;
Bryce Leec4ab62a2018-03-05 14:19:26 -080029import static com.android.server.am.ActivityStack.ActivityState.PAUSING;
30import static com.android.server.am.ActivityStack.ActivityState.RESUMED;
Wale Ogunwale04a05ac2017-09-17 21:35:02 -070031import static com.android.server.am.ActivityStack.REMOVE_TASK_MODE_DESTROYING;
Bryce Lee18d51592017-10-25 10:22:19 -070032
Bryce Lee5daa3122017-04-19 10:40:42 -070033import static org.junit.Assert.assertEquals;
David Stevens18abd0e2017-08-17 14:55:47 -070034import static org.junit.Assert.assertFalse;
Bryce Lee840c5662017-04-13 10:02:51 -070035import static org.junit.Assert.assertNotNull;
36import static org.junit.Assert.assertNull;
Wale Ogunwale7e1f5f52017-10-18 15:19:59 -070037import static org.junit.Assert.assertTrue;
Bryce Leeb0f993f2018-03-02 15:38:01 -080038import static org.mockito.ArgumentMatchers.any;
39import static org.mockito.ArgumentMatchers.eq;
Bryce Lee271617a2018-03-15 10:39:12 -070040import static org.mockito.Mockito.anyInt;
41import static org.mockito.Mockito.doReturn;
Bryce Leeb0f993f2018-03-02 15:38:01 -080042import static org.mockito.Mockito.mock;
43import static org.mockito.Mockito.times;
44import static org.mockito.Mockito.verify;
Bryce Lee840c5662017-04-13 10:02:51 -070045
Bryce Leeb0f993f2018-03-02 15:38:01 -080046import android.app.servertransaction.DestroyActivityItem;
Bryce Lee3345c4e2017-04-25 07:40:41 -070047import android.content.pm.ActivityInfo;
Bryce Lee271617a2018-03-15 10:39:12 -070048import android.os.Debug;
Bryce Lee9f6affd2017-09-01 09:18:35 -070049import android.os.UserHandle;
Bryce Lee840c5662017-04-13 10:02:51 -070050import android.platform.test.annotations.Presubmit;
51import android.support.test.filters.SmallTest;
52import android.support.test.runner.AndroidJUnit4;
53
54import org.junit.runner.RunWith;
Wale Ogunwale04a05ac2017-09-17 21:35:02 -070055import org.junit.Before;
Bryce Lee840c5662017-04-13 10:02:51 -070056import org.junit.Test;
57
58/**
59 * Tests for the {@link ActivityStack} class.
60 *
61 * Build/Install/Run:
Wale Ogunwalebb285872018-03-01 13:05:30 -080062 * atest FrameworksServicesTests:com.android.server.am.ActivityStackTests
Bryce Lee840c5662017-04-13 10:02:51 -070063 */
64@SmallTest
65@Presubmit
66@RunWith(AndroidJUnit4.class)
67public class ActivityStackTests extends ActivityTestsBase {
Wale Ogunwale04a05ac2017-09-17 21:35:02 -070068 private ActivityManagerService mService;
69 private ActivityStackSupervisor mSupervisor;
70 private ActivityStack mStack;
71 private TaskRecord mTask;
72
73 @Before
74 @Override
75 public void setUp() throws Exception {
76 super.setUp();
77
78 mService = createActivityManagerService();
79 mSupervisor = mService.mStackSupervisor;
80 mStack = mService.mStackSupervisor.getDefaultDisplay().createStack(
81 WINDOWING_MODE_FULLSCREEN, ACTIVITY_TYPE_STANDARD, true /* onTop */);
Bryce Lee18d51592017-10-25 10:22:19 -070082 mTask = new TaskBuilder(mSupervisor).setStack(mStack).build();
Wale Ogunwale04a05ac2017-09-17 21:35:02 -070083 }
84
Bryce Lee840c5662017-04-13 10:02:51 -070085 @Test
86 public void testEmptyTaskCleanupOnRemove() throws Exception {
Wale Ogunwale04a05ac2017-09-17 21:35:02 -070087 assertNotNull(mTask.getWindowContainerController());
88 mStack.removeTask(mTask, "testEmptyTaskCleanupOnRemove", REMOVE_TASK_MODE_DESTROYING);
89 assertNull(mTask.getWindowContainerController());
Bryce Lee840c5662017-04-13 10:02:51 -070090 }
Bryce Lee5daa3122017-04-19 10:40:42 -070091
Bryce Lee840c5662017-04-13 10:02:51 -070092 @Test
93 public void testOccupiedTaskCleanupOnRemove() throws Exception {
Bryce Lee18d51592017-10-25 10:22:19 -070094 final ActivityRecord r = new ActivityBuilder(mService).setTask(mTask).build();
Wale Ogunwale04a05ac2017-09-17 21:35:02 -070095 assertNotNull(mTask.getWindowContainerController());
96 mStack.removeTask(mTask, "testOccupiedTaskCleanupOnRemove", REMOVE_TASK_MODE_DESTROYING);
97 assertNotNull(mTask.getWindowContainerController());
Bryce Lee840c5662017-04-13 10:02:51 -070098 }
Bryce Lee5daa3122017-04-19 10:40:42 -070099
100 @Test
Bryce Leec4ab62a2018-03-05 14:19:26 -0800101 public void testResumedActivity() throws Exception {
102 final ActivityRecord r = new ActivityBuilder(mService).setTask(mTask).build();
103 assertEquals(mStack.getResumedActivity(), null);
104 r.setState(RESUMED, "testResumedActivity");
105 assertEquals(mStack.getResumedActivity(), r);
106 r.setState(PAUSING, "testResumedActivity");
107 assertEquals(mStack.getResumedActivity(), null);
108
Bryce Lee5daa3122017-04-19 10:40:42 -0700109 }
Bryce Lee3345c4e2017-04-25 07:40:41 -0700110
111 @Test
Bryce Lee8cab4a02018-01-05 09:00:49 -0800112 public void testPrimarySplitScreenToFullscreenWhenMovedToBack() throws Exception {
113 // Create primary splitscreen stack. This will create secondary stacks and places the
114 // existing fullscreen stack on the bottom.
115 final ActivityStack primarySplitScreen = mService.mStackSupervisor.getDefaultDisplay()
116 .createStack(WINDOWING_MODE_SPLIT_SCREEN_PRIMARY, ACTIVITY_TYPE_STANDARD,
117 true /* onTop */);
118
119 // Assert windowing mode.
120 assertEquals(primarySplitScreen.getWindowingMode(), WINDOWING_MODE_SPLIT_SCREEN_PRIMARY);
121
122 // Move primary to back.
123 primarySplitScreen.moveToBack("testPrimarySplitScreenToFullscreenWhenMovedToBack",
124 null /* task */);
125
126 // Assert that stack is at the bottom.
127 assertEquals(mService.mStackSupervisor.getDefaultDisplay().getIndexOf(primarySplitScreen),
128 0);
129
130 // Ensure no longer in splitscreen.
131 assertEquals(primarySplitScreen.getWindowingMode(), WINDOWING_MODE_FULLSCREEN);
132 }
133
134 @Test
Bryce Lee3345c4e2017-04-25 07:40:41 -0700135 public void testStopActivityWhenActivityDestroyed() throws Exception {
Bryce Lee18d51592017-10-25 10:22:19 -0700136 final ActivityRecord r = new ActivityBuilder(mService).setTask(mTask).build();
Wale Ogunwale04a05ac2017-09-17 21:35:02 -0700137 r.info.flags |= ActivityInfo.FLAG_NO_HISTORY;
138 mSupervisor.setFocusStackUnchecked("testStopActivityWithDestroy", mStack);
139 mStack.stopActivityLocked(r);
140 // Mostly testing to make sure there is a crash in the call part, so if we get here we are
141 // good-to-go!
Bryce Lee3345c4e2017-04-25 07:40:41 -0700142 }
Bryce Lee9f6affd2017-09-01 09:18:35 -0700143
144 @Test
145 public void testFindTaskWithOverlay() throws Exception {
Bryce Lee18d51592017-10-25 10:22:19 -0700146 final ActivityRecord r = new ActivityBuilder(mService)
147 .setCreateTask(true)
148 .setStack(mStack)
149 .setUid(0)
150 .build();
151 final TaskRecord task = r.getTask();
Bryce Lee9f6affd2017-09-01 09:18:35 -0700152 // Overlay must be for a different user to prevent recognizing a matching top activity
Bryce Lee18d51592017-10-25 10:22:19 -0700153 final ActivityRecord taskOverlay = new ActivityBuilder(mService).setTask(task)
154 .setUid(UserHandle.PER_USER_RANGE * 2).build();
Bryce Lee9f6affd2017-09-01 09:18:35 -0700155 taskOverlay.mTaskOverlay = true;
156
Bryce Lee9f6affd2017-09-01 09:18:35 -0700157 final ActivityStackSupervisor.FindTaskResult result =
158 new ActivityStackSupervisor.FindTaskResult();
Wale Ogunwale04a05ac2017-09-17 21:35:02 -0700159 mStack.findTaskLocked(r, result);
Bryce Lee9f6affd2017-09-01 09:18:35 -0700160
Bryce Lee18d51592017-10-25 10:22:19 -0700161 assertEquals(task.getTopActivity(false /* includeOverlays */), r);
162 assertEquals(task.getTopActivity(true /* includeOverlays */), taskOverlay);
Bryce Lee9f6affd2017-09-01 09:18:35 -0700163 assertNotNull(result.r);
164 }
Wale Ogunwale7e1f5f52017-10-18 15:19:59 -0700165
166 @Test
167 public void testShouldBeVisible_Fullscreen() throws Exception {
168 final ActivityDisplay display = mService.mStackSupervisor.getDefaultDisplay();
169 final TestActivityStack homeStack = createStackForShouldBeVisibleTest(display,
170 WINDOWING_MODE_FULLSCREEN, ACTIVITY_TYPE_HOME, true /* onTop */);
171 final ActivityStack pinnedStack = createStackForShouldBeVisibleTest(display,
172 WINDOWING_MODE_PINNED, ACTIVITY_TYPE_STANDARD, true /* onTop */);
173
174 assertTrue(homeStack.shouldBeVisible(null /* starting */));
175 assertTrue(pinnedStack.shouldBeVisible(null /* starting */));
176
177 final TestActivityStack fullscreenStack = createStackForShouldBeVisibleTest(display,
178 WINDOWING_MODE_FULLSCREEN, ACTIVITY_TYPE_STANDARD, true /* onTop */);
179 // Home stack shouldn't be visible behind an opaque fullscreen stack, but pinned stack
180 // should be visible since it is always on-top.
181 fullscreenStack.setIsTranslucent(false);
182 assertFalse(homeStack.shouldBeVisible(null /* starting */));
183 assertTrue(pinnedStack.shouldBeVisible(null /* starting */));
184 assertTrue(fullscreenStack.shouldBeVisible(null /* starting */));
185
186 // Home stack should be visible behind a translucent fullscreen stack.
187 fullscreenStack.setIsTranslucent(true);
188 assertTrue(homeStack.shouldBeVisible(null /* starting */));
189 assertTrue(pinnedStack.shouldBeVisible(null /* starting */));
190 }
191
192 @Test
193 public void testShouldBeVisible_SplitScreen() throws Exception {
194 final ActivityDisplay display = mService.mStackSupervisor.getDefaultDisplay();
195 final TestActivityStack homeStack = createStackForShouldBeVisibleTest(display,
196 WINDOWING_MODE_FULLSCREEN, ACTIVITY_TYPE_HOME, true /* onTop */);
Wale Ogunwale30e441d2017-11-09 08:28:45 -0800197 // Home stack should always be fullscreen for this test.
198 homeStack.setSupportsSplitScreen(false);
Wale Ogunwale7e1f5f52017-10-18 15:19:59 -0700199 final TestActivityStack splitScreenPrimary = createStackForShouldBeVisibleTest(display,
200 WINDOWING_MODE_SPLIT_SCREEN_PRIMARY, ACTIVITY_TYPE_STANDARD, true /* onTop */);
201 final TestActivityStack splitScreenSecondary = createStackForShouldBeVisibleTest(display,
202 WINDOWING_MODE_SPLIT_SCREEN_SECONDARY, ACTIVITY_TYPE_STANDARD, true /* onTop */);
203
204 // Home stack shouldn't be visible if both halves of split-screen are opaque.
205 splitScreenPrimary.setIsTranslucent(false);
206 splitScreenSecondary.setIsTranslucent(false);
207 assertFalse(homeStack.shouldBeVisible(null /* starting */));
208 assertTrue(splitScreenPrimary.shouldBeVisible(null /* starting */));
209 assertTrue(splitScreenSecondary.shouldBeVisible(null /* starting */));
210
211 // Home stack should be visible if one of the halves of split-screen is translucent.
212 splitScreenPrimary.setIsTranslucent(true);
213 assertTrue(homeStack.shouldBeVisible(null /* starting */));
214 assertTrue(splitScreenPrimary.shouldBeVisible(null /* starting */));
215 assertTrue(splitScreenSecondary.shouldBeVisible(null /* starting */));
216
217 final TestActivityStack splitScreenSecondary2 = createStackForShouldBeVisibleTest(display,
218 WINDOWING_MODE_SPLIT_SCREEN_SECONDARY, ACTIVITY_TYPE_STANDARD, true /* onTop */);
219 // First split-screen secondary shouldn't be visible behind another opaque split-split
220 // secondary.
221 splitScreenSecondary2.setIsTranslucent(false);
222 assertFalse(splitScreenSecondary.shouldBeVisible(null /* starting */));
223 assertTrue(splitScreenSecondary2.shouldBeVisible(null /* starting */));
224
Wale Ogunwale8e923af2018-03-23 08:48:11 -0700225 // First split-screen secondary should be visible behind another translucent split-screen
Wale Ogunwale7e1f5f52017-10-18 15:19:59 -0700226 // secondary.
227 splitScreenSecondary2.setIsTranslucent(true);
228 assertTrue(splitScreenSecondary.shouldBeVisible(null /* starting */));
229 assertTrue(splitScreenSecondary2.shouldBeVisible(null /* starting */));
230
231 final TestActivityStack assistantStack = createStackForShouldBeVisibleTest(display,
232 WINDOWING_MODE_FULLSCREEN, ACTIVITY_TYPE_ASSISTANT, true /* onTop */);
233
234 // Split-screen stacks shouldn't be visible behind an opaque fullscreen stack.
235 assistantStack.setIsTranslucent(false);
236 assertTrue(assistantStack.shouldBeVisible(null /* starting */));
237 assertFalse(splitScreenPrimary.shouldBeVisible(null /* starting */));
238 assertFalse(splitScreenSecondary.shouldBeVisible(null /* starting */));
239 assertFalse(splitScreenSecondary2.shouldBeVisible(null /* starting */));
240
241 // Split-screen stacks should be visible behind a translucent fullscreen stack.
242 assistantStack.setIsTranslucent(true);
243 assertTrue(assistantStack.shouldBeVisible(null /* starting */));
244 assertTrue(splitScreenPrimary.shouldBeVisible(null /* starting */));
245 assertTrue(splitScreenSecondary.shouldBeVisible(null /* starting */));
246 assertTrue(splitScreenSecondary2.shouldBeVisible(null /* starting */));
Wale Ogunwale8e923af2018-03-23 08:48:11 -0700247
248 // Assistant stack shouldn't be visible behind translucent split-screen stack
249 assistantStack.setIsTranslucent(false);
250 splitScreenPrimary.setIsTranslucent(true);
251 splitScreenSecondary2.setIsTranslucent(true);
252 splitScreenSecondary2.moveToFront("testShouldBeVisible_SplitScreen");
253 splitScreenPrimary.moveToFront("testShouldBeVisible_SplitScreen");
254 assertFalse(assistantStack.shouldBeVisible(null /* starting */));
255 assertTrue(splitScreenPrimary.shouldBeVisible(null /* starting */));
256 assertTrue(splitScreenSecondary2.shouldBeVisible(null /* starting */));
Wale Ogunwale7e1f5f52017-10-18 15:19:59 -0700257 }
258
259 @Test
260 public void testShouldBeVisible_Finishing() throws Exception {
261 final ActivityDisplay display = mService.mStackSupervisor.getDefaultDisplay();
262 final TestActivityStack homeStack = createStackForShouldBeVisibleTest(display,
263 WINDOWING_MODE_FULLSCREEN, ACTIVITY_TYPE_HOME, true /* onTop */);
264 final TestActivityStack translucentStack = createStackForShouldBeVisibleTest(display,
265 WINDOWING_MODE_FULLSCREEN, ACTIVITY_TYPE_STANDARD, true /* onTop */);
266 translucentStack.setIsTranslucent(true);
267
268 assertTrue(homeStack.shouldBeVisible(null /* starting */));
269 assertTrue(translucentStack.shouldBeVisible(null /* starting */));
270
271 final ActivityRecord topRunningHomeActivity = homeStack.topRunningActivityLocked();
272 topRunningHomeActivity.finishing = true;
273 final ActivityRecord topRunningTranslucentActivity =
274 translucentStack.topRunningActivityLocked();
275 topRunningTranslucentActivity.finishing = true;
276
277 // Home shouldn't be visible since its activity is marked as finishing and it isn't the top
278 // of the stack list.
279 assertFalse(homeStack.shouldBeVisible(null /* starting */));
280 // Home should be visible if we are starting an activity within it.
281 assertTrue(homeStack.shouldBeVisible(topRunningHomeActivity /* starting */));
282 // The translucent stack should be visible since it is the top of the stack list even though
283 // it has its activity marked as finishing.
284 assertTrue(translucentStack.shouldBeVisible(null /* starting */));
285 }
286
Winson Chungd922b6b2018-02-16 16:41:50 -0800287 @Test
288 public void testMoveHomeStackBehindBottomMostVisibleStack_NoMoveHomeBehindFullscreen() {
289 final ActivityDisplay display = mService.mStackSupervisor.getDefaultDisplay();
290 display.removeChild(mStack);
291
292 final TestActivityStack homeStack = createStackForShouldBeVisibleTest(display,
293 WINDOWING_MODE_FULLSCREEN, ACTIVITY_TYPE_HOME, true /* onTop */);
294 final TestActivityStack fullscreenStack = createStackForShouldBeVisibleTest(display,
295 WINDOWING_MODE_FULLSCREEN, ACTIVITY_TYPE_STANDARD, true /* onTop */);
296
297 homeStack.setIsTranslucent(false);
298 fullscreenStack.setIsTranslucent(false);
299
300 // Ensure that we don't move the home stack if it is already behind the top fullscreen stack
301 int homeStackIndex = display.getIndexOf(homeStack);
302 assertTrue(display.getStackAboveHome() == fullscreenStack);
303 display.moveHomeStackBehindBottomMostVisibleStack();
304 assertTrue(display.getIndexOf(homeStack) == homeStackIndex);
305 }
306
307 @Test
308 public void testMoveHomeStackBehindBottomMostVisibleStack_NoMoveHomeBehindTranslucent() {
309 final ActivityDisplay display = mService.mStackSupervisor.getDefaultDisplay();
310 display.removeChild(mStack);
311
312 final TestActivityStack homeStack = createStackForShouldBeVisibleTest(display,
313 WINDOWING_MODE_FULLSCREEN, ACTIVITY_TYPE_HOME, true /* onTop */);
314 final TestActivityStack fullscreenStack = createStackForShouldBeVisibleTest(display,
315 WINDOWING_MODE_FULLSCREEN, ACTIVITY_TYPE_STANDARD, true /* onTop */);
316
317 homeStack.setIsTranslucent(false);
318 fullscreenStack.setIsTranslucent(true);
319
320 // Ensure that we don't move the home stack if it is already behind the top fullscreen stack
321 int homeStackIndex = display.getIndexOf(homeStack);
322 assertTrue(display.getStackAboveHome() == fullscreenStack);
323 display.moveHomeStackBehindBottomMostVisibleStack();
324 assertTrue(display.getIndexOf(homeStack) == homeStackIndex);
325 }
326
327 @Test
328 public void testMoveHomeStackBehindBottomMostVisibleStack_NoMoveHomeOnTop() {
329 final ActivityDisplay display = mService.mStackSupervisor.getDefaultDisplay();
330 display.removeChild(mStack);
331
332 final TestActivityStack fullscreenStack = createStackForShouldBeVisibleTest(display,
333 WINDOWING_MODE_FULLSCREEN, ACTIVITY_TYPE_STANDARD, true /* onTop */);
334 final TestActivityStack homeStack = createStackForShouldBeVisibleTest(display,
335 WINDOWING_MODE_FULLSCREEN, ACTIVITY_TYPE_HOME, true /* onTop */);
336
337 homeStack.setIsTranslucent(false);
338 fullscreenStack.setIsTranslucent(false);
339
340 // Ensure we don't move the home stack if it is already on top
341 int homeStackIndex = display.getIndexOf(homeStack);
342 assertTrue(display.getStackAboveHome() == null);
343 display.moveHomeStackBehindBottomMostVisibleStack();
344 assertTrue(display.getIndexOf(homeStack) == homeStackIndex);
345 }
346
347 @Test
348 public void testMoveHomeStackBehindBottomMostVisibleStack_MoveHomeBehindFullscreen() {
349 final ActivityDisplay display = mService.mStackSupervisor.getDefaultDisplay();
350 display.removeChild(mStack);
351
352 final TestActivityStack homeStack = createStackForShouldBeVisibleTest(display,
353 WINDOWING_MODE_FULLSCREEN, ACTIVITY_TYPE_HOME, true /* onTop */);
354 final TestActivityStack fullscreenStack1 = createStackForShouldBeVisibleTest(display,
355 WINDOWING_MODE_FULLSCREEN, ACTIVITY_TYPE_STANDARD, true /* onTop */);
356 final TestActivityStack fullscreenStack2 = createStackForShouldBeVisibleTest(display,
357 WINDOWING_MODE_FULLSCREEN, ACTIVITY_TYPE_STANDARD, true /* onTop */);
358 final TestActivityStack pinnedStack = createStackForShouldBeVisibleTest(display,
359 WINDOWING_MODE_PINNED, ACTIVITY_TYPE_STANDARD, true /* onTop */);
360
361 homeStack.setIsTranslucent(false);
362 fullscreenStack1.setIsTranslucent(false);
363 fullscreenStack2.setIsTranslucent(false);
364
365 // Ensure that we move the home stack behind the bottom most fullscreen stack, ignoring the
366 // pinned stack
367 assertTrue(display.getStackAboveHome() == fullscreenStack1);
368 display.moveHomeStackBehindBottomMostVisibleStack();
369 assertTrue(display.getStackAboveHome() == fullscreenStack2);
370 }
371
372 @Test
373 public void testMoveHomeStackBehindBottomMostVisibleStack_MoveHomeBehindFullscreenAndTranslucent() {
374 final ActivityDisplay display = mService.mStackSupervisor.getDefaultDisplay();
375 display.removeChild(mStack);
376
377 final TestActivityStack homeStack = createStackForShouldBeVisibleTest(display,
378 WINDOWING_MODE_FULLSCREEN, ACTIVITY_TYPE_HOME, true /* onTop */);
379 final TestActivityStack fullscreenStack1 = createStackForShouldBeVisibleTest(display,
380 WINDOWING_MODE_FULLSCREEN, ACTIVITY_TYPE_STANDARD, true /* onTop */);
381 final TestActivityStack fullscreenStack2 = createStackForShouldBeVisibleTest(display,
382 WINDOWING_MODE_FULLSCREEN, ACTIVITY_TYPE_STANDARD, true /* onTop */);
383
384 homeStack.setIsTranslucent(false);
385 fullscreenStack1.setIsTranslucent(false);
386 fullscreenStack2.setIsTranslucent(true);
387
388 // Ensure that we move the home stack behind the bottom most non-translucent fullscreen
389 // stack
390 assertTrue(display.getStackAboveHome() == fullscreenStack1);
391 display.moveHomeStackBehindBottomMostVisibleStack();
392 assertTrue(display.getStackAboveHome() == fullscreenStack1);
393 }
394
395 @Test
396 public void testMoveHomeStackBehindStack_BehindHomeStack() {
397 final ActivityDisplay display = mService.mStackSupervisor.getDefaultDisplay();
398 display.removeChild(mStack);
399
400 final TestActivityStack fullscreenStack1 = createStackForShouldBeVisibleTest(display,
401 WINDOWING_MODE_FULLSCREEN, ACTIVITY_TYPE_STANDARD, true /* onTop */);
402 final TestActivityStack fullscreenStack2 = createStackForShouldBeVisibleTest(display,
403 WINDOWING_MODE_FULLSCREEN, ACTIVITY_TYPE_STANDARD, true /* onTop */);
404 final TestActivityStack homeStack = createStackForShouldBeVisibleTest(display,
405 WINDOWING_MODE_FULLSCREEN, ACTIVITY_TYPE_HOME, true /* onTop */);
406
407 homeStack.setIsTranslucent(false);
408 fullscreenStack1.setIsTranslucent(false);
409 fullscreenStack2.setIsTranslucent(false);
410
411 // Ensure we don't move the home stack behind itself
412 int homeStackIndex = display.getIndexOf(homeStack);
413 display.moveHomeStackBehindStack(homeStack);
414 assertTrue(display.getIndexOf(homeStack) == homeStackIndex);
415 }
416
417 @Test
418 public void testMoveHomeStackBehindStack() {
419 final ActivityDisplay display = mService.mStackSupervisor.getDefaultDisplay();
420 display.removeChild(mStack);
421
422 final TestActivityStack fullscreenStack1 = createStackForShouldBeVisibleTest(display,
423 WINDOWING_MODE_FULLSCREEN, ACTIVITY_TYPE_STANDARD, true /* onTop */);
424 final TestActivityStack fullscreenStack2 = createStackForShouldBeVisibleTest(display,
425 WINDOWING_MODE_FULLSCREEN, ACTIVITY_TYPE_STANDARD, true /* onTop */);
Winson Chung123e07a2018-02-27 11:47:16 -0800426 final TestActivityStack fullscreenStack3 = createStackForShouldBeVisibleTest(display,
427 WINDOWING_MODE_FULLSCREEN, ACTIVITY_TYPE_STANDARD, true /* onTop */);
428 final TestActivityStack fullscreenStack4 = createStackForShouldBeVisibleTest(display,
429 WINDOWING_MODE_FULLSCREEN, ACTIVITY_TYPE_STANDARD, true /* onTop */);
Winson Chungd922b6b2018-02-16 16:41:50 -0800430 final TestActivityStack homeStack = createStackForShouldBeVisibleTest(display,
431 WINDOWING_MODE_FULLSCREEN, ACTIVITY_TYPE_HOME, true /* onTop */);
432
433 display.moveHomeStackBehindStack(fullscreenStack1);
434 assertTrue(display.getStackAboveHome() == fullscreenStack1);
435 display.moveHomeStackBehindStack(fullscreenStack2);
436 assertTrue(display.getStackAboveHome() == fullscreenStack2);
Winson Chung123e07a2018-02-27 11:47:16 -0800437 display.moveHomeStackBehindStack(fullscreenStack4);
438 assertTrue(display.getStackAboveHome() == fullscreenStack4);
439 display.moveHomeStackBehindStack(fullscreenStack2);
440 assertTrue(display.getStackAboveHome() == fullscreenStack2);
Winson Chungd922b6b2018-02-16 16:41:50 -0800441 }
442
Wale Ogunwalebb285872018-03-01 13:05:30 -0800443 @Test
444 public void testSplitScreenMoveToFront() throws Exception {
445 final ActivityDisplay display = mService.mStackSupervisor.getDefaultDisplay();
446 final TestActivityStack splitScreenPrimary = createStackForShouldBeVisibleTest(display,
447 WINDOWING_MODE_SPLIT_SCREEN_PRIMARY, ACTIVITY_TYPE_STANDARD, true /* onTop */);
448 final TestActivityStack splitScreenSecondary = createStackForShouldBeVisibleTest(display,
449 WINDOWING_MODE_SPLIT_SCREEN_SECONDARY, ACTIVITY_TYPE_STANDARD, true /* onTop */);
450 final TestActivityStack assistantStack = createStackForShouldBeVisibleTest(display,
451 WINDOWING_MODE_FULLSCREEN, ACTIVITY_TYPE_ASSISTANT, true /* onTop */);
452
453 splitScreenPrimary.setIsTranslucent(false);
454 splitScreenSecondary.setIsTranslucent(false);
455 assistantStack.setIsTranslucent(false);
456
457 assertFalse(splitScreenPrimary.shouldBeVisible(null /* starting */));
458 assertFalse(splitScreenSecondary.shouldBeVisible(null /* starting */));
459 assertTrue(assistantStack.shouldBeVisible(null /* starting */));
460
461 splitScreenSecondary.moveToFront("testSplitScreenMoveToFront");
462
463 assertTrue(splitScreenPrimary.shouldBeVisible(null /* starting */));
464 assertTrue(splitScreenSecondary.shouldBeVisible(null /* starting */));
465 assertFalse(assistantStack.shouldBeVisible(null /* starting */));
466 }
467
Wale Ogunwale7e1f5f52017-10-18 15:19:59 -0700468 private <T extends ActivityStack> T createStackForShouldBeVisibleTest(
469 ActivityDisplay display, int windowingMode, int activityType, boolean onTop) {
470 final T stack = display.createStack(windowingMode, activityType, onTop);
Bryce Lee18d51592017-10-25 10:22:19 -0700471 final ActivityRecord r = new ActivityBuilder(mService).setUid(0).setStack(stack)
472 .setCreateTask(true).build();
Wale Ogunwale7e1f5f52017-10-18 15:19:59 -0700473 return stack;
474 }
Bryce Leeb0f993f2018-03-02 15:38:01 -0800475
476 @Test
Bryce Leefbd263b42018-03-07 10:33:55 -0800477 public void testFinishDisabledPackageActivities() throws Exception {
478 final ActivityRecord firstActivity = new ActivityBuilder(mService).setTask(mTask).build();
479 final ActivityRecord secondActivity = new ActivityBuilder(mService).setTask(mTask).build();
480
481 // Making the second activity a task overlay without an app means it will be removed from
482 // the task's activities as well once first activity is removed.
483 secondActivity.mTaskOverlay = true;
484 secondActivity.app = null;
485
486 assertEquals(mTask.mActivities.size(), 2);
487
488 mStack.finishDisabledPackageActivitiesLocked(firstActivity.packageName, null,
489 true /* doit */, true /* evenPersistent */, UserHandle.USER_ALL);
490
491 assertTrue(mTask.mActivities.isEmpty());
492 assertTrue(mStack.getAllTasks().isEmpty());
493 }
494
495 @Test
496 public void testHandleAppDied() throws Exception {
497 final ActivityRecord firstActivity = new ActivityBuilder(mService).setTask(mTask).build();
498 final ActivityRecord secondActivity = new ActivityBuilder(mService).setTask(mTask).build();
499
500 // Making the first activity a task overlay means it will be removed from the task's
501 // activities as well once second activity is removed as handleAppDied processes the
502 // activity list in reverse.
503 firstActivity.mTaskOverlay = true;
504 firstActivity.app = null;
505
506 // second activity will be immediately removed as it has no state.
507 secondActivity.haveState = false;
508
509 assertEquals(mTask.mActivities.size(), 2);
510
511 mStack.handleAppDiedLocked(secondActivity.app);
512
513 assertTrue(mTask.mActivities.isEmpty());
514 assertTrue(mStack.getAllTasks().isEmpty());
515 }
Bryce Lee271617a2018-03-15 10:39:12 -0700516
517 @Test
518 public void testShouldSleepActivities() throws Exception {
519 // When focused activity and keyguard is going away, we should not sleep regardless
520 // of the display state
521 verifyShouldSleepActivities(true /* focusedStack */, true /*keyguardGoingAway*/,
522 true /* displaySleeping */, false /* expected*/);
523
524 // When not the focused stack, defer to display sleeping state.
525 verifyShouldSleepActivities(false /* focusedStack */, true /*keyguardGoingAway*/,
526 true /* displaySleeping */, true /* expected*/);
527
528 // If keyguard is going away, defer to the display sleeping state.
529 verifyShouldSleepActivities(true /* focusedStack */, false /*keyguardGoingAway*/,
530 true /* displaySleeping */, true /* expected*/);
531 verifyShouldSleepActivities(true /* focusedStack */, false /*keyguardGoingAway*/,
532 false /* displaySleeping */, false /* expected*/);
533 }
534
535 private void verifyShouldSleepActivities(boolean focusedStack,
536 boolean keyguardGoingAway, boolean displaySleeping, boolean expected) {
537 mSupervisor.mFocusedStack = focusedStack ? mStack : null;
538
539 final ActivityDisplay display = mock(ActivityDisplay.class);
540 final KeyguardController keyguardController = mSupervisor.getKeyguardController();
541
542 doReturn(display).when(mSupervisor).getActivityDisplay(anyInt());
543 doReturn(keyguardGoingAway).when(keyguardController).isKeyguardGoingAway();
544 doReturn(displaySleeping).when(display).isSleeping();
545
546 assertEquals(expected, mStack.shouldSleepActivities());
547 }
548
Bryce Lee840c5662017-04-13 10:02:51 -0700549}