resolve merge conflicts of a3c74d10a7 to ub-launcher3-master.

Change-Id: Ibeb2499ac278e4094a2922501cfffad2489e58ed
diff --git a/res/values/dimens.xml b/res/values/dimens.xml
index c30ee1d..90083c0 100644
--- a/res/values/dimens.xml
+++ b/res/values/dimens.xml
@@ -17,11 +17,15 @@
 <resources>
 <!-- Dynamic Grid -->
     <dimen name="dynamic_grid_edge_margin">6dp</dimen>
-    <dimen name="dynamic_grid_search_bar_max_width">500dp</dimen>
-    <dimen name="dynamic_grid_search_bar_height">56dp</dimen>
-    <!-- We want 32dp extra for the tall search bar, but 10dp comes from unwanted padding between
-         the search bar and workspace. -->
-    <dimen name="dynamic_grid_search_bar_height_tall">78dp</dimen>
+    <dimen name="dynamic_grid_search_bar_height">48dp</dimen>
+    <!-- We want 32dp extra for the tall search bar. -->
+    <dimen name="dynamic_grid_search_bar_height_tall">80dp</dimen>
+    <dimen name="qsb_internal_padding_top">8dp</dimen>
+    <dimen name="qsb_internal_padding_bottom">8dp</dimen>
+    <dimen name="dynamic_grid_search_bar_bottom_padding">4dp</dimen>
+    <!-- Reduce the padding between the search bar and workspace when the search bar is tall -->
+    <dimen name="dynamic_grid_search_bar_bottom_padding_short">-6dp</dimen>
+    <dimen name="dynamic_grid_search_bar_bottom_padding_tablet">16dp</dimen>
     <dimen name="dynamic_grid_page_indicator_height">20dp</dimen>
     <dimen name="dynamic_grid_icon_drawable_padding">4dp</dimen>
     <dimen name="dynamic_grid_workspace_page_spacing">8dp</dimen>
diff --git a/src/com/android/launcher3/DeviceProfile.java b/src/com/android/launcher3/DeviceProfile.java
index feb5f92..906e729 100644
--- a/src/com/android/launcher3/DeviceProfile.java
+++ b/src/com/android/launcher3/DeviceProfile.java
@@ -90,7 +90,7 @@
     public int hotseatCellWidthPx;
     public int hotseatCellHeightPx;
     public int hotseatIconSizePx;
-    private int hotseatBarHeightNormalPx, hotseatBarHeightShortPx;
+    private int normalHotseatBarHeightPx, shortHotseatBarHeightPx;
     private int hotseatBarHeightPx; // One of the above.
 
     // All apps
@@ -101,8 +101,11 @@
     public final int allAppsIconTextSizePx;
 
     // QSB
