Merge "Fix ExtendedEditText not handling touch correctly b/31555902" into ub-launcher3-calgary-polish
diff --git a/res/layout/user_folder.xml b/res/layout/user_folder.xml
index d950750..50bd896 100644
--- a/res/layout/user_folder.xml
+++ b/res/layout/user_folder.xml
@@ -28,7 +28,7 @@
         android:layout_height="match_parent"
         android:paddingLeft="4dp"
         android:paddingRight="4dp"
-        android:paddingTop="8dp"
+        android:paddingTop="4dp"
         launcher:pageIndicator="@+id/folder_page_indicator" />
 
     <LinearLayout
@@ -37,8 +37,8 @@
         android:layout_height="wrap_content"
         android:clipChildren="false"
         android:orientation="horizontal"
-        android:paddingLeft="8dp"
-        android:paddingRight="8dp" >
+        android:paddingLeft="12dp"
+        android:paddingRight="12dp" >
 
         <com.android.launcher3.ExtendedEditText
             android:id="@+id/folder_name"
@@ -51,13 +51,14 @@
             android:gravity="center_horizontal"
             android:hint="@string/folder_hint_text"
             android:imeOptions="flagNoExtractUi"
-            android:paddingBottom="8dp"
-            android:paddingTop="4dp"
+            android:paddingBottom="@dimen/folder_label_padding"
+            android:paddingTop="@dimen/folder_label_padding"
             android:singleLine="true"
             android:textColor="#ff777777"
+            android:includeFontPadding="false"
             android:textColorHighlight="#ffCCCCCC"
             android:textColorHint="#ff808080"
-            android:textSize="14sp" />
+            android:textSize="@dimen/folder_label_text_size" />
 
         <com.android.launcher3.pageindicators.PageIndicatorDots
             android:id="@+id/folder_page_indicator"
diff --git a/res/layout/user_folder_icon_normalized.xml b/res/layout/user_folder_icon_normalized.xml
index bb6bd76..16e618a 100644
--- a/res/layout/user_folder_icon_normalized.xml
+++ b/res/layout/user_folder_icon_normalized.xml
@@ -26,9 +26,9 @@
         android:id="@+id/folder_content"
         android:layout_width="match_parent"
         android:layout_height="match_parent"
-        android:paddingLeft="8dp"
-        android:paddingRight="8dp"
-        android:paddingTop="8dp"
+        android:paddingLeft="4dp"
+        android:paddingRight="4dp"
+        android:paddingTop="4dp"
         launcher:pageIndicator="@+id/folder_page_indicator" />
 
     <LinearLayout
@@ -37,8 +37,8 @@
         android:layout_height="wrap_content"
         android:clipChildren="false"
         android:orientation="horizontal"
-        android:paddingLeft="8dp"
-        android:paddingRight="8dp" >
+        android:paddingLeft="12dp"
+        android:paddingRight="12dp" >
 
         <com.android.launcher3.ExtendedEditText
             android:id="@+id/folder_name"
@@ -52,13 +52,13 @@
             android:gravity="center_horizontal"
             android:hint="@string/folder_hint_text"
             android:imeOptions="flagNoExtractUi"
-            android:paddingBottom="12dp"
-            android:paddingTop="4dp"
+            android:paddingBottom="@dimen/folder_label_padding"
+            android:paddingTop="@dimen/folder_label_padding"
             android:singleLine="true"
             android:textColor="#EE777777"
             android:textColorHighlight="#ffCCCCCC"
             android:textColorHint="#ff808080"
-            android:textSize="14sp" />
+            android:textSize="@dimen/folder_label_text_size" />
 
         <com.android.launcher3.pageindicators.PageIndicatorDots
             android:id="@+id/folder_page_indicator"
diff --git a/res/layout/widgets_list_row_view.xml b/res/layout/widgets_list_row_view.xml
index 4687b38..30a34d4 100644
--- a/res/layout/widgets_list_row_view.xml
+++ b/res/layout/widgets_list_row_view.xml
@@ -59,8 +59,8 @@
             android:id="@+id/widgets_cell_list"
             android:layout_width="wrap_content"
             android:layout_height="wrap_content"
