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

Commit 28036435 authored by Vinit Nayak's avatar Vinit Nayak
Browse files

Refactor TaskShortcutFactory to return List of SystemShortcuts

* Remove ENABLE_SPLIT_SELECT feature flag
* Remove unused SystemUiProxy methods

Bug: 233006032
Test: Options show up as expected
Change-Id: I9b98d962db79363a20ad41faa15404f1c156b9ec
parent c9e64b3c
Loading
Loading
Loading
Loading
+0 −2
Original line number Diff line number Diff line
@@ -104,8 +104,6 @@ public class RecentsAnimationController {
        }
        if (mSplitScreenMinimized != splitScreenMinimized) {
            mSplitScreenMinimized = splitScreenMinimized;
            UI_HELPER_EXECUTOR.execute(() -> SystemUiProxy.INSTANCE.get(context)
                    .setSplitScreenMinimized(splitScreenMinimized));
        }
    }

+1 −2
Original line number Diff line number Diff line
@@ -17,7 +17,6 @@ package com.android.quickstep;

import static com.android.launcher3.anim.Interpolators.ACCEL_1_5;
import static com.android.launcher3.anim.Interpolators.LINEAR;
import static com.android.launcher3.config.FeatureFlags.ENABLE_SPLIT_SELECT;

import android.animation.Animator;
import android.content.Context;
@@ -80,7 +79,7 @@ public abstract class SwipeUpAnimationLogic implements
        mDeviceState = deviceState;
        mGestureState = gestureState;

        mIsSwipeForStagedSplit = ENABLE_SPLIT_SELECT.get() &&
        mIsSwipeForStagedSplit =
                TopTaskTracker.INSTANCE.get(context).getRunningSplitTaskIds().length > 1;

        mTargetGluer = new RemoteTargetGluer(mContext, mGestureState.getActivityInterface());
+0 −34
Original line number Diff line number Diff line
@@ -270,18 +270,6 @@ public class SystemUiProxy implements ISystemUiProxy, DisplayController.DisplayI
        }
    }

    @Override
    public Rect getNonMinimizedSplitScreenSecondaryBounds() {
        if (mSystemUiProxy != null) {
            try {
                return mSystemUiProxy.getNonMinimizedSplitScreenSecondaryBounds();
            } catch (RemoteException e) {
                Log.w(TAG, "Failed call getNonMinimizedSplitScreenSecondaryBounds", e);
            }
        }
        return null;
    }

    public float getLastNavButtonAlpha() {
        return mLastNavButtonAlpha;
    }