-    private int searchBarSpaceWidthPx;
-    private int searchBarSpaceHeightNormalPx, searchBarSpaceHeightTallPx;
+    private int searchBarWidgetInternalPaddingTop, searchBarWidgetInternalPaddingBottom;
+    private int searchBarTopPaddingPx;
+    private int normalSearchBarBottomPaddingPx, tallSearchBarBottomPaddingPx;
+    private int searchBarBottomPaddingPx; // One of the above.
+    private int normalSearchBarSpaceHeightPx, tallSearchBarSpaceHeightPx;
     private int searchBarSpaceHeightPx; // One of the above.
 
     public DeviceProfile(Context context, InvariantDeviceProfile inv,
@@ -205,12 +208,26 @@
         hotseatIconSizePx = (int) (Utilities.pxFromDp(inv.hotseatIconSize, dm) * scale);
 
         // Search Bar
-        searchBarSpaceWidthPx = Math.min(widthPx,
-                res.getDimensionPixelSize(R.dimen.dynamic_grid_search_bar_max_width));
-        searchBarSpaceHeightNormalPx = getSearchBarTopOffset()
-                + res.getDimensionPixelSize(R.dimen.dynamic_grid_search_bar_height);
-        searchBarSpaceHeightTallPx = getSearchBarTopOffset()
-                + res.getDimensionPixelSize(R.dimen.dynamic_grid_search_bar_height_tall);
+        normalSearchBarSpaceHeightPx = res.getDimensionPixelSize(
+                R.dimen.dynamic_grid_search_bar_height);
+        tallSearchBarSpaceHeightPx = res.getDimensionPixelSize(
+                R.dimen.dynamic_grid_search_bar_height_tall);
+        searchBarWidgetInternalPaddingTop = res.getDimensionPixelSize(
+                R.dimen.qsb_internal_padding_top);
+        searchBarWidgetInternalPaddingBottom = res.getDimensionPixelSize(
+                R.dimen.qsb_internal_padding_bottom);
+        if (isTablet && !isVerticalBarLayout()) {
+            searchBarTopPaddingPx = searchBarWidgetInternalPaddingTop;
+            normalSearchBarBottomPaddingPx = searchBarWidgetInternalPaddingBottom +
+                    res.getDimensionPixelSize(R.dimen.dynamic_grid_search_bar_bottom_padding_tablet);
+            tallSearchBarBottomPaddingPx = normalSearchBarBottomPaddingPx;
+        } else {
+            searchBarTopPaddingPx = searchBarWidgetInternalPaddingTop;
+            normalSearchBarBottomPaddingPx = searchBarWidgetInternalPaddingBottom +
+                    res.getDimensionPixelSize(R.dimen.dynamic_grid_search_bar_bottom_padding);
+            tallSearchBarBottomPaddingPx = searchBarWidgetInternalPaddingBottom +
+                    res.getDimensionPixelSize(R.dimen.dynamic_grid_search_bar_bottom_padding_short);
+        }
 
         // Calculate the actual text height
         Paint textPaint = new Paint();
@@ -222,8 +239,8 @@
         dragViewScale = (iconSizePx + scaleDps) / iconSizePx;
 
         // Hotseat
-        hotseatBarHeightNormalPx = iconSizePx + 4 * edgeMarginPx;
-        hotseatBarHeightShortPx = iconSizePx + 2 * edgeMarginPx;
+        normalHotseatBarHeightPx = iconSizePx + 4 * edgeMarginPx;
+        shortHotseatBarHeightPx = iconSizePx + 2 * edgeMarginPx;
         hotseatCellWidthPx = iconSizePx;
         hotseatCellHeightPx = iconSizePx;
 
@@ -251,13 +268,20 @@
         allAppsNumPredictiveCols = numPredictiveAppCols;
     }
 
