Refactor/clean up Overview Actions buttons

Since the number of Overview actions is growing, this patch factors out the button hiding logic so it's not all handled in OverviewActionsView.

Also, since splitscreen can now be carried out on Taskbar targets, the split button is no longer ever disabled (only hidden), so removed unused code for that.

Bug: 274835596
Test: Manual
Flag: NA
Change-Id: Icacdee6d0e6071ccb400dfc25a84572e7e9ce772
diff --git a/quickstep/res/layout/overview_actions_container.xml b/quickstep/res/layout/overview_actions_container.xml
index 0fda0bf..fe517fa 100644
--- a/quickstep/res/layout/overview_actions_container.xml
+++ b/quickstep/res/layout/overview_actions_container.xml
@@ -31,7 +31,7 @@
             android:layout_height="1dp"
             android:layout_weight="1" />
 
-        <Button
+        <com.android.quickstep.views.ScreenshotActionButton
             android:id="@+id/action_screenshot"
             style="@style/OverviewActionButton"
             android:layout_width="wrap_content"
@@ -40,17 +40,12 @@
             android:text="@string/action_screenshot"
             android:theme="@style/ThemeControlHighlightWorkspaceColor" />
 
-        <Space
-            android:id="@+id/action_split_space"
-            android:layout_width="@dimen/overview_actions_button_spacing"
-            android:layout_height="1dp"
-            android:visibility="gone" />
-
-        <Button
+        <com.android.quickstep.views.SplitActionButton
             android:id="@+id/action_split"
             style="@style/OverviewActionButton"
             android:layout_width="wrap_content"
             android:layout_height="wrap_content"
+            android:layout_marginStart="@dimen/overview_actions_button_spacing"
             android:text="@string/action_split"
             android:theme="@style/ThemeControlHighlightWorkspaceColor"
             android:visibility="gone" />
diff --git a/quickstep/src/com/android/quickstep/views/ActionButton.kt b/quickstep/src/com/android/quickstep/views/ActionButton.kt
new file mode 100644
index 0000000..5c004cc
--- /dev/null
+++ b/quickstep/src/com/android/quickstep/views/ActionButton.kt
@@ -0,0 +1,63 @@
+/*
+ * Copyright (C) 2023 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.quickstep.views
+
+import android.content.Context
+import android.util.AttributeSet
+import android.widget.Button
+
+/**
+ * A button on the Overview Actions Bar. Custom logic for hiding/showing each button type is handled
+ * in the respective subclass.
+ */
+open class ActionButton : Button {
+    private var mHiddenFlags = 0
+
+    constructor(context: Context) : super(context)
+    constructor(context: Context, attrs: AttributeSet?) : super(context, attrs)
+    constructor(
+        context: Context,
+        attrs: AttributeSet?,
+        defStyleAttr: Int
+    ) : super(context, attrs, defStyleAttr)
+
+    /**
+     * Updates the proper flags to indicate whether the button should be hidden.
+     *
+     * @param flag The flag to update.
+     * @param enable Whether to enable the hidden flag: True will cause view to be hidden.
+     */
+    protected fun updateHiddenFlags(flag: Int, enable: Boolean) {
+        if (enable) {
+            mHiddenFlags = mHiddenFlags or flag
+        } else {
+            mHiddenFlags = mHiddenFlags and flag.inv()
+        }
+        val shouldBeVisible = mHiddenFlags == 0
+        this.visibility = if (shouldBeVisible) VISIBLE else GONE
+    }
+
+    /** Show/hide the button when the focused task is a single/pair. */
+    open fun updateForMultipleTasks(hasMultipleTasks: Boolean) {
+        // overridden in subclass, or else don't do anything
+    }
+
+    /** Show/hide the button depending on if the device is a tablet. */
+    open fun updateForTablet(isTablet: Boolean) {
+        // overridden in subclass, or else don't do anything
+    }
+}
diff --git a/quickstep/src/com/android/quickstep/views/OverviewActionsView.java b/quickstep/src/com/android/quickstep/views/OverviewActionsView.java
index 7f1d619..8692e4e 100644
--- a/quickstep/src/com/android/quickstep/views/OverviewActionsView.java
+++ b/quickstep/src/com/android/quickstep/views/OverviewActionsView.java
@@ -22,7 +22,6 @@
 import android.util.AttributeSet;
 import android.view.View;
 import android.view.View.OnClickListener;
-import android.widget.Button;
 import android.widget.FrameLayout;
 
 import androidx.annotation.IntDef;