@@ -384,28 +372,6 @@ public class SystemUiProxy implements ISystemUiProxy, DisplayController.DisplayI
        }
    }

    @Override
    public void handleImageAsScreenshot(Bitmap bitmap, Rect rect, Insets insets, int i) {
        if (mSystemUiProxy != null) {
            try {
                mSystemUiProxy.handleImageAsScreenshot(bitmap, rect, insets, i);
            } catch (RemoteException e) {
                Log.w(TAG, "Failed call handleImageAsScreenshot", e);
            }
        }
    }

    @Override
    public void setSplitScreenMinimized(boolean minimized) {
        if (mSystemUiProxy != null) {
            try {
                mSystemUiProxy.setSplitScreenMinimized(minimized);
            } catch (RemoteException e) {
                Log.w(TAG, "Failed call setSplitScreenMinimized", e);
            }
        }
    }

    @Override
    public void notifySwipeUpGestureStarted() {
        if (mSystemUiProxy != null) {
+13 −62
Original line number Diff line number Diff line
@@ -23,7 +23,6 @@ import static com.android.quickstep.views.OverviewActionsView.DISABLED_NO_THUMBN
import static com.android.quickstep.views.OverviewActionsView.DISABLED_ROTATED;

import android.annotation.SuppressLint;
import android.app.ActivityManager;
import android.content.Context;
import android.graphics.Insets;
import android.graphics.Matrix;
@@ -37,17 +36,12 @@ import androidx.annotation.RequiresApi;

import com.android.launcher3.BaseActivity;
import com.android.launcher3.BaseDraggingActivity;
import com.android.launcher3.DeviceProfile;
import com.android.launcher3.R;
import com.android.launcher3.config.FeatureFlags;
import com.android.launcher3.model.data.ItemInfo;
import com.android.launcher3.model.data.WorkspaceItemInfo;
import com.android.launcher3.popup.SystemShortcut;
import com.android.launcher3.touch.PagedOrientationHandler;
import com.android.launcher3.util.ResourceBasedOverride;
import com.android.launcher3.util.SplitConfigurationOptions.SplitPositionOption;
import com.android.launcher3.views.ActivityContext;
import com.android.quickstep.TaskShortcutFactory.SplitSelectSystemShortcut;
import com.android.quickstep.util.RecentsOrientedState;
import com.android.quickstep.views.OverviewActionsView;
import com.android.quickstep.views.RecentsView;
@@ -66,7 +60,7 @@ import java.util.List;
public class TaskOverlayFactory implements ResourceBasedOverride {

    public static List<SystemShortcut> getEnabledShortcuts(TaskView taskView,
            DeviceProfile deviceProfile, TaskIdAttributeContainer taskContainer) {
            TaskIdAttributeContainer taskContainer) {
        final ArrayList<SystemShortcut> shortcuts = new ArrayList<>();
        final BaseDraggingActivity activity = BaseActivity.fromContext(taskView.getContext());
        boolean hasMultipleTasks = taskView.getTaskIds()[1] != -1;
@@ -75,17 +69,11 @@ public class TaskOverlayFactory implements ResourceBasedOverride {
                continue;
            }

            SystemShortcut shortcut = menuOption.getShortcut(activity, taskContainer);
            if (shortcut == null) {
            List<SystemShortcut> menuShortcuts = menuOption.getShortcuts(activity, taskContainer);
            if (menuShortcuts == null) {
                continue;
            }

            if (menuOption == TaskShortcutFactory.SPLIT_SCREEN &&
                    FeatureFlags.ENABLE_SPLIT_SELECT.get()) {
                addSplitOptions(shortcuts, activity, taskView, deviceProfile);
            } else {
                shortcuts.add(shortcut);
            }
            shortcuts.addAll(menuShortcuts);
        }
        RecentsOrientedState orientedState = taskView.getRecentsView().getPagedViewOrientedState();
        boolean canLauncherRotate = orientedState.isRecentsActivityRotationAllowed();
@@ -94,61 +82,24 @@ public class TaskOverlayFactory implements ResourceBasedOverride {
        // Add overview actions to the menu when in in-place rotate landscape mode.
        if (!canLauncherRotate && isInLandscape) {
            // Add screenshot action to task menu.
            SystemShortcut screenshotShortcut = TaskShortcutFactory.SCREENSHOT
                    .getShortcut(activity, taskContainer);
            if (screenshotShortcut != null) {
                shortcuts.add(screenshotShortcut);
            List<SystemShortcut> screenshotShortcuts = TaskShortcutFactory.SCREENSHOT
                    .getShortcuts(activity, taskContainer);
            if (screenshotShortcuts != null) {
                shortcuts.addAll(screenshotShortcuts);
            }

            // Add modal action only if display orientation is the same as the device orientation.
            if (orientedState.getDisplayRotation() == ROTATION_0) {
                SystemShortcut modalShortcut = TaskShortcutFactory.MODAL
                        .getShortcut(activity, taskContainer);
                if (modalShortcut != null) {
                    shortcuts.add(modalShortcut);
                List<SystemShortcut> modalShortcuts = TaskShortcutFactory.MODAL
                        .getShortcuts(activity, taskContainer);
                if (modalShortcuts != null) {
                    shortcuts.addAll(modalShortcuts);
                }
            }
        }
        return shortcuts;
    }


    /**
     * Does NOT add split options in the following scenarios:
     * * The taskView to add split options is already showing split screen tasks
     * * There aren't at least 2 tasks in overview to show split options for
     * * Device is in "Lock task mode"
     * * The taskView to show split options for is the focused task AND we haven't started
     * scrolling in overview (if we haven't scrolled, there's a split overview action button so
     * we don't need this menu option)
     */
    private static void addSplitOptions(List<SystemShortcut> outShortcuts,
            BaseDraggingActivity activity, TaskView taskView, DeviceProfile deviceProfile) {
        RecentsView recentsView = taskView.getRecentsView();
        PagedOrientationHandler orientationHandler = recentsView.getPagedOrientationHandler();
        int[] taskViewTaskIds = taskView.getTaskIds();
        boolean taskViewHasMultipleTasks = taskViewTaskIds[0] != -1 &&
                taskViewTaskIds[1] != -1;
        boolean notEnoughTasksToSplit = recentsView.getTaskViewCount() < 2;
        boolean isFocusedTask = deviceProfile.isTablet && taskView.isFocusedTask();
        boolean isTaskInExpectedScrollPosition =
                recentsView.isTaskInExpectedScrollPosition(recentsView.indexOfChild(taskView));
        ActivityManager activityManager =
                (ActivityManager) taskView.getContext().getSystemService(Context.ACTIVITY_SERVICE);
        boolean isLockTaskMode = activityManager.isInLockTaskMode();

        if (taskViewHasMultipleTasks || notEnoughTasksToSplit || isLockTaskMode ||
                (isFocusedTask && isTaskInExpectedScrollPosition)) {
            return;
        }

        List<SplitPositionOption> positions =
                orientationHandler.getSplitPositionOptions(deviceProfile);
        for (SplitPositionOption option : positions) {
            outShortcuts.add(new SplitSelectSystemShortcut(activity, taskView, option));
        }
    }

    public TaskOverlay createOverlay(TaskThumbnailView thumbnailView) {
        return new TaskOverlay(thumbnailView);
    }
@@ -170,7 +121,7 @@ public class TaskOverlayFactory implements ResourceBasedOverride {
    /** Note that these will be shown in order from top to bottom, if available for the task. */
    private static final TaskShortcutFactory[] MENU_OPTIONS = new TaskShortcutFactory[]{
            TaskShortcutFactory.APP_INFO,
            TaskShortcutFactory.SPLIT_SCREEN,
            TaskShortcutFactory.SPLIT_SELECT,
            TaskShortcutFactory.PIN,
            TaskShortcutFactory.INSTALL,
            TaskShortcutFactory.FREE_FORM,
+107 −62
Original line number Diff line number Diff line
@@ -16,14 +16,13 @@

package com.android.quickstep;

import static android.view.Display.DEFAULT_DISPLAY;

import static com.android.launcher3.config.FeatureFlags.ENABLE_OVERVIEW_SELECTIONS;
import static com.android.launcher3.logging.StatsLogManager.LauncherEvent.LAUNCHER_SYSTEM_SHORTCUT_FREE_FORM_TAP;
import static com.android.launcher3.logging.StatsLogManager.LauncherEvent.LAUNCHER_SYSTEM_SHORTCUT_SPLIT_SCREEN_TAP;

import android.app.Activity;
import android.app.ActivityManager;
import android.app.ActivityOptions;
import android.content.Context;
import android.graphics.Bitmap;
import android.graphics.Color;
import android.graphics.Rect;
@@ -32,6 +31,8 @@ import android.os.Looper;
import android.view.View;
import android.window.SplashScreen;

import androidx.annotation.Nullable;

import com.android.launcher3.BaseDraggingActivity;
import com.android.launcher3.DeviceProfile;
import com.android.launcher3.R;
@@ -39,6 +40,7 @@ import com.android.launcher3.logging.StatsLogManager.LauncherEvent;
import com.android.launcher3.model.WellbeingModel;
import com.android.launcher3.popup.SystemShortcut;
import com.android.launcher3.popup.SystemShortcut.AppInfo;
import com.android.launcher3.touch.PagedOrientationHandler;
import com.android.launcher3.util.InstantAppResolver;
import com.android.launcher3.util.SplitConfigurationOptions.SplitPositionOption;
import com.android.quickstep.views.RecentsView;
@@ -55,13 +57,18 @@ import com.android.systemui.shared.system.WindowManagerWrapper;

import java.util.Collections;
import java.util.List;
import java.util.function.Function;
import java.util.stream.Collectors;

/**
 * Represents a system shortcut that can be shown for a recent task.
 */
public interface TaskShortcutFactory {
    SystemShortcut getShortcut(BaseDraggingActivity activity,
            TaskIdAttributeContainer taskContainer);
    @Nullable
    default List<SystemShortcut> getShortcuts(BaseDraggingActivity activity,
            TaskIdAttributeContainer taskContainer) {
        return null;
    }

    default boolean showForSplitscreen() {
        return false;
@@ -69,7 +76,7 @@ public interface TaskShortcutFactory {

    TaskShortcutFactory APP_INFO = new TaskShortcutFactory() {
        @Override
        public SystemShortcut getShortcut(BaseDraggingActivity activity,
        public List<SystemShortcut> getShortcuts(BaseDraggingActivity activity,
                TaskIdAttributeContainer taskContainer) {
            TaskView taskView = taskContainer.getTaskView();
            AppInfo.SplitAccessibilityInfo accessibilityInfo =
@@ -77,7 +84,8 @@ public interface TaskShortcutFactory {
                            TaskUtils.getTitle(taskView.getContext(), taskContainer.getTask()),
                            taskContainer.getA11yNodeId()
                    );
            return new AppInfo(activity, taskContainer.getItemInfo(), taskView, accessibilityInfo);
            return Collections.singletonList(new AppInfo(activity, taskContainer.getItemInfo(),
                    taskView, accessibilityInfo));
        }

        @Override
@@ -103,7 +111,7 @@ public interface TaskShortcutFactory {
        protected abstract boolean onActivityStarted(BaseDraggingActivity activity);

        @Override
        public SystemShortcut getShortcut(BaseDraggingActivity activity,
        public List<SystemShortcut> getShortcuts(BaseDraggingActivity activity,
                TaskIdAttributeContainer taskContainer) {
            final Task task  = taskContainer.getTask();
            if (!task.isDockable) {
@@ -112,8 +120,8 @@ public interface TaskShortcutFactory {
            if (!isAvailable(activity, task.key.displayId)) {
                return null;
            }
            return new MultiWindowSystemShortcut(mIconRes, mTextRes, activity, taskContainer, this,
                    mLauncherEvent);
            return Collections.singletonList(new MultiWindowSystemShortcut(mIconRes,
                    mTextRes, activity, taskContainer, this, mLauncherEvent));
        }
    }

@@ -242,34 +250,44 @@ public interface TaskShortcutFactory {
        }
    }

    /** @Deprecated */
    TaskShortcutFactory SPLIT_SCREEN = new MultiWindowFactory(R.drawable.ic_split_screen,
            R.string.recent_task_option_split_screen, LAUNCHER_SYSTEM_SHORTCUT_SPLIT_SCREEN_TAP) {

        @Override
        protected boolean isAvailable(BaseDraggingActivity activity, int displayId) {
            // Don't show menu-item if already in multi-window and the task is from
            // the secondary display.
            // TODO(b/118266305): Temporarily disable splitscreen for secondary display while new
            // implementation is enabled
            return !activity.getDeviceProfile().isMultiWindowMode
                    && (displayId == -1 || displayId == DEFAULT_DISPLAY);
        }

    /**
     * Does NOT add split options in the following scenarios:
     * * The taskView to add split options is already showing split screen tasks
     * * There aren't at least 2 tasks in overview to show split options for
     * * Device is in "Lock task mode"
     * * The taskView to show split options for is the focused task AND we haven't started
     * scrolling in overview (if we haven't scrolled, there's a split overview action button so
     * we don't need this menu option)
     */
    TaskShortcutFactory SPLIT_SELECT = new TaskShortcutFactory() {
        @Override
        protected ActivityOptions makeLaunchOptions(Activity activity) {
            final int navBarPosition = WindowManagerWrapper.getInstance().getNavBarPosition(
                    activity.getDisplayId());
            if (navBarPosition == WindowManagerWrapper.NAV_BAR_POS_INVALID) {
        public List<SystemShortcut> getShortcuts(BaseDraggingActivity activity,
                TaskIdAttributeContainer taskContainer) {
            DeviceProfile deviceProfile = activity.getDeviceProfile();
            TaskView taskView = taskContainer.getTaskView();
            RecentsView recentsView = taskView.getRecentsView();
            PagedOrientationHandler orientationHandler = recentsView.getPagedOrientationHandler();
            int[] taskViewTaskIds = taskView.getTaskIds();
            boolean taskViewHasMultipleTasks = taskViewTaskIds[0] != -1 &&
                    taskViewTaskIds[1] != -1;
            boolean notEnoughTasksToSplit = recentsView.getTaskViewCount() < 2;
            boolean isFocusedTask = deviceProfile.isTablet && taskView.isFocusedTask();
            boolean isTaskInExpectedScrollPosition =
                    recentsView.isTaskInExpectedScrollPosition(recentsView.indexOfChild(taskView));
            ActivityManager activityManager = (ActivityManager) taskView.getContext()
                    .getSystemService(Context.ACTIVITY_SERVICE);
            boolean isLockTaskMode = activityManager.isInLockTaskMode();

            if (taskViewHasMultipleTasks || notEnoughTasksToSplit || isLockTaskMode ||
                    (isFocusedTask && isTaskInExpectedScrollPosition)) {
                return null;
            }
            boolean dockTopOrLeft = navBarPosition != WindowManagerWrapper.NAV_BAR_POS_LEFT;
            return ActivityOptionsCompat.makeSplitScreenOptions(dockTopOrLeft);
        }

        @Override
        protected boolean onActivityStarted(BaseDraggingActivity activity) {
            return true;
            return orientationHandler.getSplitPositionOptions(deviceProfile)
                    .stream()
                    .map((Function<SplitPositionOption, SystemShortcut>) option ->
                            new SplitSelectSystemShortcut(activity, taskView, option))
                    .collect(Collectors.toList());
        }
    };

@@ -297,7 +315,10 @@ public interface TaskShortcutFactory {
        }
    };

    TaskShortcutFactory PIN = (activity, taskContainer) -> {
    TaskShortcutFactory PIN = new TaskShortcutFactory() {
        @Override
        public List<SystemShortcut> getShortcuts(BaseDraggingActivity activity,
                TaskIdAttributeContainer taskContainer) {
            if (!SystemUiProxy.INSTANCE.get(activity).isActive()) {
                return null;
            }
@@ -308,7 +329,8 @@ public interface TaskShortcutFactory {
                // We shouldn't be able to pin while an app is locked.
                return null;
            }
        return new PinSystemShortcut(activity, taskContainer);
            return Collections.singletonList(new PinSystemShortcut(activity, taskContainer));
        }
    };

    class PinSystemShortcut extends SystemShortcut<BaseDraggingActivity> {
@@ -335,26 +357,49 @@ public interface TaskShortcutFactory {
        }
    }

    TaskShortcutFactory INSTALL = (activity, taskContainer) ->
            InstantAppResolver.newInstance(activity).isInstantApp(activity,
                    taskContainer.getTask().getTopComponent().getPackageName())
                    ? new SystemShortcut.Install(activity, taskContainer.getItemInfo(),
                    taskContainer.getTaskView()) : null;
    TaskShortcutFactory INSTALL = new TaskShortcutFactory() {
        @Override
        public List<SystemShortcut> getShortcuts(BaseDraggingActivity activity,
                TaskIdAttributeContainer taskContainer) {
            return InstantAppResolver.newInstance(activity).isInstantApp(activity,
                    taskContainer.getTask().getTopComponent().getPackageName()) ?
                    Collections.singletonList(new SystemShortcut.Install(activity,
                            taskContainer.getItemInfo(), taskContainer.getTaskView())) :
                    null;
        }
    };

    TaskShortcutFactory WELLBEING = (activity, taskContainer) ->
            WellbeingModel.SHORTCUT_FACTORY.getShortcut(activity, taskContainer.getItemInfo(),
                    taskContainer.getTaskView());
    TaskShortcutFactory WELLBEING = new TaskShortcutFactory() {
        @Override
        public List<SystemShortcut> getShortcuts(BaseDraggingActivity activity,
                TaskIdAttributeContainer taskContainer) {
            return Collections.singletonList(
                    WellbeingModel.SHORTCUT_FACTORY.getShortcut(activity,
                            taskContainer.getItemInfo(), taskContainer.getTaskView()));
        }
    };

    TaskShortcutFactory SCREENSHOT = (activity, taskContainer) ->
    TaskShortcutFactory SCREENSHOT = new TaskShortcutFactory() {
        @Override
        public List<SystemShortcut> getShortcuts(BaseDraggingActivity activity,
                TaskIdAttributeContainer taskContainer) {
            return Collections.singletonList(
                    taskContainer.getThumbnailView().getTaskOverlay()
                            .getScreenshotShortcut(activity, taskContainer.getItemInfo(),
                            taskContainer.getTaskView());
                                    taskContainer.getTaskView()));
        }
    };

    TaskShortcutFactory MODAL = (activity, taskContainer) -> {
    TaskShortcutFactory MODAL = new TaskShortcutFactory() {
        @Override
        public List<SystemShortcut> getShortcuts(BaseDraggingActivity activity,
                TaskIdAttributeContainer taskContainer) {
            if (ENABLE_OVERVIEW_SELECTIONS.get()) {
            return taskContainer.getThumbnailView().getTaskOverlay().getModalStateSystemShortcut(
                    taskContainer.getItemInfo(), taskContainer.getTaskView());
                return Collections.singletonList(taskContainer.getThumbnailView().getTaskOverlay()
                        .getModalStateSystemShortcut(
                                        taskContainer.getItemInfo(), taskContainer.getTaskView()));
            }
            return null;
        }
    };
}
Loading