Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 72cd98d5 authored by Evan Rosky's avatar Evan Rosky Committed by Automerger Merge Worker
Browse files

Merge "Home tasks inherit split or fullscreen from parent." into rvc-dev am: 48c653a2

Change-Id: If7aafe435352b4ca63fcd36bcbb207d9f7f4fd95
parents 67caf16a 48c653a2
Loading
Loading
Loading
Loading
+31 −21
Original line number Diff line number Diff line
@@ -2225,14 +2225,16 @@ class Task extends WindowContainer<WindowContainer> {
        }
        density *= DisplayMetrics.DENSITY_DEFAULT_SCALE;

        // If bounds have been overridden at this level, restrict config resources to these bounds
        // rather than the parent because the overridden bounds can be larger than the parent.
        boolean hasOverrideBounds = false;

        final Rect resolvedBounds = inOutConfig.windowConfiguration.getBounds();
        if (resolvedBounds == null) {
            mTmpFullBounds.setEmpty();
        if (resolvedBounds == null || resolvedBounds.isEmpty()) {
            mTmpFullBounds.set(parentConfig.windowConfiguration.getBounds());
        } else {
            mTmpFullBounds.set(resolvedBounds);
        }
        if (mTmpFullBounds.isEmpty()) {
            mTmpFullBounds.set(parentConfig.windowConfiguration.getBounds());
            hasOverrideBounds = true;
        }

        Rect outAppBounds = inOutConfig.windowConfiguration.getAppBounds();
@@ -2244,7 +2246,16 @@ class Task extends WindowContainer<WindowContainer> {
        // the out bounds doesn't need to be restricted by the parent.
        final boolean insideParentBounds = compatInsets == null;
        if (insideParentBounds && windowingMode != WINDOWING_MODE_FREEFORM) {
            final Rect parentAppBounds = parentConfig.windowConfiguration.getAppBounds();
            Rect parentAppBounds;
            if (hasOverrideBounds) {
                // Since we overrode the bounds, restrict appBounds to display non-decor rather
                // than parent. Otherwise, it won't match the overridden bounds.
                final TaskDisplayArea displayArea = getDisplayArea();
                parentAppBounds = displayArea != null
                        ? displayArea.getConfiguration().windowConfiguration.getAppBounds() : null;
            } else {
                parentAppBounds = parentConfig.windowConfiguration.getAppBounds();
            }
            if (parentAppBounds != null && !parentAppBounds.isEmpty()) {
                outAppBounds.intersect(parentAppBounds);
            }
@@ -2291,13 +2302,13 @@ class Task extends WindowContainer<WindowContainer> {

            if (inOutConfig.screenWidthDp == Configuration.SCREEN_WIDTH_DP_UNDEFINED) {
                final int overrideScreenWidthDp = (int) (mTmpStableBounds.width() / density);
                inOutConfig.screenWidthDp = insideParentBounds
                inOutConfig.screenWidthDp = (insideParentBounds && !hasOverrideBounds)
                        ? Math.min(overrideScreenWidthDp, parentConfig.screenWidthDp)
                        : overrideScreenWidthDp;
            }
            if (inOutConfig.screenHeightDp == Configuration.SCREEN_HEIGHT_DP_UNDEFINED) {
                final int overrideScreenHeightDp = (int) (mTmpStableBounds.height() / density);
                inOutConfig.screenHeightDp = insideParentBounds
                inOutConfig.screenHeightDp = (insideParentBounds && !hasOverrideBounds)
                        ? Math.min(overrideScreenHeightDp, parentConfig.screenHeightDp)
                        : overrideScreenHeightDp;
            }
@@ -2344,27 +2355,27 @@ class Task extends WindowContainer<WindowContainer> {
        mTmpBounds.set(getResolvedOverrideConfiguration().windowConfiguration.getBounds());
        super.resolveOverrideConfiguration(newParentConfig);

        // Resolve override windowing mode to fullscreen for home task (even on freeform
        // display), or split-screen-secondary if in split-screen mode.
        int windowingMode =
                getResolvedOverrideConfiguration().windowConfiguration.getWindowingMode();

        // Resolve override windowing mode to fullscreen for home task (even on freeform
        // display), or split-screen if in split-screen mode.
        if (getActivityType() == ACTIVITY_TYPE_HOME && windowingMode == WINDOWING_MODE_UNDEFINED) {
            final int parentWindowingMode = newParentConfig.windowConfiguration.getWindowingMode();
            windowingMode = parentWindowingMode == WINDOWING_MODE_SPLIT_SCREEN_SECONDARY
                    ? WINDOWING_MODE_SPLIT_SCREEN_SECONDARY
                    : WINDOWING_MODE_FULLSCREEN;
            windowingMode = WindowConfiguration.isSplitScreenWindowingMode(parentWindowingMode)
                    ? parentWindowingMode : WINDOWING_MODE_FULLSCREEN;
            getResolvedOverrideConfiguration().windowConfiguration.setWindowingMode(windowingMode);
        }

        if (!isLeafTask()) {
            // Compute configuration overrides for tasks that created by organizer, so that
            // organizer can get the correct configuration from those tasks.
            if (mCreatedByOrganizer) {
                computeConfigResourceOverrides(getResolvedOverrideConfiguration(), newParentConfig);
        if (isLeafTask()) {
            resolveLeafOnlyOverrideConfigs(newParentConfig);
        }
            return;
        computeConfigResourceOverrides(getResolvedOverrideConfiguration(), newParentConfig);
    }

    void resolveLeafOnlyOverrideConfigs(Configuration newParentConfig) {
        int windowingMode =
                getResolvedOverrideConfiguration().windowConfiguration.getWindowingMode();
        if (windowingMode == WINDOWING_MODE_UNDEFINED) {
            windowingMode = newParentConfig.windowConfiguration.getWindowingMode();
        }
@@ -2404,7 +2415,6 @@ class Task extends WindowContainer<WindowContainer> {
                outOverrideBounds.offset(0, offsetTop);
            }
        }
        computeConfigResourceOverrides(getResolvedOverrideConfiguration(), newParentConfig);
    }

    /**
+9 −1
Original line number Diff line number Diff line
@@ -329,6 +329,7 @@ class ActivityTestsBase extends SystemServiceTestsBase {
        private boolean mCreateStack = true;

        private ActivityStack mStack;
        private TaskDisplayArea mTaskDisplayArea;

        TaskBuilder(ActivityStackSupervisor supervisor) {
            mSupervisor = supervisor;
@@ -378,9 +379,16 @@ class ActivityTestsBase extends SystemServiceTestsBase {
            return this;
        }

        TaskBuilder setDisplay(DisplayContent display) {
            mTaskDisplayArea = display.getDefaultTaskDisplayArea();
            return this;
        }

        Task build() {
            if (mStack == null && mCreateStack) {
                mStack = mSupervisor.mRootWindowContainer.getDefaultTaskDisplayArea().createStack(
                TaskDisplayArea displayArea = mTaskDisplayArea != null ? mTaskDisplayArea
                        : mSupervisor.mRootWindowContainer.getDefaultTaskDisplayArea();
                mStack = displayArea.createStack(
                        WINDOWING_MODE_FULLSCREEN, ACTIVITY_TYPE_STANDARD, true /* onTop */);
                spyOn(mStack);
            }
+34 −24
Original line number Diff line number Diff line
@@ -54,10 +54,7 @@ import static org.junit.Assert.assertNull;
import static org.junit.Assert.assertThat;
import static org.junit.Assert.assertTrue;
import static org.mockito.ArgumentMatchers.any;
import static org.mockito.ArgumentMatchers.anyInt;
import static org.mockito.ArgumentMatchers.same;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.verify;

import android.app.ActivityManager;
import android.app.TaskInfo;
@@ -75,12 +72,10 @@ import android.util.DisplayMetrics;
import android.util.Xml;
import android.view.DisplayInfo;

import androidx.test.filters.FlakyTest;
import androidx.test.filters.MediumTest;

import com.android.internal.app.IVoiceInteractor;
import com.android.server.wm.Task.TaskFactory;
import com.android.server.wm.utils.WmDisplayCutout;

import org.junit.Before;
import org.junit.Test;
@@ -368,25 +363,38 @@ public class TaskRecordTests extends ActivityTestsBase {

    @Test
    public void testComputeConfigResourceOverrides() {
        final Task task = new TaskBuilder(mSupervisor).build();
        final Rect fullScreenBounds = new Rect(0, 0, 1080, 1920);
        TestDisplayContent display = new TestDisplayContent.Builder(
                mService, fullScreenBounds.width(), fullScreenBounds.height()).build();
        final Task task = new TaskBuilder(mSupervisor).setDisplay(display).build();
        final Configuration inOutConfig = new Configuration();
        final Configuration parentConfig = new Configuration();
        final int longSide = 1200;
        final int shortSide = 600;
        final Rect parentBounds = new Rect(0, 0, 250, 500);
        parentConfig.windowConfiguration.setBounds(parentBounds);
        parentConfig.densityDpi = 400;
        parentConfig.screenHeightDp = 200; // 200 * 400 / 160 = 500px
        parentConfig.screenWidthDp = 100; // 100 * 400 / 160 = 250px
        parentConfig.screenHeightDp = (parentBounds.bottom * 160) / parentConfig.densityDpi; // 200
        parentConfig.screenWidthDp = (parentBounds.right * 160) / parentConfig.densityDpi; // 100
        parentConfig.windowConfiguration.setRotation(ROTATION_0);

        // Portrait bounds.
        inOutConfig.windowConfiguration.getBounds().set(0, 0, shortSide, longSide);
        // By default, the parent bounds should limit the existing input bounds.
        // By default, the input bounds will fill parent.
        task.computeConfigResourceOverrides(inOutConfig, parentConfig);

        assertEquals(parentConfig.screenHeightDp, inOutConfig.screenHeightDp);
        assertEquals(parentConfig.screenWidthDp, inOutConfig.screenWidthDp);
        assertEquals(Configuration.ORIENTATION_PORTRAIT, inOutConfig.orientation);

        // If bounds are overridden, config properties should be made to match. Surface hierarchy
        // will crop for policy.
        inOutConfig.setToDefaults();
        inOutConfig.windowConfiguration.getBounds().set(0, 0, shortSide, longSide);
        // By default, the parent bounds should limit the existing input bounds.
        task.computeConfigResourceOverrides(inOutConfig, parentConfig);

        assertEquals(longSide, inOutConfig.screenHeightDp * parentConfig.densityDpi / 160);
        assertEquals(shortSide, inOutConfig.screenWidthDp * parentConfig.densityDpi / 160);

        inOutConfig.setToDefaults();
        // Landscape bounds.
        inOutConfig.windowConfiguration.getBounds().set(0, 0, longSide, shortSide);
@@ -394,21 +402,17 @@ public class TaskRecordTests extends ActivityTestsBase {
        // Setup the display with a top stable inset. The later assertion will ensure the inset is
        // excluded from screenHeightDp.
        final int statusBarHeight = 100;
        final DisplayContent displayContent = task.mDisplayContent;
        final DisplayPolicy policy = mock(DisplayPolicy.class);
        final DisplayPolicy policy = display.getDisplayPolicy();
        doAnswer(invocationOnMock -> {
            final Rect insets = invocationOnMock.<Rect>getArgument(0);
            insets.top = statusBarHeight;
            return null;
        }).when(policy).convertNonDecorInsetsToStableInsets(any(), eq(ROTATION_0));
        doReturn(policy).when(displayContent).getDisplayPolicy();
        doReturn(mock(WmDisplayCutout.class)).when(displayContent)
                .calculateDisplayCutoutForRotation(anyInt());

        // Without limiting to be inside the parent bounds, the out screen size should keep relative
        // to the input bounds.
        final ActivityRecord.CompatDisplayInsets compatIntsets =
                new ActivityRecord.CompatDisplayInsets(displayContent, task);
                new ActivityRecord.CompatDisplayInsets(display, task);
        task.computeConfigResourceOverrides(inOutConfig, parentConfig, compatIntsets);

        assertEquals((shortSide - statusBarHeight) * DENSITY_DEFAULT / parentConfig.densityDpi,
@@ -454,7 +458,6 @@ public class TaskRecordTests extends ActivityTestsBase {
        parentConfig.screenWidthDp = 100; // 100 * 400 / 160 = 250px
        parentConfig.windowConfiguration.setRotation(ROTATION_0);

        final float density = 2.5f; // densityDpi / DENSITY_DEFAULT_SCALE = 400 / 160.0f
        final int longSideDp = 480; // longSide / density = 1200 / 400 * 160
        final int shortSideDp = 240; // shortSide / density = 600 / 400 * 160
        final int screenLayout = parentConfig.screenLayout
@@ -463,31 +466,38 @@ public class TaskRecordTests extends ActivityTestsBase {
                Configuration.reduceScreenLayout(screenLayout, longSideDp, shortSideDp);

        // Portrait bounds overlapping with navigation bar, without insets.
        inOutConfig.windowConfiguration.getBounds().set(0,
        final Rect freeformBounds = new Rect(0,
                displayHeight - 10 - longSide,
                shortSide,
                displayHeight - 10);
        inOutConfig.windowConfiguration.setBounds(freeformBounds);
        // Set to freeform mode to verify bug fix.
        inOutConfig.windowConfiguration.setWindowingMode(WINDOWING_MODE_FREEFORM);

        task.computeConfigResourceOverrides(inOutConfig, parentConfig);

        assertEquals(parentConfig.screenWidthDp, inOutConfig.screenWidthDp);
        assertEquals(parentConfig.screenHeightDp, inOutConfig.screenHeightDp);
        // screenW/H should not be effected by parent since overridden and freeform
        assertEquals(freeformBounds.width() * 160 / parentConfig.densityDpi,
                inOutConfig.screenWidthDp);
        assertEquals(freeformBounds.height() * 160 / parentConfig.densityDpi,
                inOutConfig.screenHeightDp);
        assertEquals(reducedScreenLayout, inOutConfig.screenLayout);

        inOutConfig.setToDefaults();
        // Landscape bounds overlapping with navigtion bar, without insets.
        inOutConfig.windowConfiguration.getBounds().set(0,
        freeformBounds.set(0,
                displayHeight - 10 - shortSide,
                longSide,
                displayHeight - 10);
        inOutConfig.windowConfiguration.setBounds(freeformBounds);
        inOutConfig.windowConfiguration.setWindowingMode(WINDOWING_MODE_FREEFORM);

        task.computeConfigResourceOverrides(inOutConfig, parentConfig);

        assertEquals(parentConfig.screenWidthDp, inOutConfig.screenWidthDp);
        assertEquals(parentConfig.screenHeightDp, inOutConfig.screenHeightDp);
        assertEquals(freeformBounds.width() * 160 / parentConfig.densityDpi,
                inOutConfig.screenWidthDp);
        assertEquals(freeformBounds.height() * 160 / parentConfig.densityDpi,
                inOutConfig.screenHeightDp);
        assertEquals(reducedScreenLayout, inOutConfig.screenLayout);
    }

+3 −6
Original line number Diff line number Diff line
@@ -44,7 +44,6 @@ import static com.android.server.wm.WindowContainer.POSITION_TOP;

import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertNotEquals;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertTrue;
import static org.mockito.ArgumentMatchers.any;
@@ -407,22 +406,20 @@ public class WindowOrganizerTests extends WindowTestsBase {
                .setWindowingMode(WINDOWING_MODE_FREEFORM).build();
        final Task task = stack.getTopMostTask();
        WindowContainerTransaction t = new WindowContainerTransaction();
        t.setBounds(task.mRemoteToken.toWindowContainerToken(), new Rect(10, 10, 100, 100));
        mWm.mAtmService.mWindowOrganizerController.applyTransaction(t);
        final int origScreenWDp = task.getConfiguration().screenHeightDp;
        final int origScreenHDp = task.getConfiguration().screenHeightDp;
        t = new WindowContainerTransaction();
        // verify that setting config overrides on parent restricts children.
        t.setScreenSizeDp(stack.mRemoteToken
                .toWindowContainerToken(), origScreenWDp, origScreenHDp);
        t.setBounds(task.mRemoteToken.toWindowContainerToken(), new Rect(10, 10, 150, 200));
                .toWindowContainerToken(), origScreenWDp, origScreenHDp / 2);
        mWm.mAtmService.mWindowOrganizerController.applyTransaction(t);
        assertEquals(origScreenHDp, task.getConfiguration().screenHeightDp);
        assertEquals(origScreenHDp / 2, task.getConfiguration().screenHeightDp);
        t = new WindowContainerTransaction();
        t.setScreenSizeDp(stack.mRemoteToken.toWindowContainerToken(), SCREEN_WIDTH_DP_UNDEFINED,
                SCREEN_HEIGHT_DP_UNDEFINED);
        mWm.mAtmService.mWindowOrganizerController.applyTransaction(t);
        assertNotEquals(origScreenHDp, task.getConfiguration().screenHeightDp);
        assertEquals(origScreenHDp, task.getConfiguration().screenHeightDp);
    }

    @Test