-    /** Returns the search bar top offset */
-    private int getSearchBarTopOffset() {
-        if (isTablet && !isVerticalBarLayout()) {
-            return 4 * edgeMarginPx;
-        } else {
-            return 2 * edgeMarginPx;
+    /** Returns the amount of extra space to allocate to the search bar for vertical padding. */
+    private int getSearchBarTotalVerticalPadding() {
+        return searchBarTopPaddingPx + searchBarBottomPaddingPx;
+    }
+
+    /** Returns the width and height of the search bar, ignoring any padding. */
+    public Point getSearchBarDimensForWidgetOpts(Resources res) {
+        Rect searchBarBounds = getSearchBarBounds(Utilities.isRtl(res));
+        if (isVerticalBarLayout()) {
+            return new Point(searchBarBounds.width(), searchBarBounds.height());
         }
+        int widgetInternalPadding = searchBarWidgetInternalPaddingTop +
+                searchBarWidgetInternalPaddingBottom;
+        return new Point(searchBarBounds.width(), searchBarSpaceHeightPx + widgetInternalPadding);
     }
 
     /** Returns the search bar bounds in the current orientation */
@@ -265,13 +289,14 @@
         Rect bounds = new Rect();
         if (isVerticalBarLayout()) {
             if (isLayoutRtl) {
-                bounds.set(availableWidthPx - searchBarSpaceHeightNormalPx, edgeMarginPx,
+                bounds.set(availableWidthPx - normalSearchBarSpaceHeightPx, edgeMarginPx,
                         availableWidthPx, availableHeightPx - edgeMarginPx);
             } else {
-                bounds.set(0, edgeMarginPx, searchBarSpaceHeightNormalPx,
+                bounds.set(0, edgeMarginPx, normalSearchBarSpaceHeightPx,
                         availableHeightPx - edgeMarginPx);
             }
         } else {
+            int boundsBottom = searchBarSpaceHeightPx + getSearchBarTotalVerticalPadding();
             if (isTablet) {
                 // Pad the left and right of the workspace to ensure consistent spacing
                 // between all icons
@@ -280,14 +305,13 @@
                 //      that into account here too.
                 int gap = (int) ((width - 2 * edgeMarginPx -
                         (inv.numColumns * cellWidthPx)) / (2 * (inv.numColumns + 1)));
-                bounds.set(edgeMarginPx + gap, getSearchBarTopOffset(),
-                        availableWidthPx - (edgeMarginPx + gap),
-                        searchBarSpaceHeightPx);
+                bounds.set(edgeMarginPx + gap, 0,
+                        availableWidthPx - (edgeMarginPx + gap), boundsBottom);
             } else {
                 bounds.set(desiredWorkspaceLeftRightMarginPx - defaultWidgetPadding.left,
-                        getSearchBarTopOffset(),
+                        0,
                         availableWidthPx - (desiredWorkspaceLeftRightMarginPx -
-                        defaultWidgetPadding.right), searchBarSpaceHeightPx);
+                        defaultWidgetPadding.right), boundsBottom);
             }
         }
         return bounds;
@@ -312,21 +336,21 @@
         if (isVerticalBarLayout()) {
             // Pad the left and right of the workspace with search/hotseat bar sizes
             if (isLayoutRtl) {
-                padding.set(hotseatBarHeightNormalPx, edgeMarginPx,
+                padding.set(normalHotseatBarHeightPx, edgeMarginPx,
                         searchBarBounds.width(), edgeMarginPx);
             } else {
                 padding.set(searchBarBounds.width(), edgeMarginPx,
-                        hotseatBarHeightNormalPx, edgeMarginPx);
+                        normalHotseatBarHeightPx, edgeMarginPx);
             }
         } else {
+            int paddingTop = searchBarBounds.bottom;
+            int paddingBottom = hotseatBarHeightPx + pageIndicatorHeightPx;
             if (isTablet) {
                 // Pad the left and right of the workspace to ensure consistent spacing
                 // between all icons
                 float gapScale = 1f + (dragViewScale - 1f) / 2f;
                 int width = getCurrentWidth();
                 int height = getCurrentHeight();
-                int paddingTop = searchBarBounds.bottom;
-                int paddingBottom = hotseatBarHeightPx + pageIndicatorHeightPx;
                 // The amount of screen space available for left/right padding.
                 int availablePaddingX = Math.max(0, width - (int) ((inv.numColumns * cellWidthPx) +
                         ((inv.numColumns - 1) * gapScale * cellWidthPx)));
@@ -339,9 +363,9 @@
             } else {
                 // Pad the top and bottom of the workspace with search/hotseat bar sizes
                 padding.set(desiredWorkspaceLeftRightMarginPx - defaultWidgetPadding.left,
-                        searchBarBounds.bottom,
+                        paddingTop,
                         desiredWorkspaceLeftRightMarginPx - defaultWidgetPadding.right,
-                        hotseatBarHeightPx + pageIndicatorHeightPx);
+                        paddingBottom);
             }
         }
         return padding;
@@ -410,11 +434,13 @@
     // TODO(twickham): b/25154513
     public void setSearchBarHeight(int searchBarHeight) {
         if (searchBarHeight == LauncherCallbacks.SEARCH_BAR_HEIGHT_TALL) {
-            hotseatBarHeightPx = hotseatBarHeightShortPx;
-            searchBarSpaceHeightPx = searchBarSpaceHeightTallPx;
+            hotseatBarHeightPx = shortHotseatBarHeightPx;
+            searchBarSpaceHeightPx = tallSearchBarSpaceHeightPx;
+            searchBarBottomPaddingPx = tallSearchBarBottomPaddingPx;
         } else {
-            hotseatBarHeightPx = hotseatBarHeightNormalPx;
-            searchBarSpaceHeightPx = searchBarSpaceHeightNormalPx;
+            hotseatBarHeightPx = normalHotseatBarHeightPx;
+            searchBarSpaceHeightPx = normalSearchBarSpaceHeightPx;
+            searchBarBottomPaddingPx = normalSearchBarBottomPaddingPx;
         }
     }
 
@@ -424,8 +450,11 @@
         final boolean isLayoutRtl = Utilities.isRtl(launcher.getResources());
 
         // Layout the search bar space
+        Rect searchBarBounds = getSearchBarBounds(isLayoutRtl);
         View searchBar = launcher.getSearchDropTargetBar();
         lp = getDropTargetBarLayoutParams(hasVerticalBarLayout, searchBar, Gravity.TOP);
+        lp.width = searchBarBounds.width();
+        lp.height = searchBarBounds.height();
         searchBar.setLayoutParams(lp);
 
         // Layout the app info bar space
@@ -457,7 +486,7 @@
             // Vertical hotseat -- The hotseat is fixed in the layout to be on the right of the
             //                     screen regardless of RTL
             lp.gravity = Gravity.RIGHT;
-            lp.width = hotseatBarHeightNormalPx;
+            lp.width = normalHotseatBarHeightPx;
             lp.height = LayoutParams.MATCH_PARENT;
             hotseat.findViewById(R.id.layout).setPadding(0, 2 * edgeMarginPx, 0, 2 * edgeMarginPx);
         } else if (isTablet) {
@@ -544,7 +573,7 @@
             // Vertical drop target bar space -- The drop target bar is fixed in the layout to be on
             //                                   the left of the screen regardless of RTL
             lp.gravity = Gravity.LEFT;
-            lp.width = searchBarSpaceHeightNormalPx;
+            lp.width = normalSearchBarSpaceHeightPx;
 
             LinearLayout targets = (LinearLayout) dropTargetBar.findViewById(R.id.drag_target_bar);
             targets.setOrientation(LinearLayout.VERTICAL);
@@ -555,9 +584,6 @@
             // Horizontal drop target bar space
             lp.gravity = verticalGravity;
             lp.height = searchBarSpaceHeightPx;
-
-            LinearLayout targets = (LinearLayout) dropTargetBar.findViewById(R.id.drag_target_bar);
-            targets.getLayoutParams().width = searchBarSpaceWidthPx;
         }
         return lp;
     }
