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

Commit 10de7a4f authored by Jerry Chang's avatar Jerry Chang
Browse files

Fix first drag to split not working

There's a timing when dragging to split opening a new app, the new app
might not be put into DC.mOpeningApps yet while startLegacyTransition
triggering app transition. And result to executing an extra TRANSIT_NONE
app transition. This patch leaves the app transition triggering to
ActivityTaskSupervisor.reportResumedActivityLocked where the new opening
app has been put into DC.mOpeningApps.

With CL[1], it'll invoke onAnimationCancelled when there's no valid app
to anmate while executing app transition. So we don't need to cancel
animation with startActivity result.

Also unbind exit split screen logic with onAnimationCancelled in
wm-shell since it only enters split screen after a new task being
launched/reparented to the side stage root after CL[2].

[1]: I50ddc91f7bd7ed24a977fa3face9c6e56e1bea02
[2]: I1cad96f6265eb1a14369bfc708871f701764066a

Fix: 197917994
Test: drag and drop to split works
Change-Id: If9ab7c3a89c8153c3731103571162fe21c94b3aa
parent a42a8d6b
Loading
Loading
Loading
Loading
+12 −24
Original line number Original line Diff line number Diff line
@@ -22,7 +22,6 @@ import static android.view.RemoteAnimationTarget.MODE_OPENING;
import static com.android.wm.shell.common.ExecutorUtils.executeRemoteCallWithTaskPermission;
import static com.android.wm.shell.common.ExecutorUtils.executeRemoteCallWithTaskPermission;
import static com.android.wm.shell.common.split.SplitLayout.SPLIT_POSITION_BOTTOM_OR_RIGHT;
import static com.android.wm.shell.common.split.SplitLayout.SPLIT_POSITION_BOTTOM_OR_RIGHT;
import static com.android.wm.shell.common.split.SplitLayout.SPLIT_POSITION_TOP_OR_LEFT;
import static com.android.wm.shell.common.split.SplitLayout.SPLIT_POSITION_TOP_OR_LEFT;
import static com.android.wm.shell.splitscreen.SplitScreen.STAGE_TYPE_MAIN;


import android.app.ActivityManager;
import android.app.ActivityManager;
import android.app.ActivityTaskManager;
import android.app.ActivityTaskManager;
@@ -76,6 +75,7 @@ import java.util.concurrent.Executor;
 * {@link SplitScreen}.
 * {@link SplitScreen}.
 * @see StageCoordinator
 * @see StageCoordinator
 */
 */