-            android:layout_marginStart="@dimen/widget_row_padding"
-            android:layout_marginLeft="@dimen/widget_row_padding"
+            android:paddingStart="@dimen/widget_row_padding"
+            android:paddingEnd="0dp"
             android:orientation="horizontal"
             android:divider="@drawable/widgets_row_divider"
             android:showDividers="middle"/>
diff --git a/res/values/attrs.xml b/res/values/attrs.xml
index 3cfaf02..3423835 100644
--- a/res/values/attrs.xml
+++ b/res/values/attrs.xml
@@ -25,7 +25,8 @@
         <attr name="iconDisplay" format="integer">
             <enum name="workspace" value="0" />
             <enum name="all_apps" value="1" />
-            <enum name="widget_section" value="2" />
+            <enum name="folder" value="2" />
+            <enum name="widget_section" value="3" />
         </attr>
         <attr name="deferShadowGeneration" format="boolean" />
         <attr name="customShadows" format="boolean" />
diff --git a/res/values/dimens.xml b/res/values/dimens.xml
index 1ae4685..33466a8 100644
--- a/res/values/dimens.xml
+++ b/res/values/dimens.xml
@@ -137,6 +137,12 @@
     <dimen name="folder_preview_padding">6dp</dimen>
     <dimen name="page_indicator_dot_size">8dp</dimen>
 
+    <dimen name="folder_cell_x_padding">9dp</dimen>
+    <dimen name="folder_cell_y_padding">8dp</dimen>
+    <dimen name="folder_child_text_size">13sp</dimen>
+    <dimen name="folder_label_padding">12dp</dimen>
+    <dimen name="folder_label_text_size">14sp</dimen>
+
 <!-- Sizes for managed profile badges -->
     <dimen name="profile_badge_size">24dp</dimen>
     <dimen name="profile_badge_margin">5dp</dimen>
diff --git a/res/values/strings.xml b/res/values/strings.xml
index d11d5a5..60a37e5 100644
--- a/res/values/strings.xml
+++ b/res/values/strings.xml
@@ -46,6 +46,8 @@
     <!-- The format string for the dimensions of a widget in the drawer -->
     <!-- There is a special version of this format string for Farsi -->
     <string name="widget_dims_format">%1$d \u00d7 %2$d</string>
+    <!-- Accessibility spoken message format for the dimensions of a widget in the drawer -->
+    <string name="widget_accessible_dims_format">%1$d wide by %2$d high</string>
 
     <!-- All Apps -->
     <!-- Search bar text in the apps view. [CHAR_LIMIT=50] -->
diff --git a/res/values/styles.xml b/res/values/styles.xml
index f029765..ecc11b0 100644
--- a/res/values/styles.xml
+++ b/res/values/styles.xml
@@ -74,7 +74,11 @@
         <item name="android:background">@null</item>
         <item name="android:textColor">@color/quantum_panel_text_color</item>
         <item name="android:shadowRadius">0</item>
+        <item name="android:textSize">@dimen/folder_child_text_size</item>
+        <item name="android:gravity">center</item>
+        <item name="android:includeFontPadding">false</item>
         <item name="customShadows">false</item>
+        <item name="iconDisplay">folder</item>
     </style>
 
     <style name="Icon.DeepShortcut">
diff --git a/src/com/android/launcher3/BubbleTextView.java b/src/com/android/launcher3/BubbleTextView.java
index 33b3ad3..a294fa5 100644
--- a/src/com/android/launcher3/BubbleTextView.java
+++ b/src/com/android/launcher3/BubbleTextView.java
@@ -65,6 +65,7 @@
 
     private static final int DISPLAY_WORKSPACE = 0;
     private static final int DISPLAY_ALL_APPS = 1;
+    private static final int DISPLAY_FOLDER = 2;
 
     private final Launcher mLauncher;
     private Drawable mIcon;