diff --git a/src/com/android/launcher3/Launcher.java b/src/com/android/launcher3/Launcher.java
index 19bdea0..cca0e36 100644
--- a/src/com/android/launcher3/Launcher.java
+++ b/src/com/android/launcher3/Launcher.java
@@ -52,6 +52,7 @@
 import android.graphics.Bitmap;
 import android.graphics.Canvas;
 import android.graphics.Color;
+import android.graphics.Point;
 import android.graphics.PorterDuff;
 import android.graphics.Rect;
 import android.graphics.drawable.ColorDrawable;
@@ -3589,17 +3590,17 @@
             DeviceProfile portraitProfile = app.getInvariantDeviceProfile().portraitProfile;
             DeviceProfile landscapeProfile = app.getInvariantDeviceProfile().landscapeProfile;
             float density = getResources().getDisplayMetrics().density;
-            Rect searchBounds = portraitProfile.getSearchBarBounds(Utilities.isRtl(getResources()));
-            int maxHeight = (int) (searchBounds.height() / density);
+            Point searchDimens = portraitProfile.getSearchBarDimensForWidgetOpts(getResources());
+            int maxHeight = (int) (searchDimens.y / density);
             int minHeight = maxHeight;
-            int maxWidth = (int) (searchBounds.width() / density);
+            int maxWidth = (int) (searchDimens.x / density);
             int minWidth = maxWidth;
             if (!landscapeProfile.isVerticalBarLayout()) {
-                searchBounds = landscapeProfile.getSearchBarBounds(Utilities.isRtl(getResources()));
-                maxHeight = (int) Math.max(maxHeight, searchBounds.height() / density);
-                minHeight = (int) Math.min(minHeight, searchBounds.height() / density);
-                maxWidth = (int) Math.max(maxWidth, searchBounds.width() / density);
-                minWidth = (int) Math.min(minWidth, searchBounds.width() / density);
+                searchDimens = landscapeProfile.getSearchBarDimensForWidgetOpts(getResources());
+                maxHeight = (int) Math.max(maxHeight, searchDimens.y / density);
+                minHeight = (int) Math.min(minHeight, searchDimens.y / density);
+                maxWidth = (int) Math.max(maxWidth, searchDimens.x / density);
+                minWidth = (int) Math.min(minWidth, searchDimens.x / density);
             }
             opts.putInt(AppWidgetManager.OPTION_APPWIDGET_MAX_HEIGHT, maxHeight);
             opts.putInt(AppWidgetManager.OPTION_APPWIDGET_MIN_HEIGHT, minHeight);
diff --git a/tests/src/com/android/launcher3/InvariantDeviceProfileTest.java b/tests/src/com/android/launcher3/InvariantDeviceProfileTest.java
index a99ae4f..db3f72f 100644
--- a/tests/src/com/android/launcher3/InvariantDeviceProfileTest.java
+++ b/tests/src/com/android/launcher3/InvariantDeviceProfileTest.java
@@ -15,15 +15,14 @@
  */
 package com.android.launcher3;
 
+import android.content.res.Resources;
+import android.graphics.Point;
 import android.graphics.PointF;
+import android.graphics.Rect;
 import android.test.AndroidTestCase;
 import android.test.suitebuilder.annotation.SmallTest;
 import android.util.Log;
 