// TODO(b/198577848): Implement split screen flicker test to consolidate CUJ of split screen.
public class SplitScreenController implements DragAndDropPolicy.Starter,
public class SplitScreenController implements DragAndDropPolicy.Starter,
        RemoteCallable<SplitScreenController> {
        RemoteCallable<SplitScreenController> {
    private static final String TAG = SplitScreenController.class.getSimpleName();
    private static final String TAG = SplitScreenController.class.getSimpleName();
@@ -241,48 +241,36 @@ public class SplitScreenController implements DragAndDropPolicy.Starter,
    private void startIntentLegacy(PendingIntent intent, Intent fillInIntent,
    private void startIntentLegacy(PendingIntent intent, Intent fillInIntent,
            @SplitScreen.StageType int stage, @SplitPosition int position,
            @SplitScreen.StageType int stage, @SplitPosition int position,
            @Nullable Bundle options) {
            @Nullable Bundle options) {
        final boolean wasInSplit = isSplitScreenVisible();

        LegacyTransitions.ILegacyTransition transition = new LegacyTransitions.ILegacyTransition() {
        LegacyTransitions.ILegacyTransition transition = new LegacyTransitions.ILegacyTransition() {
            @Override
            @Override
            public void onAnimationStart(int transit, RemoteAnimationTarget[] apps,
            public void onAnimationStart(int transit, RemoteAnimationTarget[] apps,
                    RemoteAnimationTarget[] wallpapers, RemoteAnimationTarget[] nonApps,
                    RemoteAnimationTarget[] wallpapers, RemoteAnimationTarget[] nonApps,
                    IRemoteAnimationFinishedCallback finishedCallback,
                    IRemoteAnimationFinishedCallback finishedCallback,
                    SurfaceControl.Transaction t) {
                    SurfaceControl.Transaction t) {
                boolean cancelled = apps == null || apps.length == 0;
                mStageCoordinator.updateSurfaceBounds(null /* layout */, t);
                mStageCoordinator.updateSurfaceBounds(null /* layout */, t);
                if (cancelled) {

                    if (!wasInSplit) {
                if (apps != null) {
                        final WindowContainerTransaction undoWct = new WindowContainerTransaction();
                        mStageCoordinator.prepareExitSplitScreen(STAGE_TYPE_MAIN, undoWct);
                        mSyncQueue.queue(undoWct);
                        mSyncQueue.runInSync(undoT -> {
                            // looks weird, but we want undoT to execute after t but still want the
                            // rest of the syncQueue runnables to aggregate.
                            t.merge(undoT);
                            undoT.merge(t);
                        });
                        return;
                    }
                } else {
                    for (int i = 0; i < apps.length; ++i) {
                    for (int i = 0; i < apps.length; ++i) {
                        if (apps[i].mode == MODE_OPENING) {
                        if (apps[i].mode == MODE_OPENING) {
                            t.show(apps[i].leash);
                            t.show(apps[i].leash);
                        }
                        }
                    }
                    }
                }
                }
                RemoteAnimationTarget divider = mStageCoordinator.getDividerBarLegacyTarget();

                final RemoteAnimationTarget divider = mStageCoordinator.getDividerBarLegacyTarget();
                if (divider.leash != null) {
                if (divider.leash != null) {
                    t.show(divider.leash);
                    t.show(divider.leash);
                }
                }

                t.apply();
                t.apply();
                if (cancelled) return;
                if (finishedCallback != null) {
                    try {
                    try {
                        finishedCallback.onAnimationFinished();
                        finishedCallback.onAnimationFinished();
                    } catch (RemoteException e) {
                    } catch (RemoteException e) {
                        Slog.e(TAG, "Error finishing legacy transition: ", e);
                        Slog.e(TAG, "Error finishing legacy transition: ", e);
                    }
                    }
                }
                }
            }
        };
        };
        WindowContainerTransaction wct = new WindowContainerTransaction();
        WindowContainerTransaction wct = new WindowContainerTransaction();
        options = mStageCoordinator.resolveStartStage(stage, position, options, wct);
        options = mStageCoordinator.resolveStartStage(stage, position, options, wct);
+1 −11
Original line number Original line Diff line number Diff line
@@ -275,8 +275,6 @@ class WindowOrganizerController extends IWindowOrganizerController.Stub
                syncId = startSyncWithOrganizer(callback);
                syncId = startSyncWithOrganizer(callback);
                applyTransaction(t, syncId, null /* transition */, caller);
                applyTransaction(t, syncId, null /* transition */, caller);
                setSyncReady(syncId);
                setSyncReady(syncId);
                mService.mRootWindowContainer.getDisplayContent(DEFAULT_DISPLAY)
                        .executeAppTransition();
            }
            }
        } finally {
        } finally {
            Binder.restoreCallingIdentity(ident);
            Binder.restoreCallingIdentity(ident);
@@ -653,18 +651,10 @@ class WindowOrganizerController extends IWindowOrganizerController.Stub
                    options = activityOptions.toBundle();
                    options = activityOptions.toBundle();
                }
                }


                int res = mService.mAmInternal.sendIntentSender(hop.getPendingIntent().getTarget(),
                mService.mAmInternal.sendIntentSender(hop.getPendingIntent().getTarget(),
                        hop.getPendingIntent().getWhitelistToken(), 0 /* code */,
                        hop.getPendingIntent().getWhitelistToken(), 0 /* code */,
                        hop.getActivityIntent(), resolvedType, null /* finishReceiver */,
                        hop.getActivityIntent(), resolvedType, null /* finishReceiver */,
                        null /* requiredPermission */, options);
                        null /* requiredPermission */, options);
                if (res != ActivityManager.START_SUCCESS
                        && res != ActivityManager.START_TASK_TO_FRONT) {
                    if (!mTransitionController.isShellTransitionsEnabled()) {
                        final DisplayContent dc =
                                mService.mRootWindowContainer.getDisplayContent(DEFAULT_DISPLAY);
                        dc.cancelAppTransition();
                    }
                }
                break;
                break;
            case HIERARCHY_OP_TYPE_CREATE_TASK_FRAGMENT:
            case HIERARCHY_OP_TYPE_CREATE_TASK_FRAGMENT:
                final TaskFragmentCreationParams taskFragmentCreationOptions =
                final TaskFragmentCreationParams taskFragmentCreationOptions =