blob: 5d0788881704db6f7140af2d935ad9a8a1ca5dd8 [file] [log] [blame]
Garfield Tan9b1efea2017-12-05 16:43:46 -08001/*
Wale Ogunwale59507092018-10-29 09:00:30 -07002 * Copyright (C) 2018 The Android Open Source Project
Garfield Tan9b1efea2017-12-05 16:43:46 -08003 *
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
Wale Ogunwale59507092018-10-29 09:00:30 -070014 * limitations under the License
Garfield Tan9b1efea2017-12-05 16:43:46 -080015 */
16
Wale Ogunwale59507092018-10-29 09:00:30 -070017package com.android.server.wm;
Garfield Tan9b1efea2017-12-05 16:43:46 -080018
Evan Rosky1ac84462018-11-13 11:25:30 -080019import static android.app.WindowConfiguration.ACTIVITY_TYPE_STANDARD;
20import static android.app.WindowConfiguration.WINDOWING_MODE_FREEFORM;
21import static android.app.WindowConfiguration.WINDOWING_MODE_FULLSCREEN;
Bryce Lee1a990e52018-04-23 10:54:11 -070022import static android.content.Intent.FLAG_ACTIVITY_NEW_TASK;
23import static android.content.Intent.FLAG_ACTIVITY_TASK_ON_HOME;
Evan Rosky730f6e82018-12-03 17:40:11 -080024import static android.content.pm.ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE;
25import static android.content.pm.ActivityInfo.SCREEN_ORIENTATION_PORTRAIT;
26import static android.content.pm.ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED;
Riddle Hsu88e3c8732019-02-18 19:15:12 +080027import static android.util.DisplayMetrics.DENSITY_DEFAULT;
Evan Rosky730f6e82018-12-03 17:40:11 -080028
29import static com.android.server.wm.WindowContainer.POSITION_TOP;
Bryce Lee1a990e52018-04-23 10:54:11 -070030
Riddle Hsu2f9acd22018-11-06 23:44:43 +080031import static org.hamcrest.Matchers.not;
32import static org.hamcrest.Matchers.sameInstance;
Garfield Tan367b35a2017-12-13 12:16:21 -080033import static org.junit.Assert.assertEquals;
Garfield Tan9b1efea2017-12-05 16:43:46 -080034import static org.junit.Assert.assertFalse;
35import static org.junit.Assert.assertNotNull;
Riddle Hsu2f9acd22018-11-06 23:44:43 +080036import static org.junit.Assert.assertThat;
Garfield Tan9b1efea2017-12-05 16:43:46 -080037import static org.junit.Assert.assertTrue;
Garfield Tan49dae102019-02-04 09:51:59 -080038import static org.mockito.Mockito.mock;
Garfield Tan9b1efea2017-12-05 16:43:46 -080039
40import android.app.ActivityManager;
Mark Renoufc808f062019-02-07 15:20:37 -050041import android.app.TaskInfo;
Garfield Tan9b1efea2017-12-05 16:43:46 -080042import android.content.ComponentName;
43import android.content.Intent;
44import android.content.pm.ActivityInfo;
Louis Chang96c7b832018-12-27 09:27:53 +080045import android.content.pm.ApplicationInfo;
Evan Rosky1ac84462018-11-13 11:25:30 -080046import android.content.res.Configuration;
Garfield Tan367b35a2017-12-13 12:16:21 -080047import android.graphics.Rect;
Garfield Tan9b1efea2017-12-05 16:43:46 -080048import android.platform.test.annotations.Presubmit;
49import android.service.voice.IVoiceInteractionSession;
Garfield Tan367b35a2017-12-13 12:16:21 -080050import android.util.Xml;
Evan Rosky1ac84462018-11-13 11:25:30 -080051import android.view.DisplayInfo;
Garfield Tan9b1efea2017-12-05 16:43:46 -080052
Brett Chabota26eda92018-07-23 13:08:30 -070053import androidx.test.filters.MediumTest;
Brett Chabota26eda92018-07-23 13:08:30 -070054
Garfield Tan9b1efea2017-12-05 16:43:46 -080055import com.android.internal.app.IVoiceInteractor;
Wale Ogunwale59507092018-10-29 09:00:30 -070056import com.android.server.wm.TaskRecord.TaskRecordFactory;
Garfield Tan9b1efea2017-12-05 16:43:46 -080057
58import org.junit.Before;
59import org.junit.Test;
Garfield Tan49dae102019-02-04 09:51:59 -080060import org.mockito.Mockito;
Garfield Tan9b1efea2017-12-05 16:43:46 -080061import org.xmlpull.v1.XmlPullParser;
62import org.xmlpull.v1.XmlPullParserException;
Garfield Tan367b35a2017-12-13 12:16:21 -080063import org.xmlpull.v1.XmlSerializer;
Garfield Tan9b1efea2017-12-05 16:43:46 -080064
Tadashi G. Takaoka88df5c32018-11-21 16:33:57 +090065import java.io.ByteArrayInputStream;
66import java.io.ByteArrayOutputStream;
Garfield Tan9b1efea2017-12-05 16:43:46 -080067import java.io.IOException;
Tadashi G. Takaoka88df5c32018-11-21 16:33:57 +090068import java.io.InputStreamReader;
Garfield Tan367b35a2017-12-13 12:16:21 -080069import java.io.Reader;
Garfield Tan9b1efea2017-12-05 16:43:46 -080070import java.util.ArrayList;
71
72/**
73 * Tests for exercising {@link TaskRecord}.
74 *
75 * Build/Install/Run:
Tadashi G. Takaoka74ccec22018-10-23 11:07:13 +090076 * atest WmTests:TaskRecordTests
Garfield Tan9b1efea2017-12-05 16:43:46 -080077 */
78@MediumTest
79@Presubmit
Garfield Tan367b35a2017-12-13 12:16:21 -080080public class TaskRecordTests extends ActivityTestsBase {
81
82 private static final String TASK_TAG = "task";
83
Evan Rosky1ac84462018-11-13 11:25:30 -080084 private Rect mParentBounds;
85
Garfield Tan9b1efea2017-12-05 16:43:46 -080086 @Before
87 public void setUp() throws Exception {
88 TaskRecord.setTaskRecordFactory(null);
Evan Rosky1ac84462018-11-13 11:25:30 -080089 mParentBounds = new Rect(10 /*left*/, 30 /*top*/, 80 /*right*/, 60 /*bottom*/);
Garfield Tan367b35a2017-12-13 12:16:21 -080090 }
91
92 @Test
93 public void testRestoreWindowedTask() throws Exception {
94 final TaskRecord expected = createTaskRecord(64);
95 expected.mLastNonFullscreenBounds = new Rect(50, 50, 100, 100);
96
Tadashi G. Takaoka88df5c32018-11-21 16:33:57 +090097 final byte[] serializedBytes = serializeToBytes(expected);
98 final TaskRecord actual = restoreFromBytes(serializedBytes);
99 assertEquals(expected.taskId, actual.taskId);
100 assertEquals(expected.mLastNonFullscreenBounds, actual.mLastNonFullscreenBounds);
Garfield Tan9b1efea2017-12-05 16:43:46 -0800101 }
102
103 @Test
104 public void testDefaultTaskFactoryNotNull() throws Exception {
105 assertNotNull(TaskRecord.getTaskRecordFactory());
106 }
107
Riddle Hsu2f9acd22018-11-06 23:44:43 +0800108 /** Ensure we have no chance to modify the original intent. */
109 @Test
110 public void testCopyBaseIntentForTaskInfo() {
111 final TaskRecord task = createTaskRecord(1);
112 task.lastTaskDescription = new ActivityManager.TaskDescription();
Mark Renoufc808f062019-02-07 15:20:37 -0500113 final TaskInfo info = task.getTaskInfo();
Riddle Hsu2f9acd22018-11-06 23:44:43 +0800114
115 // The intent of info should be a copy so assert that they are different instances.
116 assertThat(info.baseIntent, not(sameInstance(task.getBaseIntent())));
117 }
118
Garfield Tan9b1efea2017-12-05 16:43:46 -0800119 @Test
120 public void testCreateTestRecordUsingCustomizedFactory() throws Exception {
121 TestTaskRecordFactory factory = new TestTaskRecordFactory();
122 TaskRecord.setTaskRecordFactory(factory);
123
124 assertFalse(factory.mCreated);
125
126 TaskRecord.create(null, 0, null, null, null, null);
127
128 assertTrue(factory.mCreated);
129 }
130
Bryce Lee1a990e52018-04-23 10:54:11 -0700131 @Test
132 public void testReturnsToHomeStack() throws Exception {
133 final TaskRecord task = createTaskRecord(1);
134 assertFalse(task.returnsToHomeStack());
135 task.intent = null;
136 assertFalse(task.returnsToHomeStack());
137 task.intent = new Intent();
138 assertFalse(task.returnsToHomeStack());
139 task.intent.addFlags(FLAG_ACTIVITY_NEW_TASK | FLAG_ACTIVITY_TASK_ON_HOME);
140 assertTrue(task.returnsToHomeStack());
141 }
142
Evan Rosky1ac84462018-11-13 11:25:30 -0800143 /** Ensures that empty bounds are not propagated to the configuration. */
144 @Test
145 public void testAppBounds_EmptyBounds() {
146 final Rect emptyBounds = new Rect();
147 testStackBoundsConfiguration(WINDOWING_MODE_FULLSCREEN, mParentBounds, emptyBounds,
148 null /*ExpectedBounds*/);
149 }
150
151 /** Ensures that bounds on freeform stacks are not clipped. */
152 @Test
153 public void testAppBounds_FreeFormBounds() {
154 final Rect freeFormBounds = new Rect(mParentBounds);
155 freeFormBounds.offset(10, 10);
156 testStackBoundsConfiguration(WINDOWING_MODE_FREEFORM, mParentBounds, freeFormBounds,
157 freeFormBounds);
158 }
159
160 /** Ensures that fully contained bounds are not clipped. */
161 @Test
162 public void testAppBounds_ContainedBounds() {
163 final Rect insetBounds = new Rect(mParentBounds);
164 insetBounds.inset(5, 5, 5, 5);
165 testStackBoundsConfiguration(
Evan Rosky730f6e82018-12-03 17:40:11 -0800166 WINDOWING_MODE_FREEFORM, mParentBounds, insetBounds, insetBounds);
Evan Rosky1ac84462018-11-13 11:25:30 -0800167 }
168
Evan Rosky730f6e82018-12-03 17:40:11 -0800169 /** Tests that the task bounds adjust properly to changes between FULLSCREEN and FREEFORM */
Evan Rosky1ac84462018-11-13 11:25:30 -0800170 @Test
Evan Rosky730f6e82018-12-03 17:40:11 -0800171 public void testBoundsOnModeChangeFreeformToFullscreen() {
Evan Rosky1ac84462018-11-13 11:25:30 -0800172 ActivityDisplay display = mService.mRootActivityContainer.getDefaultDisplay();
Evan Rosky730f6e82018-12-03 17:40:11 -0800173 ActivityStack stack = new StackBuilder(mRootActivityContainer).setDisplay(display)
174 .setWindowingMode(WINDOWING_MODE_FREEFORM).build();
175 TaskRecord task = stack.getChildAt(0);
176 task.getRootActivity().mAppWindowToken.setOrientation(SCREEN_ORIENTATION_UNSPECIFIED);
Evan Rosky1ac84462018-11-13 11:25:30 -0800177 DisplayInfo info = new DisplayInfo();
178 display.mDisplay.getDisplayInfo(info);
179 final Rect fullScreenBounds = new Rect(0, 0, info.logicalWidth, info.logicalHeight);
Evan Rosky730f6e82018-12-03 17:40:11 -0800180 final Rect freeformBounds = new Rect(fullScreenBounds);
181 freeformBounds.inset((int) (freeformBounds.width() * 0.2),
182 (int) (freeformBounds.height() * 0.2));
183 task.setBounds(freeformBounds);
184
185 assertEquals(freeformBounds, task.getBounds());
186
187 // FULLSCREEN inherits bounds
188 stack.setWindowingMode(WINDOWING_MODE_FULLSCREEN);
189 assertEquals(fullScreenBounds, task.getBounds());
190 assertEquals(freeformBounds, task.mLastNonFullscreenBounds);
191
192 // FREEFORM restores bounds
193 stack.setWindowingMode(WINDOWING_MODE_FREEFORM);
194 assertEquals(freeformBounds, task.getBounds());
195 }
196
197 /**
198 * This is a temporary hack to trigger an onConfigurationChange at the task level after an
199 * orientation is requested. Normally this is done by the onDescendentOrientationChanged call
200 * up the WM hierarchy, but since the WM hierarchy is mocked out, it doesn't happen here.
201 * TODO: remove this when we either get a WM hierarchy or when hierarchies are merged.
202 */
203 private void setActivityRequestedOrientation(ActivityRecord activity, int orientation) {
204 activity.setRequestedOrientation(orientation);
205 ConfigurationContainer taskRecord = activity.getParent();
206 taskRecord.onConfigurationChanged(taskRecord.getParent().getConfiguration());
207 }
208
209 /**
210 * Tests that a task with forced orientation has orientation-consistent bounds within the
211 * parent.
212 */
213 @Test
214 public void testFullscreenBoundsForcedOrientation() {
215 final Rect fullScreenBounds = new Rect(0, 0, 1920, 1080);
216 final Rect fullScreenBoundsPort = new Rect(0, 0, 1080, 1920);
217 DisplayInfo info = new DisplayInfo();
218 info.logicalWidth = fullScreenBounds.width();
219 info.logicalHeight = fullScreenBounds.height();
220 ActivityDisplay display = addNewActivityDisplayAt(info, POSITION_TOP);
221 assertTrue(mRootActivityContainer.getActivityDisplay(display.mDisplayId) != null);
Evan Rosky130d94f2019-01-15 10:18:17 -0800222 // Override display orientation. Normally this is available via DisplayContent, but DC
223 // is mocked-out.
224 display.getRequestedOverrideConfiguration().orientation =
225 Configuration.ORIENTATION_LANDSCAPE;
226 display.onRequestedOverrideConfigurationChanged(
227 display.getRequestedOverrideConfiguration());
Evan Rosky730f6e82018-12-03 17:40:11 -0800228 ActivityStack stack = new StackBuilder(mRootActivityContainer)
229 .setWindowingMode(WINDOWING_MODE_FULLSCREEN).setDisplay(display).build();
230 TaskRecord task = stack.getChildAt(0);
Evan Rosky130d94f2019-01-15 10:18:17 -0800231 ActivityRecord root = task.getTopActivity();
232 assertEquals(root, task.getTopActivity());
Evan Rosky730f6e82018-12-03 17:40:11 -0800233
234 assertEquals(fullScreenBounds, task.getBounds());
235
236 // Setting app to fixed portrait fits within parent
237 setActivityRequestedOrientation(root, SCREEN_ORIENTATION_PORTRAIT);
238 assertEquals(root, task.getRootActivity());
239 assertEquals(SCREEN_ORIENTATION_PORTRAIT, task.getRootActivity().getOrientation());
240 assertTrue(task.getBounds().width() < task.getBounds().height());
241 assertEquals(fullScreenBounds.height(), task.getBounds().height());
242
Evan Rosky130d94f2019-01-15 10:18:17 -0800243 // Top activity gets used
244 ActivityRecord top = new ActivityBuilder(mService).setTask(task).setStack(stack).build();
245 assertEquals(top, task.getTopActivity());
246 setActivityRequestedOrientation(top, SCREEN_ORIENTATION_LANDSCAPE);
247 assertTrue(task.getBounds().width() > task.getBounds().height());
248 assertEquals(task.getBounds().width(), fullScreenBounds.width());
Evan Rosky730f6e82018-12-03 17:40:11 -0800249
250 // Setting app to unspecified restores
Evan Rosky130d94f2019-01-15 10:18:17 -0800251 setActivityRequestedOrientation(top, SCREEN_ORIENTATION_UNSPECIFIED);
Evan Rosky730f6e82018-12-03 17:40:11 -0800252 assertEquals(fullScreenBounds, task.getBounds());
253
254 // Setting app to fixed landscape and changing display
Evan Rosky130d94f2019-01-15 10:18:17 -0800255 setActivityRequestedOrientation(top, SCREEN_ORIENTATION_LANDSCAPE);
256 // simulate display orientation changing (normally done via DisplayContent)
257 display.getRequestedOverrideConfiguration().orientation =
258 Configuration.ORIENTATION_PORTRAIT;
Evan Rosky730f6e82018-12-03 17:40:11 -0800259 display.setBounds(fullScreenBoundsPort);
260 assertTrue(task.getBounds().width() > task.getBounds().height());
261 assertEquals(fullScreenBoundsPort.width(), task.getBounds().width());
262
263 // in FREEFORM, no constraint
264 final Rect freeformBounds = new Rect(display.getBounds());
265 freeformBounds.inset((int) (freeformBounds.width() * 0.2),
266 (int) (freeformBounds.height() * 0.2));
267 stack.setWindowingMode(WINDOWING_MODE_FREEFORM);
268 task.setBounds(freeformBounds);
269 assertEquals(freeformBounds, task.getBounds());
270
271 // FULLSCREEN letterboxes bounds
272 stack.setWindowingMode(WINDOWING_MODE_FULLSCREEN);
273 assertTrue(task.getBounds().width() > task.getBounds().height());
274 assertEquals(fullScreenBoundsPort.width(), task.getBounds().width());
275
276 // FREEFORM restores bounds as before
277 stack.setWindowingMode(WINDOWING_MODE_FREEFORM);
278 assertEquals(freeformBounds, task.getBounds());
Evan Rosky1ac84462018-11-13 11:25:30 -0800279 }
280
Yunfan Chenf93c06f2019-01-17 07:01:49 +0000281 @Test
Garfield Tan49dae102019-02-04 09:51:59 -0800282 public void testIgnoresForcedOrientationWhenParentHandles() {
283 final Rect fullScreenBounds = new Rect(0, 0, 1920, 1080);
284 DisplayInfo info = new DisplayInfo();
285 info.logicalWidth = fullScreenBounds.width();
286 info.logicalHeight = fullScreenBounds.height();
287 ActivityDisplay display = addNewActivityDisplayAt(info, POSITION_TOP);
Yunfan Chenf93c06f2019-01-17 07:01:49 +0000288
Garfield Tan49dae102019-02-04 09:51:59 -0800289 display.getRequestedOverrideConfiguration().orientation =
290 Configuration.ORIENTATION_LANDSCAPE;
291 display.onRequestedOverrideConfigurationChanged(
292 display.getRequestedOverrideConfiguration());
293 ActivityStack stack = new StackBuilder(mRootActivityContainer)
Yunfan Chenf93c06f2019-01-17 07:01:49 +0000294 .setWindowingMode(WINDOWING_MODE_FULLSCREEN).setDisplay(display).build();
Garfield Tan49dae102019-02-04 09:51:59 -0800295 TaskRecord task = stack.getChildAt(0);
296 ActivityRecord root = task.getTopActivity();
Yunfan Chenf93c06f2019-01-17 07:01:49 +0000297
Garfield Tan49dae102019-02-04 09:51:59 -0800298 final WindowContainer parentWindowContainer = mock(WindowContainer.class);
299 Mockito.doReturn(parentWindowContainer).when(task.mTask).getParent();
300 Mockito.doReturn(true).when(parentWindowContainer)
301 .handlesOrientationChangeFromDescendant();
Yunfan Chenf93c06f2019-01-17 07:01:49 +0000302
Garfield Tan49dae102019-02-04 09:51:59 -0800303 // Setting app to fixed portrait fits within parent, but TaskRecord shouldn't adjust the
304 // bounds because its parent says it will handle it at a later time.
305 setActivityRequestedOrientation(root, SCREEN_ORIENTATION_PORTRAIT);
306 assertEquals(root, task.getRootActivity());
307 assertEquals(SCREEN_ORIENTATION_PORTRAIT, task.getRootActivity().getOrientation());
308 assertEquals(fullScreenBounds, task.getBounds());
Yunfan Chenf93c06f2019-01-17 07:01:49 +0000309 }
310
Riddle Hsu88e3c8732019-02-18 19:15:12 +0800311 @Test
312 public void testComputeConfigResourceOverrides() {
313 final TaskRecord task = new TaskBuilder(mSupervisor).build();
314 final Configuration inOutConfig = new Configuration();
315 final Configuration parentConfig = new Configuration();
316 final int longSide = 1200;
317 final int shortSide = 600;
318 parentConfig.densityDpi = 400;
319 parentConfig.screenHeightDp = 200; // 200 * 400 / 160 = 500px
320 parentConfig.screenWidthDp = 100; // 100 * 400 / 160 = 250px
321
322 // Portrait bounds.
323 inOutConfig.windowConfiguration.getBounds().set(0, 0, shortSide, longSide);
324 // By default, the parent bounds should limit the existing input bounds.
325 task.computeConfigResourceOverrides(inOutConfig, parentConfig);
326
327 assertEquals(parentConfig.screenHeightDp, inOutConfig.screenHeightDp);
328 assertEquals(parentConfig.screenWidthDp, inOutConfig.screenWidthDp);
329 assertEquals(Configuration.ORIENTATION_PORTRAIT, inOutConfig.orientation);
330
331 inOutConfig.setToDefaults();
332 // Landscape bounds.
333 inOutConfig.windowConfiguration.getBounds().set(0, 0, longSide, shortSide);
334 // Without limiting to be inside the parent bounds, the out screen size should keep relative
335 // to the input bounds.
336 task.computeConfigResourceOverrides(inOutConfig, parentConfig,
337 false /* insideParentBounds */);
338
339 assertEquals(shortSide * DENSITY_DEFAULT / parentConfig.densityDpi,
340 inOutConfig.screenHeightDp);
341 assertEquals(longSide * DENSITY_DEFAULT / parentConfig.densityDpi,
342 inOutConfig.screenWidthDp);
343 assertEquals(Configuration.ORIENTATION_LANDSCAPE, inOutConfig.orientation);
344 }
345
Louis Chang96c7b832018-12-27 09:27:53 +0800346 /** Ensures that the alias intent won't have target component resolved. */
347 @Test
348 public void testTaskIntentActivityAlias() {
Louis Chang23df1a62019-01-09 15:10:49 +0800349 final String aliasClassName = DEFAULT_COMPONENT_PACKAGE_NAME + ".aliasActivity";
350 final String targetClassName = DEFAULT_COMPONENT_PACKAGE_NAME + ".targetActivity";
351 final ComponentName aliasComponent =
352 new ComponentName(DEFAULT_COMPONENT_PACKAGE_NAME, aliasClassName);
353 final ComponentName targetComponent =
354 new ComponentName(DEFAULT_COMPONENT_PACKAGE_NAME, targetClassName);
355
Louis Chang96c7b832018-12-27 09:27:53 +0800356 final Intent intent = new Intent();
Louis Chang23df1a62019-01-09 15:10:49 +0800357 intent.setComponent(aliasComponent);
Louis Chang96c7b832018-12-27 09:27:53 +0800358 final ActivityInfo info = new ActivityInfo();
359 info.applicationInfo = new ApplicationInfo();
360 info.packageName = DEFAULT_COMPONENT_PACKAGE_NAME;
Louis Chang23df1a62019-01-09 15:10:49 +0800361 info.targetActivity = targetClassName;
Louis Chang96c7b832018-12-27 09:27:53 +0800362
363 final TaskRecord task = TaskRecord.create(mService, 1 /* taskId */, info, intent,
364 null /* taskDescription */);
Louis Chang23df1a62019-01-09 15:10:49 +0800365 assertEquals("The alias activity component should be saved in task intent.", aliasClassName,
Louis Chang96c7b832018-12-27 09:27:53 +0800366 task.intent.getComponent().getClassName());
Louis Chang23df1a62019-01-09 15:10:49 +0800367
368 ActivityRecord aliasActivity = new ActivityBuilder(mService).setComponent(
369 aliasComponent).setTargetActivity(targetClassName).build();
370 assertEquals("Should be the same intent filter.", true,
371 task.isSameIntentFilter(aliasActivity));
372
373 ActivityRecord targetActivity = new ActivityBuilder(mService).setComponent(
374 targetComponent).build();
375 assertEquals("Should be the same intent filter.", true,
376 task.isSameIntentFilter(targetActivity));
377
378 ActivityRecord defaultActivity = new ActivityBuilder(mService).build();
379 assertEquals("Should not be the same intent filter.", false,
380 task.isSameIntentFilter(defaultActivity));
Louis Chang96c7b832018-12-27 09:27:53 +0800381 }
382
Evan Rosky1ac84462018-11-13 11:25:30 -0800383 private void testStackBoundsConfiguration(int windowingMode, Rect parentBounds, Rect bounds,
384 Rect expectedConfigBounds) {
385
386 ActivityDisplay display = mService.mRootActivityContainer.getDefaultDisplay();
387 ActivityStack stack = display.createStack(windowingMode, ACTIVITY_TYPE_STANDARD,
388 true /* onTop */);
389 TaskRecord task = new TaskBuilder(mSupervisor).setStack(stack).build();
390
391 final Configuration parentConfig = stack.getConfiguration();
392 parentConfig.windowConfiguration.setAppBounds(parentBounds);
393 task.setBounds(bounds);
394
395 task.resolveOverrideConfiguration(parentConfig);
396 // Assert that both expected and actual are null or are equal to each other
397 assertEquals(expectedConfigBounds,
398 task.getResolvedOverrideConfiguration().windowConfiguration.getAppBounds());
399 }
400
Tadashi G. Takaoka88df5c32018-11-21 16:33:57 +0900401 private byte[] serializeToBytes(TaskRecord r) throws IOException, XmlPullParserException {
402 try (ByteArrayOutputStream os = new ByteArrayOutputStream()) {
Garfield Tan367b35a2017-12-13 12:16:21 -0800403 final XmlSerializer serializer = Xml.newSerializer();
404 serializer.setOutput(os, "UTF-8");
405 serializer.startDocument(null, true);
406 serializer.startTag(null, TASK_TAG);
407 r.saveToXml(serializer);
408 serializer.endTag(null, TASK_TAG);
409 serializer.endDocument();
Garfield Tan367b35a2017-12-13 12:16:21 -0800410
Tadashi G. Takaoka88df5c32018-11-21 16:33:57 +0900411 os.flush();
412 return os.toByteArray();
413 }
Garfield Tan367b35a2017-12-13 12:16:21 -0800414 }
415
Tadashi G. Takaoka88df5c32018-11-21 16:33:57 +0900416 private TaskRecord restoreFromBytes(byte[] in) throws IOException, XmlPullParserException {
417 try (Reader reader = new InputStreamReader(new ByteArrayInputStream(in))) {
Garfield Tan367b35a2017-12-13 12:16:21 -0800418 final XmlPullParser parser = Xml.newPullParser();
419 parser.setInput(reader);
420 assertEquals(XmlPullParser.START_TAG, parser.next());
421 assertEquals(TASK_TAG, parser.getName());
422 return TaskRecord.restoreFromXml(parser, mService.mStackSupervisor);
423 }
424 }
425
426 private TaskRecord createTaskRecord(int taskId) {
Wale Ogunwale31913b52018-10-13 08:29:31 -0700427 return new TaskRecord(mService, taskId, new Intent(), null, null, null,
Kazuki Takisec2e17bf2018-07-17 17:46:38 +0900428 ActivityBuilder.getDefaultComponent(), null, false, false, false, 0, 10050, null,
429 new ArrayList<>(), 0, false, null, 0, 0, 0, 0, 0, null, 0, false, false, false, 0, 0
430 );
Garfield Tan367b35a2017-12-13 12:16:21 -0800431 }
432
Garfield Tan9b1efea2017-12-05 16:43:46 -0800433 private static class TestTaskRecordFactory extends TaskRecordFactory {
434 private boolean mCreated = false;
435
436 @Override
Wale Ogunwaled95c06b2018-05-08 10:35:38 -0700437 TaskRecord create(ActivityTaskManagerService service, int taskId, ActivityInfo info,
Garfield Tan9b1efea2017-12-05 16:43:46 -0800438 Intent intent,
439 IVoiceInteractionSession voiceSession, IVoiceInteractor voiceInteractor) {
440 mCreated = true;
441 return null;
442 }
443
444 @Override
Wale Ogunwaled95c06b2018-05-08 10:35:38 -0700445 TaskRecord create(ActivityTaskManagerService service, int taskId, ActivityInfo info,
Garfield Tan9b1efea2017-12-05 16:43:46 -0800446 Intent intent,
447 ActivityManager.TaskDescription taskDescription) {
448 mCreated = true;
449 return null;
450 }
451
452 @Override
Wale Ogunwaled95c06b2018-05-08 10:35:38 -0700453 TaskRecord create(ActivityTaskManagerService service, int taskId, Intent intent,
Garfield Tan9b1efea2017-12-05 16:43:46 -0800454 Intent affinityIntent, String affinity, String rootAffinity,
455 ComponentName realActivity,
456 ComponentName origActivity, boolean rootWasReset, boolean autoRemoveRecents,
457 boolean askedCompatMode, int userId, int effectiveUid, String lastDescription,
458 ArrayList<ActivityRecord> activities, long lastTimeMoved,
459 boolean neverRelinquishIdentity,
460 ActivityManager.TaskDescription lastTaskDescription,
461 int taskAffiliation, int prevTaskId, int nextTaskId, int taskAffiliationColor,
462 int callingUid, String callingPackage, int resizeMode,
463 boolean supportsPictureInPicture,
464 boolean realActivitySuspended, boolean userSetupComplete, int minWidth,
465 int minHeight) {
466 mCreated = true;
467 return null;
468 }
469
470 @Override
471 TaskRecord restoreFromXml(XmlPullParser in, ActivityStackSupervisor stackSupervisor)
472 throws IOException, XmlPullParserException {
473 mCreated = true;
474 return null;
475 }
476 }
477}