-import com.android.launcher3.DeviceProfile;
-import com.android.launcher3.InvariantDeviceProfile;
-import com.android.launcher3.util.FocusLogic;
-
 import java.util.ArrayList;
 
 /**
@@ -123,4 +122,72 @@
     // Add more tests for other devices, however, running them once on a single device is enough
     // for verifying that for a platform version, the WindowManager and DisplayMetrics is
     // working as intended.
+
+    /**
+     * Make sure that the height for the QSB is what we expect in normal mode.
+     */
+    public void testQsbNormalHeight() {
+        Resources resources = getContext().getResources();
+        DeviceProfile landscapeProfile = mInvariantProfile.landscapeProfile;
+        DeviceProfile portraitProfile = mInvariantProfile.portraitProfile;
+        landscapeProfile.setSearchBarHeight(LauncherCallbacks.SEARCH_BAR_HEIGHT_NORMAL);
+        portraitProfile.setSearchBarHeight(LauncherCallbacks.SEARCH_BAR_HEIGHT_NORMAL);
+        Rect portraitBounds = portraitProfile.getSearchBarBounds(true); // RTL shouldn't matter.
+        int portraitHeight = (int) Utilities.dpiFromPx(portraitBounds.height(),
+                resources.getDisplayMetrics());
+        Rect landscapeBounds = landscapeProfile.getSearchBarBounds(true); // RTL shouldn't matter.
+        int landscapeHeight = (int) Utilities.dpiFromPx(landscapeBounds.height(),
+                resources.getDisplayMetrics());
+        if (portraitProfile.isTablet) {
+            assertEquals(8 + 48 + 24, portraitHeight);
+        } else {
+            assertEquals(8 + 48 + 12, portraitHeight);
+        }
+        // Make sure the height that we pass in the widget options bundle is the height of the
+        // search bar + 8dps padding top and bottom.
+        Point portraitDimens = portraitProfile.getSearchBarDimensForWidgetOpts(resources);
+        int portraitWidgetOptsHeight = portraitDimens.y;
+        Point landscapeDimens = landscapeProfile.getSearchBarDimensForWidgetOpts(resources);
+        int landscapeWidgetOptsHeight = landscapeDimens.y;
+        assertEquals(8 + 48 + 8, (int) Utilities.dpiFromPx(portraitWidgetOptsHeight,
+                resources.getDisplayMetrics()));
+        if (!landscapeProfile.isVerticalBarLayout()) {
+            assertEquals(portraitHeight, landscapeHeight);
+            assertEquals(portraitWidgetOptsHeight, landscapeWidgetOptsHeight);
+        }
+    }
+
+    /**
+     * Make sure that the height for the QSB is what we expect in tall mode.
+     */
+    public void testQsbTallHeight() {
+        Resources resources = getContext().getResources();
+        DeviceProfile landscapeProfile = mInvariantProfile.landscapeProfile;
+        DeviceProfile portraitProfile = mInvariantProfile.portraitProfile;
+        landscapeProfile.setSearchBarHeight(LauncherCallbacks.SEARCH_BAR_HEIGHT_TALL);
+        portraitProfile.setSearchBarHeight(LauncherCallbacks.SEARCH_BAR_HEIGHT_TALL);
+        Rect portraitBounds = portraitProfile.getSearchBarBounds(true); // RTL shouldn't matter.
+        int portraitHeight = (int) Utilities.dpiFromPx(portraitBounds.height(),
+                resources.getDisplayMetrics());
+        Rect landscapeBounds = landscapeProfile.getSearchBarBounds(true); // RTL shouldn't matter.
+        int landscapeHeight = (int) Utilities.dpiFromPx(landscapeBounds.height(),
+                resources.getDisplayMetrics());
+        if (portraitProfile.isTablet) {
+            assertEquals(8 + 80 + 24, portraitHeight);
+        } else {
+            assertEquals(8 + 80 + 2, portraitHeight);
+        }
+        // Make sure the height that we pass in the widget options bundle is the height of the
+        // search bar + 8dps padding top and bottom.
+        Point portraitDimens = portraitProfile.getSearchBarDimensForWidgetOpts(resources);
+        int portraitWidgetOptsHeight = portraitDimens.y;
+        Point landscapeDimens = landscapeProfile.getSearchBarDimensForWidgetOpts(resources);
+        int landscapeWidgetOptsHeight = landscapeDimens.y;
+        assertEquals(8 + 80 + 8, (int) Utilities.dpiFromPx(portraitWidgetOptsHeight,
+                resources.getDisplayMetrics()));
+        if (!landscapeProfile.isVerticalBarLayout()) {
+            assertEquals(portraitHeight, landscapeHeight);
+            assertEquals(portraitWidgetOptsHeight, landscapeWidgetOptsHeight);
+        }
+    }
 }