@@ -125,12 +126,13 @@
             setTextSize(TypedValue.COMPLEX_UNIT_PX, grid.allAppsIconTextSizePx);
             setCompoundDrawablePadding(grid.allAppsIconDrawablePaddingPx);
             defaultIconSize = grid.allAppsIconSizePx;
+        } else if (display == DISPLAY_FOLDER) {
+            setCompoundDrawablePadding(grid.folderChildDrawablePaddingPx);
         }
         mCenterVertically = a.getBoolean(R.styleable.BubbleTextView_centerVertically, false);
 
         mIconSize = a.getDimensionPixelSize(R.styleable.BubbleTextView_iconSizeOverride,
                 defaultIconSize);
-
         a.recycle();
 
         if (mCustomShadowsEnabled) {
diff --git a/src/com/android/launcher3/DeviceProfile.java b/src/com/android/launcher3/DeviceProfile.java
index c9fd85a..c4e6ed1 100644
--- a/src/com/android/launcher3/DeviceProfile.java
+++ b/src/com/android/launcher3/DeviceProfile.java
@@ -20,8 +20,6 @@
 import android.content.ComponentName;
 import android.content.Context;
 import android.content.res.Resources;
-import android.graphics.Paint;
-import android.graphics.Paint.FontMetrics;
 import android.graphics.Point;
 import android.graphics.Rect;
 import android.util.DisplayMetrics;
@@ -100,6 +98,7 @@
     public int folderIconPreviewPadding;
     public int folderCellWidthPx;
     public int folderCellHeightPx;
+    public int folderChildDrawablePaddingPx;
 
     // Hotseat
     public int hotseatCellWidthPx;
@@ -255,12 +254,9 @@
         allAppsIconDrawablePaddingPx = iconDrawablePaddingPx;
         allAppsIconTextSizePx = iconTextSizePx;
 
-        // Calculate the actual text height
-        Paint textPaint = new Paint();
-        textPaint.setTextSize(iconTextSizePx);
-        FontMetrics fm = textPaint.getFontMetrics();
         cellWidthPx = iconSizePx;
-        cellHeightPx = iconSizePx + iconDrawablePaddingPx + (int) Math.ceil(fm.bottom - fm.top);
+        cellHeightPx = iconSizePx + iconDrawablePaddingPx
+                + Utilities.calculateTextHeight(iconTextSizePx);
         final float scaleDps = !FeatureFlags.LAUNCHER3_LEGACY_WORKSPACE_DND ? 0f
                 : res.getDimensionPixelSize(R.dimen.dragViewScale);
         dragViewScale = (iconSizePx + scaleDps) / iconSizePx;
@@ -281,12 +277,25 @@
                     res.getInteger(R.integer.config_workspaceSpringLoadShrinkPercentage) / 100.0f;
         }
 
-        // Folder
-        int folderCellPadding = isTablet || isLandscape ? 6 * edgeMarginPx : 3 * edgeMarginPx;
+        // Folder cell
+        int cellPaddingX = res.getDimensionPixelSize(R.dimen.folder_cell_x_padding);
+        int cellPaddingY = res.getDimensionPixelSize(R.dimen.folder_cell_y_padding);
+        final int folderChildTextSize =
+                Utilities.calculateTextHeight(res.getDimension(R.dimen.folder_child_text_size));
+
+        final int folderBottomPanelSize =
+                2 * res.getDimensionPixelSize(R.dimen.folder_label_padding)
+                + Utilities.calculateTextHeight(res.getDimension(R.dimen.folder_label_text_size));
+
         // Don't let the folder get too close to the edges of the screen.
