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

Commit 60f3c56e authored by Jiaming Liu's avatar Jiaming Liu
Browse files

Add TaskFragment operation to set can affect system ui flag

This allows system apps such as Launcher to specify when a TaskFragment
can affect system UI.

Bug: 339262182
Test: atest TaskFragmentOrganizerControllerTest
Flag: EXEMPT bugfix
Change-Id: I09e00935e110edc6146df46af6181528ba7f353d
parent 10ea6f00
Loading
Loading
Loading
Loading
+11 −0
Original line number Diff line number Diff line
@@ -161,6 +161,16 @@ public final class TaskFragmentOperation implements Parcelable {
     */
    public static final int OP_TYPE_SET_PINNED = 19;

    /**
     * Sets whether this TaskFragment can affect system UI flags such as the status bar. Default
     * is {@code true}.
     *
     * This operation is only allowed for system organizers. See
     * {@link com.android.server.wm.TaskFragmentOrganizerController#registerOrganizer(
     * ITaskFragmentOrganizer, boolean)}
     */
    public static final int OP_TYPE_SET_CAN_AFFECT_SYSTEM_UI_FLAGS = 20;

    @IntDef(prefix = { "OP_TYPE_" }, value = {
            OP_TYPE_UNKNOWN,
            OP_TYPE_CREATE_TASK_FRAGMENT,
@@ -183,6 +193,7 @@ public final class TaskFragmentOperation implements Parcelable {
            OP_TYPE_SET_MOVE_TO_BOTTOM_IF_CLEAR_WHEN_LAUNCH,
            OP_TYPE_SET_DECOR_SURFACE_BOOSTED,
            OP_TYPE_SET_PINNED,
            OP_TYPE_SET_CAN_AFFECT_SYSTEM_UI_FLAGS,
    })
    @Retention(RetentionPolicy.SOURCE)
    public @interface OperationType {}
+18 −0
Original line number Diff line number Diff line
@@ -38,6 +38,7 @@ import static android.window.TaskFragmentOperation.OP_TYPE_REPARENT_ACTIVITY_TO_
import static android.window.TaskFragmentOperation.OP_TYPE_REQUEST_FOCUS_ON_TASK_FRAGMENT;
import static android.window.TaskFragmentOperation.OP_TYPE_SET_ADJACENT_TASK_FRAGMENTS;
import static android.window.TaskFragmentOperation.OP_TYPE_SET_ANIMATION_PARAMS;
import static android.window.TaskFragmentOperation.OP_TYPE_SET_CAN_AFFECT_SYSTEM_UI_FLAGS;
import static android.window.TaskFragmentOperation.OP_TYPE_SET_COMPANION_TASK_FRAGMENT;
import static android.window.TaskFragmentOperation.OP_TYPE_SET_DECOR_SURFACE_BOOSTED;
import static android.window.TaskFragmentOperation.OP_TYPE_SET_DIM_ON_TASK;
@@ -1862,6 +1863,13 @@ class WindowOrganizerController extends IWindowOrganizerController.Stub
                taskFragment.setPinned(pinned);
                break;
            }
            case OP_TYPE_SET_CAN_AFFECT_SYSTEM_UI_FLAGS: {
                taskFragment.setCanAffectSystemUiFlags(operation.getBooleanValue());

                // Request to apply the flags.
                mService.mWindowManager.mWindowPlacerLocked.requestTraversal();
                break;
            }
        }
        return effects;
    }
