Merge "Move taskbar to be closer to QSB" into sc-dev
diff --git a/quickstep/res/layout/taskbar.xml b/quickstep/res/layout/taskbar.xml
index 84e2304..732222a 100644
--- a/quickstep/res/layout/taskbar.xml
+++ b/quickstep/res/layout/taskbar.xml
@@ -24,7 +24,6 @@
         android:id="@+id/taskbar_view"
         android:layout_width="wrap_content"
         android:layout_height="wrap_content"
-        android:background="@color/taskbar_background"
         android:gravity="center"/>
 
 </com.android.launcher3.taskbar.TaskbarContainerView>
\ No newline at end of file
diff --git a/quickstep/src/com/android/launcher3/taskbar/TaskbarAnimationController.java b/quickstep/src/com/android/launcher3/taskbar/TaskbarAnimationController.java
index 7c54e2d..46e4506 100644
--- a/quickstep/src/com/android/launcher3/taskbar/TaskbarAnimationController.java
+++ b/quickstep/src/com/android/launcher3/taskbar/TaskbarAnimationController.java
@@ -50,6 +50,10 @@
     private final AnimatedFloat mTaskbarScaleForLauncherState = new AnimatedFloat(
             this::updateScale);
 
+    // TranslationY.
+    private final AnimatedFloat mTaskbarTranslationYForLauncherState = new AnimatedFloat(
+            this::updateTranslationY);
+
     public TaskbarAnimationController(BaseQuickstepLauncher launcher,
             TaskbarController.TaskbarAnimationControllerCallbacks taskbarCallbacks) {
         mLauncher = launcher;
@@ -81,6 +85,10 @@
         return mTaskbarScaleForLauncherState;
     }
 
+    protected AnimatedFloat getTaskbarTranslationYForLauncherState() {
+        return mTaskbarTranslationYForLauncherState;
+    }
+
     protected Animator createAnimToBackgroundAlpha(float toAlpha, long duration) {
         return mTaskbarBackgroundAlpha.animateToValue(mTaskbarBackgroundAlpha.value, toAlpha)
                 .setDuration(duration);
@@ -95,6 +103,7 @@
         mTaskbarCallbacks.updateTaskbarBackgroundAlpha(mTaskbarBackgroundAlpha.value);
         updateVisibilityAlpha();
         updateScale();
+        updateTranslationY();
     }
 
     private void updateVisibilityAlpha() {
@@ -120,6 +129,15 @@
         mTaskbarCallbacks.updateTaskbarScale(scale);
     }
 
+    private void updateTranslationY() {
+        // We use mTaskbarBackgroundAlpha as a proxy for whether Launcher is resumed/paused, the
+        // assumption being that Taskbar should always be at translationY 0f regardless of the
+        // current LauncherState if Launcher is paused.
+        float translationY = mTaskbarTranslationYForLauncherState.value;
+        translationY = Utilities.mapRange(mTaskbarBackgroundAlpha.value, translationY, 0f);
+        mTaskbarCallbacks.updateTaskbarTranslationY(translationY);
+    }
+
     private void setNavBarButtonAlpha(float navBarAlpha) {
         SystemUiProxy.INSTANCE.get(mLauncher).setNavBarButtonAlpha(navBarAlpha, false);
     }
diff --git a/quickstep/src/com/android/launcher3/taskbar/TaskbarContainerView.java b/quickstep/src/com/android/launcher3/taskbar/TaskbarContainerView.java
index ccf6b41..621bba7 100644
--- a/quickstep/src/com/android/launcher3/taskbar/TaskbarContainerView.java
+++ b/quickstep/src/com/android/launcher3/taskbar/TaskbarContainerView.java
@@ -19,6 +19,8 @@
 import static com.android.systemui.shared.system.ViewTreeObserverWrapper.InsetsInfo.TOUCHABLE_INSETS_REGION;
 
 import android.content.Context;
+import android.graphics.Canvas;
+import android.graphics.Paint;
 import android.graphics.Rect;
 import android.util.AttributeSet;
 import android.view.View;