-        folderCellWidthPx = Math.min(cellWidthPx + folderCellPadding,
+        folderCellWidthPx = Math.min(iconSizePx + 2 * cellPaddingX,
                 (availableWidthPx - 4 * edgeMarginPx) / inv.numFolderColumns);
-        folderCellHeightPx = cellHeightPx + edgeMarginPx;
+        folderCellHeightPx = Math.min(iconSizePx + 3 * cellPaddingY + folderChildTextSize,
+                (availableHeightPx - 4 * edgeMarginPx - folderBottomPanelSize) / inv.numFolderRows);
+        folderChildDrawablePaddingPx = Math.max(0,
+                (folderCellHeightPx - iconSizePx - folderChildTextSize) / 3);
+
+        // Folder icon
         folderBackgroundOffset = -edgeMarginPx;
         folderIconSizePx = iconSizePx + 2 * -folderBackgroundOffset;
         folderIconPreviewPadding = res.getDimensionPixelSize(R.dimen.folder_preview_padding);
@@ -296,9 +305,6 @@
         mInsets.set(insets);
     }
 
-    /**
-     * @param recyclerViewWidth the available width of the AllAppsRecyclerView
-     */
     public void updateAppsViewNumCols() {
         allAppsNumCols = allAppsNumPredictiveCols = inv.numColumns;
     }
diff --git a/src/com/android/launcher3/Utilities.java b/src/com/android/launcher3/Utilities.java
index e34f509..b0e096a 100644
--- a/src/com/android/launcher3/Utilities.java
+++ b/src/com/android/launcher3/Utilities.java
@@ -686,11 +686,11 @@
     /**
      * Calculates the height of a given string at a specific text size.
      */
-    public static float calculateTextHeight(float textSizePx) {
+    public static int calculateTextHeight(float textSizePx) {
         Paint p = new Paint();
         p.setTextSize(textSizePx);
         Paint.FontMetrics fm = p.getFontMetrics();
-        return -fm.top + fm.bottom;
+        return (int) Math.ceil(fm.bottom - fm.top);
     }
 
     /**
diff --git a/src/com/android/launcher3/allapps/AllAppsSearchBarController.java b/src/com/android/launcher3/allapps/AllAppsSearchBarController.java
index 41abb4c..365ab31 100644
--- a/src/com/android/launcher3/allapps/AllAppsSearchBarController.java
+++ b/src/com/android/launcher3/allapps/AllAppsSearchBarController.java
@@ -127,10 +127,9 @@
 
     @Override
     public boolean onBackKey() {
-        // Only hide the search field if there is no query, or if there
-        // are no filtered results
+        // Only hide the search field if there is no query
         String query = Utilities.trim(mInput.getEditableText().toString());
-        if (query.isEmpty() || mApps.hasNoFilteredResults()) {
+        if (query.isEmpty()) {
             reset();
             return true;
         }
diff --git a/src/com/android/launcher3/shortcuts/DeepShortcutsContainer.java b/src/com/android/launcher3/shortcuts/DeepShortcutsContainer.java
index cfa6efd..7657ed6 100644
--- a/src/com/android/launcher3/shortcuts/DeepShortcutsContainer.java
+++ b/src/com/android/launcher3/shortcuts/DeepShortcutsContainer.java
@@ -52,6 +52,7 @@
 import com.android.launcher3.LauncherAnimUtils;
 import com.android.launcher3.LauncherAppState;
 import com.android.launcher3.LauncherModel;
+import com.android.launcher3.LauncherSettings;
 import com.android.launcher3.LauncherViewPropertyAnimator;
 import com.android.launcher3.R;
 import com.android.launcher3.ShortcutInfo;
@@ -687,7 +688,9 @@
         mDeferContainerRemoval = false;
         // Make the original icon visible in All Apps, but not in Workspace or Folders.
         cleanupDeferredDrag(mDeferredDragIcon.getTag() instanceof AppInfo);
-        mDeferredDragIcon.setTextVisibility(true);
+        boolean isInHotseat = ((ItemInfo) mDeferredDragIcon.getTag()).container
+                == LauncherSettings.Favorites.CONTAINER_HOTSEAT;
+        mDeferredDragIcon.setTextVisibility(!isInHotseat);
         mLauncher.getDragController().removeDragListener(this);
         mLauncher.getDragLayer().removeView(this);
     }
diff --git a/src/com/android/launcher3/widget/WidgetCell.java b/src/com/android/launcher3/widget/WidgetCell.java
index 97877fd..293585d 100644
--- a/src/com/android/launcher3/widget/WidgetCell.java
+++ b/src/com/android/launcher3/widget/WidgetCell.java
@@ -135,6 +135,8 @@
         mWidgetName.setText(mItem.label);
         mWidgetDims.setText(getContext().getString(R.string.widget_dims_format,
                 mItem.spanX, mItem.spanY));
+        mWidgetDims.setContentDescription(getContext().getString(
+                R.string.widget_accessible_dims_format, mItem.spanX, mItem.spanY));
         mWidgetPreviewLoader = loader;
 
         if (item.activityInfo != null) {
diff --git a/src/com/android/launcher3/widget/WidgetsContainerView.java b/src/com/android/launcher3/widget/WidgetsContainerView.java
index 70b2945..89c44c8 100644
--- a/src/com/android/launcher3/widget/WidgetsContainerView.java
+++ b/src/com/android/launcher3/widget/WidgetsContainerView.java
@@ -49,6 +49,7 @@
 import com.android.launcher3.userevent.nano.LauncherLogProto;
 import com.android.launcher3.userevent.nano.LauncherLogProto.Target;
 import com.android.launcher3.util.Thunk;
+import com.android.launcher3.util.TransformingTouchDelegate;
 
 /**
  * The widgets list view container.
@@ -64,11 +65,11 @@
     private IconCache mIconCache;
 
     private final Rect mTmpBgPaddingRect = new Rect();
-    private final Rect mTmpRect = new Rect();
 
     /* Recycler view related member variables */
     private WidgetsRecyclerView mRecyclerView;
     private WidgetsListAdapter mAdapter;
+    private TransformingTouchDelegate mRecyclerViewTouchDelegate;
 
     /* Touch handling related member variables. */
     private Toast mWidgetInstructionToast;
@@ -96,29 +97,29 @@
     }
 
     @Override