@@ -1937,6 +1945,16 @@ class WindowOrganizerController extends IWindowOrganizerController.Stub
            return false;
        }

        if ((opType == OP_TYPE_SET_CAN_AFFECT_SYSTEM_UI_FLAGS)
                && !mTaskFragmentOrganizerController.isSystemOrganizer(organizer.asBinder())) {
            final Throwable exception = new SecurityException(
                    "Only a system organizer can perform OP_TYPE_SET_CAN_AFFECT_SYSTEM_UI_FLAGS."
            );
            sendTaskFragmentOperationFailure(organizer, errorCallbackToken, taskFragment,
                    opType, exception);
            return false;
        }

        final IBinder secondaryFragmentToken = operation.getSecondaryFragmentToken();
        return secondaryFragmentToken == null
                || validateTaskFragment(mLaunchTaskFragments.get(secondaryFragmentToken), opType,
+48 −0
Original line number Diff line number Diff line
@@ -36,6 +36,7 @@ import static android.window.TaskFragmentOperation.OP_TYPE_REORDER_TO_TOP_OF_TAS
import static android.window.TaskFragmentOperation.OP_TYPE_REPARENT_ACTIVITY_TO_TASK_FRAGMENT;
import static android.window.TaskFragmentOperation.OP_TYPE_SET_ADJACENT_TASK_FRAGMENTS;
import static android.window.TaskFragmentOperation.OP_TYPE_SET_ANIMATION_PARAMS;
import static android.window.TaskFragmentOperation.OP_TYPE_SET_CAN_AFFECT_SYSTEM_UI_FLAGS;
import static android.window.TaskFragmentOperation.OP_TYPE_SET_DIM_ON_TASK;
import static android.window.TaskFragmentOperation.OP_TYPE_START_ACTIVITY_IN_TASK_FRAGMENT;
import static android.window.TaskFragmentOrganizer.KEY_ERROR_CALLBACK_OP_TYPE;
@@ -1911,6 +1912,53 @@ public class TaskFragmentOrganizerControllerTest extends WindowTestsBase {
                OP_TYPE_REORDER_TO_TOP_OF_TASK);
    }

    @Test
    public void testApplyTransaction_setCanAffectSystemUiFlags() {
        mController.unregisterOrganizer(mIOrganizer);
        registerTaskFragmentOrganizer(mIOrganizer, true /* isSystemOrganizer */);

        final Task task = createTask(mDisplayContent);
        final TaskFragment tf = createTaskFragment(task);

        // Setting the flag to false.
        TaskFragmentOperation operation = new TaskFragmentOperation.Builder(
                OP_TYPE_SET_CAN_AFFECT_SYSTEM_UI_FLAGS).setBooleanValue(false).build();
        mTransaction.addTaskFragmentOperation(tf.getFragmentToken(), operation);

        assertApplyTransactionAllowed(mTransaction);

        verify(tf).setCanAffectSystemUiFlags(false);

        // Setting the flag back to true.
        operation = new TaskFragmentOperation.Builder(
                OP_TYPE_SET_CAN_AFFECT_SYSTEM_UI_FLAGS).setBooleanValue(true).build();
        mTransaction.addTaskFragmentOperation(tf.getFragmentToken(), operation);

        assertApplyTransactionAllowed(mTransaction);

        verify(tf).setCanAffectSystemUiFlags(true);
    }

    @Test
    public void testApplyTransaction_setCanAffectSystemUiFlags_failsIfNotSystemOrganizer() {
        final Task task = createTask(mDisplayContent);
        final TaskFragment tf = createTaskFragment(task);

        TaskFragmentOperation operation = new TaskFragmentOperation.Builder(
                OP_TYPE_SET_CAN_AFFECT_SYSTEM_UI_FLAGS).setBooleanValue(false).build();
        mTransaction
                .addTaskFragmentOperation(tf.getFragmentToken(), operation)
                .setErrorCallbackToken(mErrorToken);

        assertApplyTransactionAllowed(mTransaction);

        // The pending event will be dispatched on the handler (from requestTraversal).
        waitHandlerIdle(mWm.mAnimationHandler);

        assertTaskFragmentErrorTransaction(OP_TYPE_SET_CAN_AFFECT_SYSTEM_UI_FLAGS,
                SecurityException.class);
    }

    @NonNull
    private ActivityRecord setupUntrustedEmbeddingPipReparent() {
        final int pid = Binder.getCallingPid();