@@ -38,6 +40,7 @@
 
     private final int[] mTempLoc = new int[2];
     private final int mFolderMargin;
+    private final Paint mTaskbarBackgroundPaint;
 
     // Initialized in TaskbarController constructor.
     private TaskbarController.TaskbarContainerViewCallbacks mControllerCallbacks;
@@ -63,6 +66,8 @@
             int defStyleAttr, int defStyleRes) {
         super(context, attrs, 1 /* alphaChannelCount */);
         mFolderMargin = getResources().getDimensionPixelSize(R.dimen.taskbar_folder_margin);
+        mTaskbarBackgroundPaint = new Paint();
+        mTaskbarBackgroundPaint.setColor(getResources().getColor(R.color.taskbar_background));
     }
 
     protected void construct(TaskbarController.TaskbarContainerViewCallbacks callbacks) {
@@ -97,11 +102,14 @@
             // mTaskbarView is, since its position never changes and insets rather than overlays.
             int[] loc = mTempLoc;
             float scale = mTaskbarView.getScaleX();
+            float translationY = mTaskbarView.getTranslationY();
             mTaskbarView.setScaleX(1);
             mTaskbarView.setScaleY(1);
+            mTaskbarView.setTranslationY(0);
             mTaskbarView.getLocationInWindow(loc);
             mTaskbarView.setScaleX(scale);
             mTaskbarView.setScaleY(scale);
+            mTaskbarView.setTranslationY(translationY);
             insetsInfo.contentInsets.left = loc[0];
             insetsInfo.contentInsets.top = loc[1];
             insetsInfo.contentInsets.right = getWidth() - (loc[0] + mTaskbarView.getWidth());
@@ -153,4 +161,20 @@
     protected TaskbarActivityContext getTaskbarActivityContext() {
         return mActivity;
     }
+
+    @Override
+    protected void dispatchDraw(Canvas canvas) {
+        canvas.drawRect(0, canvas.getHeight() - mTaskbarView.getHeight(), canvas.getWidth(),
+                canvas.getHeight(), mTaskbarBackgroundPaint);
+        super.dispatchDraw(canvas);
+    }
+
+    /**
+     * Sets the alpha of the background color behind all the Taskbar contents.
+     * @param alpha 0 is fully transparent, 1 is fully opaque.
+     */
+    protected void setTaskbarBackgroundAlpha(float alpha) {
+        mTaskbarBackgroundPaint.setAlpha((int) (alpha * 255));
+        invalidate();
+    }
 }
diff --git a/quickstep/src/com/android/launcher3/taskbar/TaskbarController.java b/quickstep/src/com/android/launcher3/taskbar/TaskbarController.java
index d772964..c93de00 100644
--- a/quickstep/src/com/android/launcher3/taskbar/TaskbarController.java
+++ b/quickstep/src/com/android/launcher3/taskbar/TaskbarController.java
@@ -103,7 +103,7 @@
         return new TaskbarAnimationControllerCallbacks() {
             @Override
             public void updateTaskbarBackgroundAlpha(float alpha) {
-                mTaskbarViewInApp.setBackgroundAlpha(alpha);
+                mTaskbarContainerView.setTaskbarBackgroundAlpha(alpha);
             }
 
             @Override
@@ -117,6 +117,18 @@
                 mTaskbarViewInApp.setScaleX(scale);
                 mTaskbarViewInApp.setScaleY(scale);
             }
+
+            @Override
+            public void updateTaskbarTranslationY(float translationY) {
+                if (translationY < 0) {
+                    // Resize to accommodate the max translation we'll reach.
+                    setTaskbarWindowHeight(mTaskbarSize.y
+                            + mLauncher.getHotseat().getTaskbarOffsetY());
+                } else {
+                    setTaskbarWindowHeight(mTaskbarSize.y);
+                }
+                mTaskbarViewInApp.setTranslationY(translationY);
+            }
         };
     }
 
@@ -240,6 +252,11 @@
             public AnimatedFloat getScaleTarget() {
                 return mTaskbarAnimationController.getTaskbarScaleForLauncherState();
             }