@@ -41,6 +40,8 @@
 
 import java.lang.annotation.Retention;
 import java.lang.annotation.RetentionPolicy;
+import java.util.ArrayList;
+import java.util.List;
 
 /**
  * View for showing action buttons in Overview
@@ -89,14 +90,11 @@
     private static final int INDEX_SCROLL_ALPHA = 5;
     private static final int NUM_ALPHAS = 6;
 
-    public @interface SplitButtonHiddenFlags { }
-    public static final int FLAG_IS_NOT_TABLET = 1 << 0;
-
-    public @interface SplitButtonDisabledFlags { }
-    public static final int FLAG_SINGLE_TASK = 1 << 0;
-
     private MultiValueAlpha mMultiValueAlpha;
-    private Button mSplitButton;
+
+    private List<ActionButton> mActionButtons = new ArrayList<>();
+    private ScreenshotActionButton mScreenshotButton;
+    private SplitActionButton mSplitButton;
 
     @ActionsHiddenFlags
     private int mHiddenFlags;
@@ -104,12 +102,6 @@
     @ActionsDisabledFlags
     protected int mDisabledFlags;
 
-    @SplitButtonHiddenFlags
-    private int mSplitButtonHiddenFlags;
-
-    @SplitButtonDisabledFlags
-    private int mSplitButtonDisabledFlags;
-
     @Nullable
     protected T mCallbacks;
 
@@ -135,9 +127,12 @@
         mMultiValueAlpha = new MultiValueAlpha(findViewById(R.id.action_buttons), NUM_ALPHAS);
         mMultiValueAlpha.setUpdateVisibility(true);
 
-        findViewById(R.id.action_screenshot).setOnClickListener(this);
+        mScreenshotButton = findViewById(R.id.action_screenshot);
+        mScreenshotButton.setOnClickListener(this);
+        mActionButtons.add(mScreenshotButton);
         mSplitButton = findViewById(R.id.action_split);
         mSplitButton.setOnClickListener(this);
+        mActionButtons.add(mSplitButton);
     }
 
     /**
@@ -201,40 +196,28 @@
         }
         boolean isEnabled = (mDisabledFlags & ~DISABLED_ROTATED) == 0;
         LayoutUtils.setViewEnabled(this, isEnabled);
-        updateSplitButtonEnabledState();
     }
 
     /**
-     * Updates the proper flags to indicate whether the "Split screen" button should be hidden.
-     *
-     * @param flag   The flag to update.
-     * @param enable Whether to enable the hidden flag: True will cause view to be hidden.
+     * Updates flags to hide and show actions buttons when a grouped task (split screen) is focused.
+     * @param isGroupedTask True if the focused task is a grouped task.
      */