+    protected void onLayout(boolean changed, int left, int top, int right, int bottom) {
+        super.onLayout(changed, left, top, right, bottom);
+        getRevealView().getBackground().getPadding(mTmpBgPaddingRect);
+        mRecyclerViewTouchDelegate.setBounds(
+                mRecyclerView.getLeft() - mTmpBgPaddingRect.left,
+                mRecyclerView.getTop() - mTmpBgPaddingRect.top,
+                mRecyclerView.getRight() + mTmpBgPaddingRect.right,
+                mRecyclerView.getBottom() + mTmpBgPaddingRect.bottom);
+    }
+
+    @Override
     protected void onFinishInflate() {
         super.onFinishInflate();
         mRecyclerView = (WidgetsRecyclerView) getContentView().findViewById(R.id.widgets_list_view);
         mRecyclerView.setAdapter(mAdapter);
         mRecyclerView.setLayoutManager(new LinearLayoutManager(getContext()));
+        mRecyclerViewTouchDelegate = new TransformingTouchDelegate(mRecyclerView);
     }
 
     @Override
-    protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
-        getRevealView().getBackground().getPadding(mTmpBgPaddingRect);
-        if (Utilities.isRtl(getResources())) {
-            getContentView().setPadding(0, mTmpBgPaddingRect.top, mTmpBgPaddingRect.right,
-                    mTmpBgPaddingRect.bottom);
-            mTmpRect.set(mTmpBgPaddingRect.left, 0, 0, 0);
-            mRecyclerView.updateBackgroundPadding(mTmpRect);
-        } else {
-            getContentView().setPadding(mTmpBgPaddingRect.left, mTmpBgPaddingRect.top, 0,
-                    mTmpBgPaddingRect.bottom);
-            mTmpRect.set(0, 0, mTmpBgPaddingRect.right, 0);
-            mRecyclerView.updateBackgroundPadding(mTmpRect);
-        }
-
-        super.onMeasure(widthMeasureSpec, heightMeasureSpec);
+    protected void onAttachedToWindow() {
+        super.onAttachedToWindow();
+        ((View) mRecyclerView.getParent()).setTouchDelegate(mRecyclerViewTouchDelegate);
     }
 
     //