+
+            @Override
+            public AnimatedFloat getTranslationYTarget() {
+                return mTaskbarAnimationController.getTaskbarTranslationYForLauncherState();
+            }
         };
     }
 
@@ -406,13 +423,15 @@
         Rect hotseatBounds = new Rect();
         DeviceProfile grid = mLauncher.getDeviceProfile();
         int hotseatHeight = grid.workspacePadding.bottom + grid.taskbarSize;
-        int hotseatTopDiff = hotseatHeight - grid.taskbarSize;
+        int taskbarOffset = mLauncher.getHotseat().getTaskbarOffsetY();
+        int hotseatTopDiff = hotseatHeight - grid.taskbarSize - taskbarOffset;
+        int hotseatBottomDiff = taskbarOffset;
 
         mTaskbarViewOnHome.getHotseatBounds().roundOut(hotseatBounds);
         mLauncher.getHotseat().setPadding(hotseatBounds.left,
                 hotseatBounds.top + hotseatTopDiff,
                 mTaskbarViewOnHome.getWidth() - hotseatBounds.right,
-                mTaskbarViewOnHome.getHeight() - hotseatBounds.bottom);
+                mTaskbarViewOnHome.getHeight() - hotseatBounds.bottom + hotseatBottomDiff);
     }
 
     private void setWhichTaskbarViewIsVisible(@Nullable TaskbarView visibleTaskbar) {
@@ -438,13 +457,15 @@
      * Updates the TaskbarContainer to MATCH_PARENT vs original Taskbar size.
      */
     private void setTaskbarWindowFullscreen(boolean fullscreen) {
-        if (fullscreen) {
-            mWindowLayoutParams.width = MATCH_PARENT;
-            mWindowLayoutParams.height = MATCH_PARENT;
-        } else {
-            mWindowLayoutParams.width = mTaskbarSize.x;
-            mWindowLayoutParams.height = mTaskbarSize.y;
-        }
+        setTaskbarWindowHeight(fullscreen ? MATCH_PARENT : mTaskbarSize.y);
+    }
+
+    /**
+     * Updates the TaskbarContainer height (pass mTaskbarSize.y to reset).
+     */
+    private void setTaskbarWindowHeight(int height) {
+        mWindowLayoutParams.width = mTaskbarSize.x;
+        mWindowLayoutParams.height = height;
         mWindowManager.updateViewLayout(mTaskbarContainerView, mWindowLayoutParams);
     }
 
@@ -454,6 +475,7 @@
     protected interface TaskbarStateHandlerCallbacks {
         AnimatedFloat getAlphaTarget();
         AnimatedFloat getScaleTarget();
+        AnimatedFloat getTranslationYTarget();
     }
 
     /**
@@ -464,6 +486,7 @@
         void updateTaskbarBackgroundAlpha(float alpha);
         void updateTaskbarVisibilityAlpha(float alpha);
         void updateTaskbarScale(float scale);
+        void updateTaskbarTranslationY(float translationY);
     }
 
     /**
diff --git a/quickstep/src/com/android/launcher3/taskbar/TaskbarStateHandler.java b/quickstep/src/com/android/launcher3/taskbar/TaskbarStateHandler.java
index 9fc7d99..6ea51fa 100644
--- a/quickstep/src/com/android/launcher3/taskbar/TaskbarStateHandler.java
+++ b/quickstep/src/com/android/launcher3/taskbar/TaskbarStateHandler.java
@@ -16,6 +16,7 @@
 package com.android.launcher3.taskbar;
 
 import static com.android.launcher3.LauncherState.TASKBAR;
+import static com.android.launcher3.anim.Interpolators.ACCEL_DEACCEL;
 import static com.android.launcher3.anim.Interpolators.LINEAR;
 
 import androidx.annotation.Nullable;
@@ -54,9 +55,11 @@
 
         AnimatedFloat alphaTarget = mTaskbarCallbacks.getAlphaTarget();
         AnimatedFloat scaleTarget = mTaskbarCallbacks.getScaleTarget();
+        AnimatedFloat translationYTarget = mTaskbarCallbacks.getTranslationYTarget();
         boolean isTaskbarVisible = (state.getVisibleElements(mLauncher) & TASKBAR) != 0;
         alphaTarget.updateValue(isTaskbarVisible ? 1f : 0f);
         scaleTarget.updateValue(state.getTaskbarScale(mLauncher));
+        translationYTarget.updateValue(state.getTaskbarTranslationY(mLauncher));
     }
 
     @Override
@@ -68,9 +71,12 @@
 
         AnimatedFloat alphaTarget = mTaskbarCallbacks.getAlphaTarget();
         AnimatedFloat scaleTarget = mTaskbarCallbacks.getScaleTarget();
+        AnimatedFloat translationYTarget = mTaskbarCallbacks.getTranslationYTarget();
         boolean isTaskbarVisible = (toState.getVisibleElements(mLauncher) & TASKBAR) != 0;
         animation.setFloat(alphaTarget, AnimatedFloat.VALUE, isTaskbarVisible ? 1f : 0f, LINEAR);
         animation.setFloat(scaleTarget, AnimatedFloat.VALUE, toState.getTaskbarScale(mLauncher),
                 LINEAR);
+        animation.setFloat(translationYTarget, AnimatedFloat.VALUE,
+                toState.getTaskbarTranslationY(mLauncher), ACCEL_DEACCEL);
     }
 }
diff --git a/quickstep/src/com/android/launcher3/taskbar/TaskbarView.java b/quickstep/src/com/android/launcher3/taskbar/TaskbarView.java
index f254844..60a7add 100644
--- a/quickstep/src/com/android/launcher3/taskbar/TaskbarView.java
+++ b/quickstep/src/com/android/launcher3/taskbar/TaskbarView.java
@@ -24,7 +24,6 @@
 import android.graphics.Canvas;
 import android.graphics.Rect;
 import android.graphics.RectF;
-import android.graphics.drawable.ColorDrawable;
 import android.util.AttributeSet;
 import android.view.DragEvent;
 import android.view.MotionEvent;
@@ -52,7 +51,6 @@
  */
 public class TaskbarView extends LinearLayout implements FolderIcon.FolderIconParent, Insettable {
 
-    private final ColorDrawable mBackgroundDrawable;
     private final int mIconTouchSize;
     private final boolean mIsRtl;
     private final int mTouchSlop;
@@ -97,7 +95,6 @@
         super(context, attrs, defStyleAttr, defStyleRes);
 
         Resources resources = getResources();
-        mBackgroundDrawable = (ColorDrawable) getBackground();
         mIconTouchSize = resources.getDimensionPixelSize(R.dimen.taskbar_icon_touch_size);
         mIsRtl = Utilities.isRtl(resources);
         mTouchSlop = ViewConfiguration.get(context).getScaledTouchSlop();
@@ -160,14 +157,6 @@
     }
 
     /**
-     * Sets the alpha of the background color behind all the Taskbar contents.
-     * @param alpha 0 is fully transparent, 1 is fully opaque.
-     */
-    public void setBackgroundAlpha(float alpha) {
-        mBackgroundDrawable.setAlpha((int) (alpha * 255));
-    }
-
-    /**
      * Inflates/binds the Hotseat views to show in the Taskbar given their ItemInfos.
      */
     protected void updateHotseatItems(ItemInfo[] hotseatItemInfos) {
diff --git a/quickstep/src/com/android/launcher3/uioverrides/states/OverviewState.java b/quickstep/src/com/android/launcher3/uioverrides/states/OverviewState.java
index 6cdeb0f..30c07b0 100644
--- a/quickstep/src/com/android/launcher3/uioverrides/states/OverviewState.java
+++ b/quickstep/src/com/android/launcher3/uioverrides/states/OverviewState.java
@@ -88,6 +88,11 @@
     }
 
     @Override
+    public float getTaskbarTranslationY(Launcher launcher) {
+        return 0f;
+    }
+
+    @Override
     public PageAlphaProvider getWorkspacePageAlphaProvider(Launcher launcher) {
         return new PageAlphaProvider(DEACCEL_2) {
             @Override
diff --git a/quickstep/src/com/android/quickstep/AbsSwipeUpHandler.java b/quickstep/src/com/android/quickstep/AbsSwipeUpHandler.java
index 2a903eb..c547d00 100644
--- a/quickstep/src/com/android/quickstep/AbsSwipeUpHandler.java
+++ b/quickstep/src/com/android/quickstep/AbsSwipeUpHandler.java
@@ -801,11 +801,9 @@
             }
         }
         if (mParallelRunningAnim != null) {
-            if (cancel) {
-                mParallelRunningAnim.cancel();
-            } else {
-                mParallelRunningAnim.end();
-            }
+            // Unlike the above animation, the parallel animation won't have anything to take up
+            // the work if it's canceled, so just end it instead.
+            mParallelRunningAnim.end();
         }
     }
 