-    public void updateSplitButtonHiddenFlags(@SplitButtonHiddenFlags int flag, boolean enable) {
-        if (enable) {
-            mSplitButtonHiddenFlags |= flag;
-        } else {
-            mSplitButtonHiddenFlags &= ~flag;
+    public void updateForGroupedTask(boolean isGroupedTask) {
+        for (ActionButton button : mActionButtons) {
+            // Update flags to show/hide buttons.
+            button.updateForMultipleTasks(isGroupedTask);
         }
-        if (mSplitButton == null) return;
-        boolean shouldBeVisible = mSplitButtonHiddenFlags == 0;
-        mSplitButton.setVisibility(shouldBeVisible ? VISIBLE : GONE);
-        findViewById(R.id.action_split_space).setVisibility(shouldBeVisible ? VISIBLE : GONE);
     }
 
     /**
-     * Updates the proper flags to indicate whether the "Split screen" button should be disabled.
-     *
-     * @param flag   The flag to update.
-     * @param enable Whether to enable the disable flag: True will cause view to be disabled.
+     * Updates flags to hide and show actions buttons depending on if the device is a tablet.
+     * @param isTablet True if the current device is a tablet.
      */
-    public void updateSplitButtonDisabledFlags(@SplitButtonDisabledFlags int flag, boolean enable) {
-        if (enable) {
-            mSplitButtonDisabledFlags |= flag;
-        } else {
-            mSplitButtonDisabledFlags &= ~flag;
+    public void updateForTablet(boolean isTablet) {
+        for (ActionButton button : mActionButtons) {
+            // Update flags to show/hide buttons.
+            button.updateForTablet(isTablet);
         }
-        updateSplitButtonEnabledState();
     }
 
     public MultiProperty getContentAlpha() {
@@ -312,18 +295,4 @@
                 (dp.isLandscape ? R.drawable.ic_split_horizontal : R.drawable.ic_split_vertical),
                 0, 0, 0);
     }
-
-    /**
-     * Enables/disables the "Split" button based on the status of mSplitButtonDisabledFlags and
-     * mDisabledFlags.
-     */
-    private void updateSplitButtonEnabledState() {
-        if (mSplitButton == null) {
-            return;
-        }
-        boolean isParentEnabled = (mDisabledFlags & ~DISABLED_ROTATED) == 0;
-        boolean shouldBeEnabled = mSplitButtonDisabledFlags == 0 && isParentEnabled;
-        mSplitButton.setEnabled(shouldBeEnabled);
-    }
-
 }
diff --git a/quickstep/src/com/android/quickstep/views/RecentsView.java b/quickstep/src/com/android/quickstep/views/RecentsView.java
index 7972999..6a275e6 100644
--- a/quickstep/src/com/android/quickstep/views/RecentsView.java
+++ b/quickstep/src/com/android/quickstep/views/RecentsView.java
@@ -20,7 +20,6 @@
 import static android.view.Surface.ROTATION_0;
 import static android.view.View.MeasureSpec.EXACTLY;
 import static android.view.View.MeasureSpec.makeMeasureSpec;
-
 import static com.android.app.animation.Interpolators.ACCELERATE;
 import static com.android.app.animation.Interpolators.ACCELERATE_0_75;
 import static com.android.app.animation.Interpolators.ACCELERATE_DECELERATE;
@@ -34,6 +33,7 @@
 import static com.android.launcher3.AbstractFloatingView.TYPE_TASK_MENU;
 import static com.android.launcher3.AbstractFloatingView.getTopOpenViewWithType;
 import static com.android.launcher3.BaseActivity.STATE_HANDLER_INVISIBILITY_FLAGS;
+import static com.android.launcher3.Flags.enableGridOnlyOverview;
 import static com.android.launcher3.LauncherAnimUtils.SUCCESS_TRANSITION_PROGRESS;
 import static com.android.launcher3.LauncherAnimUtils.VIEW_ALPHA;
 import static com.android.launcher3.LauncherState.BACKGROUND_APP;
@@ -42,7 +42,6 @@
 import static com.android.launcher3.Utilities.mapToRange;
 import static com.android.launcher3.Utilities.squaredHypot;
 import static com.android.launcher3.Utilities.squaredTouchSlop;
-import static com.android.launcher3.Flags.enableGridOnlyOverview;
 import static com.android.launcher3.logging.StatsLogManager.LauncherEvent.LAUNCHER_OVERVIEW_ACTIONS_SPLIT;
 import static com.android.launcher3.logging.StatsLogManager.LauncherEvent.LAUNCHER_TASK_CLEAR_ALL;
 import static com.android.launcher3.logging.StatsLogManager.LauncherEvent.LAUNCHER_TASK_DISMISS_SWIPE_UP;
@@ -57,8 +56,6 @@
 import static com.android.quickstep.util.LogUtils.splitFailureMessage;
 import static com.android.quickstep.views.ClearAllButton.DISMISS_ALPHA;
 import static com.android.quickstep.views.DesktopTaskView.isDesktopModeSupported;
-import static com.android.quickstep.views.OverviewActionsView.FLAG_IS_NOT_TABLET;
-import static com.android.quickstep.views.OverviewActionsView.FLAG_SINGLE_TASK;
 import static com.android.quickstep.views.OverviewActionsView.HIDDEN_ACTIONS_IN_MENU;
 import static com.android.quickstep.views.OverviewActionsView.HIDDEN_DESKTOP;
 import static com.android.quickstep.views.OverviewActionsView.HIDDEN_NON_ZERO_ROTATION;
@@ -3927,18 +3924,23 @@
     }
 
     /**
-     * Hides all overview actions if current page is for split apps, shows otherwise
-     * If actions are showing, we only show split option if
+     * Hides all overview actions if user is halfway through split selection, shows otherwise.
+     * We only show split option if:
+     * * Focused view is a single app
      * * Device is large screen
-     * * There are at least 2 tasks to invoke split
      */
     private void updateCurrentTaskActionsVisibility() {
-        boolean isCurrentSplit = getCurrentPageTaskView() instanceof GroupedTaskView;
-        mActionsView.updateHiddenFlags(HIDDEN_SPLIT_SCREEN, isCurrentSplit);
+        boolean isGroupedTask = getCurrentPageTaskView() != null
+                && getCurrentPageTaskView().containsMultipleTasks();
+        // Update flags to see if entire actions bar should be hidden.
+        mActionsView.updateHiddenFlags(HIDDEN_SPLIT_SCREEN, isGroupedTask);
         mActionsView.updateHiddenFlags(HIDDEN_SPLIT_SELECT_ACTIVE, isSplitSelectionActive());
-        mActionsView.updateSplitButtonHiddenFlags(FLAG_IS_NOT_TABLET,
-                !mActivity.getDeviceProfile().isTablet);
-        mActionsView.updateSplitButtonDisabledFlags(FLAG_SINGLE_TASK, /*enable=*/ false);
+        // Update flags to see if actions bar should show buttons for a single task or a pair of
+        // tasks.
+        mActionsView.updateForGroupedTask(isGroupedTask);
+        // Update flags to see if split button should be hidden.
+        mActionsView.updateForTablet(mActivity.getDeviceProfile().isTablet);
+
         if (isDesktopModeSupported()) {
             boolean isCurrentDesktop = getCurrentPageTaskView() instanceof DesktopTaskView;
             mActionsView.updateHiddenFlags(HIDDEN_DESKTOP, isCurrentDesktop);
diff --git a/quickstep/src/com/android/quickstep/views/ScreenshotActionButton.kt b/quickstep/src/com/android/quickstep/views/ScreenshotActionButton.kt
new file mode 100644
index 0000000..9cb48b8
--- /dev/null
+++ b/quickstep/src/com/android/quickstep/views/ScreenshotActionButton.kt
@@ -0,0 +1,41 @@
+/*
+ * Copyright (C) 2023 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.quickstep.views
+
+import android.content.Context
+import android.util.AttributeSet
+
+/** A button on the Overview Actions Bar for screenshotting the focused app. */
+class ScreenshotActionButton : ActionButton {
+    companion object {
+        const val FLAG_MULTIPLE_TASKS_HIDE_SCREENSHOT = 1 shl 0
+    }
+
+    constructor(context: Context) : super(context)
+    constructor(context: Context, attrs: AttributeSet?) : super(context, attrs)
+    constructor(
+        context: Context,
+        attrs: AttributeSet?,
+        defStyleAttr: Int
+    ) : super(context, attrs, defStyleAttr)
+
+    /** Show/hide the button when the focused task is a single/pair. */
+    override fun updateForMultipleTasks(hasMultipleTasks: Boolean) {
+        // Hidden for multiple tasks
+        updateHiddenFlags(FLAG_MULTIPLE_TASKS_HIDE_SCREENSHOT, hasMultipleTasks)
+    }
+}
diff --git a/quickstep/src/com/android/quickstep/views/SplitActionButton.kt b/quickstep/src/com/android/quickstep/views/SplitActionButton.kt
new file mode 100644
index 0000000..88d1a77
--- /dev/null
+++ b/quickstep/src/com/android/quickstep/views/SplitActionButton.kt
@@ -0,0 +1,48 @@
+/*
+ * Copyright (C) 2023 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.quickstep.views
+
+import android.content.Context
+import android.util.AttributeSet
+
+/** A button on the Overview Actions Bar for initiating split screen. */
+class SplitActionButton : ActionButton {
+    companion object {
+        const val FLAG_IS_NOT_TABLET_HIDE_SPLIT = 1 shl 0
+        const val FLAG_MULTIPLE_TASKS_HIDE_SPLIT = 1 shl 1
+    }
+
+    constructor(context: Context) : super(context)
+    constructor(context: Context, attrs: AttributeSet?) : super(context, attrs)
+    constructor(
+        context: Context,
+        attrs: AttributeSet?,
+        defStyleAttr: Int
+    ) : super(context, attrs, defStyleAttr)
+
+    /** Show/hide the button when the focused task is a single/pair. */
+    override fun updateForMultipleTasks(hasMultipleTasks: Boolean) {
+        // Hidden for multiple tasks
+        updateHiddenFlags(FLAG_MULTIPLE_TASKS_HIDE_SPLIT, hasMultipleTasks)
+    }
+
+    /** Show/hide the button depending on if the device is a tablet. */
+    override fun updateForTablet(isTablet: Boolean) {
+        // Hidden for non-tablets
+        updateHiddenFlags(FLAG_IS_NOT_TABLET_HIDE_SPLIT, !isTablet)
+    }
+}