Per-app configuration for force non-resizable

We're defining a new compat framework change id that indicates whether a
given app should be force non-resizable.

Bug: 181136395
Test: atest WmTests:SizeCompatTests
Change-Id: Ibd91bc8fe3da57f17e32fa8efaf98c51fe4dd677
This commit is contained in:
tomnatan
2021-02-26 22:17:52 +00:00
committed by Tom Natan
parent c50df25a88
commit 7b22b447da
5 changed files with 194 additions and 18 deletions

View File

@@ -721,6 +721,8 @@ package android.content.pm {
public class ActivityInfo extends android.content.pm.ComponentInfo implements android.os.Parcelable {
method public static boolean isTranslucentOrFloating(android.content.res.TypedArray);
field public static final long FORCE_NON_RESIZE_APP = 181136395L; // 0xacbec0bL
field public static final long FORCE_RESIZE_APP = 174042936L; // 0xa5faf38L
field public static final int RESIZE_MODE_RESIZEABLE = 2; // 0x2
}

View File

@@ -892,22 +892,42 @@ public class ActivityInfo extends ComponentInfo implements Parcelable {
*/
@ChangeId
@Disabled
public static final long FORCE_RESIZE_APP = 174042936L; // number refers to buganizer id
@TestApi
public static final long FORCE_RESIZE_APP = 174042936L; // buganizer id
/**
* This change id forces the packages it is applied to to be non-resizable.
* @hide
*/
@ChangeId
@Disabled
@TestApi
public static final long FORCE_NON_RESIZE_APP = 181136395L; // buganizer id
/**
* Return value for {@link #supportsSizeChanges()} indicating that this activity does not
* support size changes.
* support size changes due to the android.supports_size_changes metadata flag either being
* unset or set to {@code false} on application or activity level.
*
* @hide
*/
public static final int SIZE_CHANGES_UNSUPPORTED = 0;
public static final int SIZE_CHANGES_UNSUPPORTED_METADATA = 0;
/**
* Return value for {@link #supportsSizeChanges()} indicating that this activity has been
* overridden to not support size changes through the compat framework change id
* {@link #FORCE_NON_RESIZE_APP}.
* @hide
*/
public static final int SIZE_CHANGES_UNSUPPORTED_OVERRIDE = 1;
/**
* Return value for {@link #supportsSizeChanges()} indicating that this activity supports size
* changes due to the android.supports_size_changes metadata flag being set either on
* application or on activity level.
* changes due to the android.supports_size_changes metadata flag being set to {@code true}
* either on application or activity level.
* @hide
*/
public static final int SIZE_CHANGES_SUPPORTED_METADATA = 1;
public static final int SIZE_CHANGES_SUPPORTED_METADATA = 2;
/**
* Return value for {@link #supportsSizeChanges()} indicating that this activity has been
@@ -915,11 +935,12 @@ public class ActivityInfo extends ComponentInfo implements Parcelable {
* {@link #FORCE_RESIZE_APP}.
* @hide
*/
public static final int SIZE_CHANGES_SUPPORTED_OVERRIDE = 2;
public static final int SIZE_CHANGES_SUPPORTED_OVERRIDE = 3;
/** @hide */
@IntDef(prefix = { "SIZE_CHANGES_" }, value = {
SIZE_CHANGES_UNSUPPORTED,
SIZE_CHANGES_UNSUPPORTED_METADATA,
SIZE_CHANGES_UNSUPPORTED_OVERRIDE,
SIZE_CHANGES_SUPPORTED_METADATA,
SIZE_CHANGES_SUPPORTED_OVERRIDE,
})
@@ -1213,6 +1234,12 @@ public class ActivityInfo extends ComponentInfo implements Parcelable {
*/
@SizeChangesSupportMode
public int supportsSizeChanges() {
if (CompatChanges.isChangeEnabled(FORCE_NON_RESIZE_APP,
applicationInfo.packageName,
UserHandle.getUserHandleForUid(applicationInfo.uid))) {
return SIZE_CHANGES_UNSUPPORTED_OVERRIDE;
}
if (supportsSizeChanges) {
return SIZE_CHANGES_SUPPORTED_METADATA;
}
@@ -1223,7 +1250,7 @@ public class ActivityInfo extends ComponentInfo implements Parcelable {
return SIZE_CHANGES_SUPPORTED_OVERRIDE;
}
return SIZE_CHANGES_UNSUPPORTED;
return SIZE_CHANGES_UNSUPPORTED_METADATA;
}
/** @hide */
@@ -1269,8 +1296,10 @@ public class ActivityInfo extends ComponentInfo implements Parcelable {
/** @hide */
public static String sizeChangesSupportModeToString(@SizeChangesSupportMode int mode) {
switch (mode) {
case SIZE_CHANGES_UNSUPPORTED:
return "SIZE_CHANGES_UNSUPPORTED";
case SIZE_CHANGES_UNSUPPORTED_METADATA:
return "SIZE_CHANGES_UNSUPPORTED_METADATA";
case SIZE_CHANGES_UNSUPPORTED_OVERRIDE:
return "SIZE_CHANGES_UNSUPPORTED_OVERRIDE";
case SIZE_CHANGES_SUPPORTED_METADATA:
return "SIZE_CHANGES_SUPPORTED_METADATA";
case SIZE_CHANGES_SUPPORTED_OVERRIDE:

View File

@@ -85,6 +85,9 @@ import static android.content.pm.ActivityInfo.RESIZE_MODE_RESIZEABLE_VIA_SDK_VER
import static android.content.pm.ActivityInfo.RESIZE_MODE_UNRESIZEABLE;
import static android.content.pm.ActivityInfo.SCREEN_ORIENTATION_BEHIND;
import static android.content.pm.ActivityInfo.SCREEN_ORIENTATION_UNSET;
import static android.content.pm.ActivityInfo.SIZE_CHANGES_SUPPORTED_METADATA;
import static android.content.pm.ActivityInfo.SIZE_CHANGES_SUPPORTED_OVERRIDE;
import static android.content.pm.ActivityInfo.SIZE_CHANGES_UNSUPPORTED_OVERRIDE;
import static android.content.pm.ActivityInfo.isFixedOrientationLandscape;
import static android.content.pm.ActivityInfo.isFixedOrientationPortrait;
import static android.content.pm.PackageManager.PERMISSION_GRANTED;
@@ -6819,8 +6822,14 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A
* aspect ratio.
*/
boolean shouldCreateCompatDisplayInsets() {
if (info.supportsSizeChanges() != ActivityInfo.SIZE_CHANGES_UNSUPPORTED) {
return false;
switch (info.supportsSizeChanges()) {
case SIZE_CHANGES_SUPPORTED_METADATA:
case SIZE_CHANGES_SUPPORTED_OVERRIDE:
return false;
case SIZE_CHANGES_UNSUPPORTED_OVERRIDE:
return true;
default:
// Fall through
}
if (inMultiWindowMode() || getWindowConfiguration().hasWindowDecorCaption()) {
final ActivityRecord root = task != null ? task.getRootActivity() : null;

View File

@@ -605,13 +605,13 @@ public class SizeCompatTests extends WindowTestsBase {
}
@Test
public void testShouldUseSizeCompatModeOnResizableTask() {
public void testShouldCreateCompatDisplayInsetsOnResizeableTask() {
setUpDisplaySizeWithApp(1000, 2500);
// Make the task root resizable.
mActivity.info.resizeMode = RESIZE_MODE_RESIZEABLE;
// Create a size compat activity on the same task.
// Create an activity on the same task.
final ActivityRecord activity = new ActivityBuilder(mAtm)
.setTask(mTask)
.setResizeMode(ActivityInfo.RESIZE_MODE_UNRESIZEABLE)
@@ -636,17 +636,17 @@ public class SizeCompatTests extends WindowTestsBase {
}
@Test
@EnableCompatChanges({ActivityInfo.FORCE_RESIZE_APP})
public void testNoSizeCompatWhenPerAppOverrideSet() {
public void testShouldCreateCompatDisplayInsetsWhenUnresizeableAndSupportsSizeChangesTrue() {
setUpDisplaySizeWithApp(1000, 2500);
// Make the task root resizable.
mActivity.info.resizeMode = RESIZE_MODE_RESIZEABLE;
// Create a size compat activity on the same task.
// Create an activity on the same task.
final ActivityRecord activity = new ActivityBuilder(mAtm)
.setTask(mTask)
.setResizeMode(ActivityInfo.RESIZE_MODE_UNRESIZEABLE)
.setSupportsSizeChanges(true)
.setScreenOrientation(ActivityInfo.SCREEN_ORIENTATION_PORTRAIT)
.setComponent(ComponentName.createRelative(mContext,
SizeCompatTests.class.getName()))
@@ -655,6 +655,130 @@ public class SizeCompatTests extends WindowTestsBase {
assertFalse(activity.shouldCreateCompatDisplayInsets());
}
@Test
public void testShouldCreateCompatDisplayInsetsWhenUnresizeableAndSupportsSizeChangesFalse() {
setUpDisplaySizeWithApp(1000, 2500);
// Make the task root resizable.
mActivity.info.resizeMode = RESIZE_MODE_RESIZEABLE;
// Create an activity on the same task.
final ActivityRecord activity = new ActivityBuilder(mAtm)
.setTask(mTask)
.setResizeMode(ActivityInfo.RESIZE_MODE_UNRESIZEABLE)
.setSupportsSizeChanges(false)
.setScreenOrientation(ActivityInfo.SCREEN_ORIENTATION_PORTRAIT)
.setComponent(ComponentName.createRelative(mContext,
SizeCompatTests.class.getName()))
.setUid(android.os.Process.myUid())
.build();
assertTrue(activity.shouldCreateCompatDisplayInsets());
}
@Test
public void testShouldCreateCompatDisplayInsetsWhenResizeableAndSupportsSizeChangesFalse() {
setUpDisplaySizeWithApp(1000, 2500);
// Make the task root resizable.
mActivity.info.resizeMode = RESIZE_MODE_RESIZEABLE;
// Create an activity on the same task.
final ActivityRecord activity = new ActivityBuilder(mAtm)
.setTask(mTask)
.setResizeMode(ActivityInfo.RESIZE_MODE_RESIZEABLE)
.setSupportsSizeChanges(false)
.setScreenOrientation(ActivityInfo.SCREEN_ORIENTATION_PORTRAIT)
.setComponent(ComponentName.createRelative(mContext,
SizeCompatTests.class.getName()))
.setUid(android.os.Process.myUid())
.build();
assertFalse(activity.shouldCreateCompatDisplayInsets());
}
@Test
public void
testShouldCreateCompatDisplayInsetsWhenUnfixedOrientationSupportsSizeChangesFalse() {
setUpDisplaySizeWithApp(1000, 2500);
// Make the task root resizable.
mActivity.info.resizeMode = RESIZE_MODE_RESIZEABLE;
// Create an activity on the same task.
final ActivityRecord activity = new ActivityBuilder(mAtm)
.setTask(mTask)
.setResizeMode(ActivityInfo.RESIZE_MODE_UNRESIZEABLE)
.setSupportsSizeChanges(false)
.setScreenOrientation(ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED)
.setComponent(ComponentName.createRelative(mContext,
SizeCompatTests.class.getName()))
.setUid(android.os.Process.myUid())
.build();
assertFalse(activity.shouldCreateCompatDisplayInsets());
}
@Test
@EnableCompatChanges({ActivityInfo.FORCE_RESIZE_APP})
public void testShouldCreateCompatDisplayInsetsWhenForceResizeAppOverrideSet() {
setUpDisplaySizeWithApp(1000, 2500);
// Make the task root resizable.
mActivity.info.resizeMode = RESIZE_MODE_RESIZEABLE;
// Create an activity on the same task.
final ActivityRecord activity = new ActivityBuilder(mAtm)
.setTask(mTask)
.setResizeMode(ActivityInfo.RESIZE_MODE_UNRESIZEABLE)
.setSupportsSizeChanges(false)
.setScreenOrientation(ActivityInfo.SCREEN_ORIENTATION_PORTRAIT)
.setComponent(ComponentName.createRelative(mContext,
SizeCompatTests.class.getName()))
.setUid(android.os.Process.myUid())
.build();
assertFalse(activity.shouldCreateCompatDisplayInsets());
}
@Test
@EnableCompatChanges({ActivityInfo.FORCE_NON_RESIZE_APP})
public void testShouldCreateCompatDisplayInsetsWhenForceNonResizeOverrideSet() {
setUpDisplaySizeWithApp(1000, 2500);
// Make the task root resizable.
mActivity.info.resizeMode = RESIZE_MODE_RESIZEABLE;
// Create an activity on the same task.
final ActivityRecord activity = new ActivityBuilder(mAtm)
.setTask(mTask)
.setResizeMode(ActivityInfo.RESIZE_MODE_RESIZEABLE)
.setSupportsSizeChanges(true)
.setScreenOrientation(ActivityInfo.SCREEN_ORIENTATION_PORTRAIT)
.setComponent(ComponentName.createRelative(mContext,
SizeCompatTests.class.getName()))
.setUid(android.os.Process.myUid())
.build();
assertTrue(activity.shouldCreateCompatDisplayInsets());
}
@Test
@EnableCompatChanges({ActivityInfo.FORCE_NON_RESIZE_APP})
public void testShouldCreateCompatDisplayInsetsWhenForceNonResizeSetAndUnfixedOrientation() {
setUpDisplaySizeWithApp(1000, 2500);
// Make the task root resizable.
mActivity.info.resizeMode = RESIZE_MODE_RESIZEABLE;
// Create an activity on the same task.
final ActivityRecord activity = new ActivityBuilder(mAtm)
.setTask(mTask)
.setResizeMode(ActivityInfo.RESIZE_MODE_RESIZEABLE)
.setSupportsSizeChanges(true)
.setScreenOrientation(ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED)
.setComponent(ComponentName.createRelative(mContext,
SizeCompatTests.class.getName()))
.setUid(android.os.Process.myUid())
.build();
assertTrue(activity.shouldCreateCompatDisplayInsets());
}
@Test
public void testLaunchWithFixedRotationTransform() {
final int dw = 1000;

View File

@@ -176,6 +176,11 @@ class WindowTestsBase extends SystemServiceTestsBase {
} else {
mDisplayContent = mDefaultDisplay;
}
// Ensure letterbox aspect ratio is not overridden on any device target.
// {@link com.android.internal.R.dimen.config_fixedOrientationLetterboxAspectRatio}, is set
// on some device form factors.
mAtm.mWindowManager.setFixedOrientationLetterboxAspectRatio(0);
}
private void createTestDisplay(UseTestDisplay annotation) {
@@ -704,6 +709,7 @@ class WindowTestsBase extends SystemServiceTestsBase {
private int mLaunchMode;
private int mResizeMode = RESIZE_MODE_RESIZEABLE;
private float mMaxAspectRatio;
private boolean mSupportsSizeChanges;
private int mScreenOrientation = SCREEN_ORIENTATION_UNSPECIFIED;
private boolean mLaunchTaskBehind = false;
private int mConfigChanges;
@@ -782,6 +788,11 @@ class WindowTestsBase extends SystemServiceTestsBase {
return this;
}
ActivityBuilder setSupportsSizeChanges(boolean supportsSizeChanges) {
mSupportsSizeChanges = supportsSizeChanges;
return this;
}
ActivityBuilder setScreenOrientation(int screenOrientation) {
mScreenOrientation = screenOrientation;
return this;
@@ -869,6 +880,7 @@ class WindowTestsBase extends SystemServiceTestsBase {
aInfo.launchMode = mLaunchMode;
aInfo.resizeMode = mResizeMode;
aInfo.maxAspectRatio = mMaxAspectRatio;
aInfo.supportsSizeChanges = mSupportsSizeChanges;
aInfo.screenOrientation = mScreenOrientation;
aInfo.configChanges |= mConfigChanges;
aInfo.taskAffinity = mAffinity;