diff --git a/src/com/android/launcher3/Hotseat.java b/src/com/android/launcher3/Hotseat.java
index da41200..8496fd5 100644
--- a/src/com/android/launcher3/Hotseat.java
+++ b/src/com/android/launcher3/Hotseat.java
@@ -199,25 +199,38 @@
         int left = (r - l - qsbWidth) / 2;
         int right = left + qsbWidth;
 
-        DeviceProfile dp = mActivity.getDeviceProfile();
-        int freeSpace = dp.isTaskbarPresent
-                ? dp.workspacePadding.bottom
-                : dp.hotseatBarSizePx - dp.hotseatCellHeightPx - mQsbHeight;
-        int bottom = b - t
-                - (int) (freeSpace * QSB_CENTER_FACTOR)
-                - (dp.isTaskbarPresent ? dp.taskbarSize : dp.getInsets().bottom);
+        int bottom = b - t - getQsbOffsetY();
         int top = bottom - mQsbHeight;
         mQsb.layout(left, top, right, bottom);
 
         int taskbarWidth = mTaskbarView.getMeasuredWidth();
         left = (r - l - taskbarWidth) / 2;
         right = left + taskbarWidth;
-        bottom = b - t;
+        bottom = b - t - getTaskbarOffsetY();
         top = bottom - mTaskbarViewHeight;
         mTaskbarView.layout(left, top, right, bottom);
     }
 
     /**
+     * Returns the number of pixels the QSB is translated from the bottom of the screen.
+     */
+    private int getQsbOffsetY() {
+        DeviceProfile dp = mActivity.getDeviceProfile();
+        int freeSpace = dp.isTaskbarPresent
+                ? dp.workspacePadding.bottom
+                : dp.hotseatBarSizePx - dp.hotseatCellHeightPx - mQsbHeight;
+        return (int) (freeSpace * QSB_CENTER_FACTOR)
+                + (dp.isTaskbarPresent ? dp.taskbarSize : dp.getInsets().bottom);
+    }
+
+    /**
+     * Returns the number of pixels the taskbar is translated from the bottom of the screen.
+     */
+    public int getTaskbarOffsetY() {
+        return (getQsbOffsetY() - mTaskbarViewHeight) / 2;
+    }
+
+    /**
      * Sets the alpha value of just our ShortcutAndWidgetContainer.
      */
     public void setIconsAlpha(float alpha) {
diff --git a/src/com/android/launcher3/LauncherState.java b/src/com/android/launcher3/LauncherState.java
index 0c509a1..58df9c8 100644
--- a/src/com/android/launcher3/LauncherState.java
+++ b/src/com/android/launcher3/LauncherState.java
@@ -184,6 +184,10 @@
         return launcher.getNormalTaskbarScale();
     }
 
+    public float getTaskbarTranslationY(Launcher launcher) {
+        return -launcher.getHotseat().getTaskbarOffsetY();
+    }
+
     public float getOverviewFullscreenProgress() {
         return 0;
     }