Merge "Optimizing open shortcuts container lookep" into ub-launcher3-calgary
diff --git a/protos/launcher_log.proto b/protos/launcher_log.proto
index eae02ca..3730555 100644
--- a/protos/launcher_log.proto
+++ b/protos/launcher_log.proto
@@ -61,6 +61,7 @@
SHORTCUT = 2;
WIDGET = 3;
FOLDER_ICON = 4;
+ DEEPSHORTCUT = 5;
}
// Used to define what type of container a Target would represent.
@@ -74,6 +75,7 @@
OVERVIEW = 6;
PREDICTION = 7;
SEARCHRESULT = 8;
+ DEEPSHORTCUTS = 9;
}
// Used to define what type of control a Target would represent.
@@ -106,8 +108,16 @@
FLING = 4;
PINCH = 5;
}
+ enum Direction {
+ NONE = 0;
+ UP = 1;
+ DOWN = 2;
+ LEFT = 3;
+ RIGHT = 4;
+ }
optional Type type = 1;
optional Touch touch = 2;
+ optional Direction dir = 3;
}
//
@@ -126,4 +136,4 @@
optional int64 action_duration_millis = 4;
optional int64 elapsed_container_millis = 5;
optional int64 elapsed_session_millis = 6;
-}
\ No newline at end of file
+}
diff --git a/res/drawable/bg_white_pill.xml b/res/drawable/bg_white_pill.xml
index 186b06b..f92f739 100644
--- a/res/drawable/bg_white_pill.xml
+++ b/res/drawable/bg_white_pill.xml
@@ -16,6 +16,6 @@
<shape xmlns:android="http://schemas.android.com/apk/res/android"
android:shape="rectangle">
- <solid android:color="@color/quantum_panel_bg_color" />
+ <solid android:color="#FFFFFF" />
<corners android:radius="@dimen/bg_pill_radius" />
</shape>
\ No newline at end of file
diff --git a/res/drawable/deep_shortcuts_drag_handle.xml b/res/drawable/deep_shortcuts_drag_handle.xml
new file mode 100644
index 0000000..d5fca2e
--- /dev/null
+++ b/res/drawable/deep_shortcuts_drag_handle.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2016 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.
+-->
+
+<vector xmlns:android="http://schemas.android.com/apk/res/android"
+ android:width="24dp"
+ android:height="24dp"
+ android:viewportWidth="24.0"
+ android:viewportHeight="24.0">
+
+ <path
+ android:pathData="M20 9H4v2h16V9zM4 15h16v-2H4v2z"
+ android:fillColor="#757575"/>
+</vector>
\ No newline at end of file
diff --git a/res/layout/all_apps_search_market.xml b/res/layout/all_apps_search_market.xml
index 0199212..3f19b25 100644
--- a/res/layout/all_apps_search_market.xml
+++ b/res/layout/all_apps_search_market.xml
@@ -18,7 +18,7 @@
android:id="@+id/search_market_text"
android:layout_width="match_parent"
android:layout_height="48dp"
- android:gravity="start|center_vertical"
+ android:gravity="center"
android:paddingLeft="@dimen/container_fastscroll_thumb_max_width"
android:paddingRight="@dimen/container_fastscroll_thumb_max_width"
android:fontFamily="sans-serif-medium"
diff --git a/res/layout/deep_shortcut.xml b/res/layout/deep_shortcut.xml
index 0895460..4fcbbd2 100644
--- a/res/layout/deep_shortcut.xml
+++ b/res/layout/deep_shortcut.xml
@@ -21,7 +21,7 @@
android:elevation="@dimen/deep_shortcuts_elevation"
android:background="@drawable/bg_white_pill">
- <com.android.launcher3.BubbleTextView
+ <com.android.launcher3.shortcuts.DeepShortcutTextView
android:id="@+id/deep_shortcut"
style="@style/Icon.DeepShortcut"
android:focusable="true"/>
diff --git a/res/values/dimens.xml b/res/values/dimens.xml
index 54b3d09..6897269 100644
--- a/res/values/dimens.xml
+++ b/res/values/dimens.xml
@@ -28,7 +28,7 @@
<dimen name="dynamic_grid_overview_bar_item_width">80dp</dimen>
<dimen name="dynamic_grid_overview_bar_spacer_width">25dp</dimen>
<dimen name="dynamic_grid_hotseat_height">88dp</dimen>
- <dimen name="dynamic_grid_hotseat_top_padding">12dp</dimen>
+ <dimen name="dynamic_grid_hotseat_top_padding">8dp</dimen>
<dimen name="dynamic_grid_hotseat_gutter_width">24dp</dimen>
<dimen name="dynamic_grid_workspace_top_padding">12dp</dimen>
<dimen name="dynamic_grid_workspace_page_spacing">8dp</dimen>
diff --git a/res/values/styles.xml b/res/values/styles.xml
index 532b701..627c433 100644
--- a/res/values/styles.xml
+++ b/res/values/styles.xml
@@ -81,7 +81,8 @@
<item name="android:gravity">start|center_vertical</item>
<item name="android:elevation">@dimen/deep_shortcuts_elevation</item>
<item name="android:paddingLeft">7dp</item>
- <item name="android:drawablePadding">12dp</item>
+ <item name="android:paddingRight">12dp</item>
+ <item name="android:drawablePadding">9dp</item>
<item name="android:textColor">@color/quantum_panel_text_color</item>
<item name="android:shadowRadius">0</item>
<item name="customShadows">false</item>
diff --git a/src/com/android/launcher3/BubbleTextView.java b/src/com/android/launcher3/BubbleTextView.java
index 00ec4c2..c0c6673 100644
--- a/src/com/android/launcher3/BubbleTextView.java
+++ b/src/com/android/launcher3/BubbleTextView.java
@@ -526,19 +526,23 @@
* Sets the icon for this view based on the layout direction.
*/
@TargetApi(Build.VERSION_CODES.JELLY_BEAN_MR1)
- public void setIcon(Drawable icon) {
+ private void setIcon(Drawable icon) {
mIcon = icon;
if (mIconSize != -1) {
mIcon.setBounds(0, 0, mIconSize, mIconSize);
}
+ applyCompoundDrawables(mIcon);
+ }
+
+ protected void applyCompoundDrawables(Drawable icon) {
if (mLayoutHorizontal) {
if (Utilities.ATLEAST_JB_MR1) {
- setCompoundDrawablesRelative(mIcon, null, null, null);
+ setCompoundDrawablesRelative(icon, null, null, null);
} else {
- setCompoundDrawables(mIcon, null, null, null);
+ setCompoundDrawables(icon, null, null, null);
}
} else {
- setCompoundDrawables(null, mIcon, null, null);
+ setCompoundDrawables(null, icon, null, null);
}
}
diff --git a/src/com/android/launcher3/CellLayout.java b/src/com/android/launcher3/CellLayout.java
index 9030dae..77f6612 100644
--- a/src/com/android/launcher3/CellLayout.java
+++ b/src/com/android/launcher3/CellLayout.java
@@ -406,7 +406,8 @@
mTouchFeedbackView.animate().cancel();
} else {
if (mTouchFeedbackView.setBitmap(background)) {
- mTouchFeedbackView.alignWithIconView(icon, mShortcutsAndWidgets);
+ mTouchFeedbackView.alignWithIconView(icon, mShortcutsAndWidgets,
+ null /* clipAgainstView */);
mTouchFeedbackView.animateShadow();
}
}
diff --git a/src/com/android/launcher3/ClickShadowView.java b/src/com/android/launcher3/ClickShadowView.java
index e2bc6ba..aad1112 100644
--- a/src/com/android/launcher3/ClickShadowView.java
+++ b/src/com/android/launcher3/ClickShadowView.java
@@ -21,6 +21,7 @@
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
+import android.graphics.Rect;
import android.view.View;
import android.view.ViewDebug;
import android.view.ViewGroup;
@@ -91,13 +92,27 @@
* Aligns the shadow with {@param view}
* @param viewParent immediate parent of {@param view}. It must be a sibling of this view.
*/
- public void alignWithIconView(BubbleTextView view, ViewGroup viewParent) {
+ public void alignWithIconView(BubbleTextView view, ViewGroup viewParent, View clipAgainstView) {
float leftShift = view.getLeft() + viewParent.getLeft() - getLeft();
float topShift = view.getTop() + viewParent.getTop() - getTop();
int iconWidth = view.getRight() - view.getLeft();
+ int iconHeight = view.getBottom() - view.getTop();
int iconHSpace = iconWidth - view.getCompoundPaddingRight() - view.getCompoundPaddingLeft();
float drawableWidth = view.getIcon().getBounds().width();
+ if (clipAgainstView != null) {
+ // Set the bounds to clip against
+ int[] coords = new int[] {0, 0};
+ Utilities.getDescendantCoordRelativeToAncestor(clipAgainstView, (View) getParent(),
+ coords, false);
+ int clipLeft = (int) Math.max(0, coords[0] - leftShift - mShadowPadding);
+ int clipTop = (int) Math.max(0, coords[1] - topShift - mShadowPadding) ;
+ setClipBounds(new Rect(clipLeft, clipTop, clipLeft + iconWidth, clipTop + iconHeight));
+ } else {
+ // Reset the clip bounds
+ setClipBounds(null);
+ }
+
setTranslationX(leftShift
+ viewParent.getTranslationX()
+ view.getCompoundPaddingLeft() * view.getScaleX()
diff --git a/src/com/android/launcher3/DeviceProfile.java b/src/com/android/launcher3/DeviceProfile.java
index 5828dfc..c9d5cff 100644
--- a/src/com/android/launcher3/DeviceProfile.java
+++ b/src/com/android/launcher3/DeviceProfile.java
@@ -460,7 +460,7 @@
qsbContainer.setLayoutParams(lp);
// Layout the hotseat
- View hotseat = launcher.findViewById(R.id.hotseat);
+ Hotseat hotseat = (Hotseat) launcher.findViewById(R.id.hotseat);
lp = (FrameLayout.LayoutParams) hotseat.getLayoutParams();
// We want the edges of the hotseat to line up with the edges of the workspace, but the
// icons in the hotseat are a different size, and so don't line up perfectly. To account for
@@ -475,27 +475,25 @@
lp.gravity = Gravity.RIGHT;
lp.width = hotseatBarHeightPx + mInsets.left + mInsets.right;
lp.height = LayoutParams.MATCH_PARENT;
- hotseat.findViewById(R.id.layout).setPadding(0, 2 * edgeMarginPx, 0, 2 * edgeMarginPx);
- hotseat.setPadding(mInsets.left, 0, mInsets.right, 0);
+ hotseat.getLayout().setPadding(mInsets.left, mInsets.top, mInsets.right,
+ workspacePadding.bottom);
} else if (isTablet) {
// Pad the hotseat with the workspace padding calculated above
lp.gravity = Gravity.BOTTOM;
lp.width = LayoutParams.MATCH_PARENT;
lp.height = hotseatBarHeightPx + mInsets.bottom;
- hotseat.findViewById(R.id.layout).setPadding(
- hotseatAdjustment + workspacePadding.left, 0,
- hotseatAdjustment + workspacePadding.right, 2 * edgeMarginPx);
- hotseat.setPadding(0, hotseatBarTopPaddingPx, 0, mInsets.bottom);
+ hotseat.getLayout().setPadding(hotseatAdjustment + workspacePadding.left,
+ hotseatBarTopPaddingPx, hotseatAdjustment + workspacePadding.right,
+ mInsets.bottom);
} else {
// For phones, layout the hotseat without any bottom margin
// to ensure that we have space for the folders
lp.gravity = Gravity.BOTTOM;
lp.width = LayoutParams.MATCH_PARENT;
lp.height = hotseatBarHeightPx + mInsets.bottom;
- hotseat.findViewById(R.id.layout).setPadding(
- hotseatAdjustment + workspacePadding.left, 0,
- hotseatAdjustment + workspacePadding.right, 0);
- hotseat.setPadding(0, hotseatBarTopPaddingPx, 0, mInsets.bottom);
+ hotseat.getLayout().setPadding(hotseatAdjustment + workspacePadding.left,
+ hotseatBarTopPaddingPx, hotseatAdjustment + workspacePadding.right,
+ mInsets.bottom);
}
hotseat.setLayoutParams(lp);
diff --git a/src/com/android/launcher3/Launcher.java b/src/com/android/launcher3/Launcher.java
index 0571787..f8b7c27 100644
--- a/src/com/android/launcher3/Launcher.java
+++ b/src/com/android/launcher3/Launcher.java
@@ -117,6 +117,7 @@
import com.android.launcher3.pageindicators.PageIndicator;
import com.android.launcher3.shortcuts.DeepShortcutManager;
import com.android.launcher3.shortcuts.DeepShortcutsContainer;
+import com.android.launcher3.userevent.nano.LauncherLogProto;
import com.android.launcher3.util.ComponentKey;
import com.android.launcher3.util.MultiHashMap;
import com.android.launcher3.util.PackageManagerHelper;
@@ -2590,6 +2591,8 @@
protected void onClickAllAppsButton(View v) {
if (LOGD) Log.d(TAG, "onClickAllAppsButton");
if (!isAppsViewVisible()) {
+ mUserEventDispatcher.logActionOnControl(LauncherLogProto.Action.TAP,
+ LauncherLogProto.ALL_APPS_BUTTON);
showAppsView(true /* animated */, false /* resetListToTop */,
true /* updatePredictedApps */, false /* focusSearchBar */);
}
@@ -2598,6 +2601,8 @@
protected void onLongClickAllAppsButton(View v) {
if (LOGD) Log.d(TAG, "onLongClickAllAppsButton");
if (!isAppsViewVisible()) {
+ mUserEventDispatcher.logActionOnControl(LauncherLogProto.Action.LONGPRESS,
+ LauncherLogProto.ALL_APPS_BUTTON);
showAppsView(true /* animated */, false /* resetListToTop */,
true /* updatePredictedApps */, true /* focusSearchBar */);
}
diff --git a/src/com/android/launcher3/Utilities.java b/src/com/android/launcher3/Utilities.java
index 7b1a16c..ef78195 100644
--- a/src/com/android/launcher3/Utilities.java
+++ b/src/com/android/launcher3/Utilities.java
@@ -113,8 +113,8 @@
&& "NMR1".compareTo(VERSION.CODENAME) <= 0;
}
- // TODO: use Build.VERSION_CODES when available
- public static final boolean ATLEAST_MARSHMALLOW = Build.VERSION.SDK_INT >= 23;
+ public static final boolean ATLEAST_MARSHMALLOW =
+ Build.VERSION.SDK_INT >= Build.VERSION_CODES.M;
public static final boolean ATLEAST_LOLLIPOP_MR1 =
Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP_MR1;
diff --git a/src/com/android/launcher3/allapps/AllAppsGridAdapter.java b/src/com/android/launcher3/allapps/AllAppsGridAdapter.java
index 97c46b1..d8f9fb1 100644
--- a/src/com/android/launcher3/allapps/AllAppsGridAdapter.java
+++ b/src/com/android/launcher3/allapps/AllAppsGridAdapter.java
@@ -66,7 +66,7 @@
public static final int VIEW_TYPE_PREDICTION_ICON = 1 << 2;
// The message shown when there are no filtered results
public static final int VIEW_TYPE_EMPTY_SEARCH = 1 << 3;
- // A divider that separates the apps list and the search market button
+ // The message to continue to a market search when there are no filtered results
public static final int VIEW_TYPE_SEARCH_MARKET = 1 << 4;
// We use various dividers for various purposes. They share enough attributes to reuse layouts,
@@ -528,8 +528,6 @@
TextView searchView = (TextView) holder.mContent;
if (mMarketSearchIntent != null) {
searchView.setVisibility(View.VISIBLE);
- searchView.setGravity(mApps.hasNoFilteredResults() ? Gravity.CENTER :
- Gravity.START | Gravity.CENTER_VERTICAL);
} else {
searchView.setVisibility(View.GONE);
}
diff --git a/src/com/android/launcher3/allapps/AllAppsRecyclerViewContainerView.java b/src/com/android/launcher3/allapps/AllAppsRecyclerViewContainerView.java
index 09a7d59..1d5b209 100644
--- a/src/com/android/launcher3/allapps/AllAppsRecyclerViewContainerView.java
+++ b/src/com/android/launcher3/allapps/AllAppsRecyclerViewContainerView.java
@@ -18,6 +18,7 @@
import android.content.Context;
import android.graphics.Bitmap;
import android.util.AttributeSet;
+import android.view.View;
import android.view.ViewGroup;
import android.widget.FrameLayout;
@@ -26,6 +27,7 @@
import com.android.launcher3.ClickShadowView;
import com.android.launcher3.DeviceProfile;
import com.android.launcher3.Launcher;
+import com.android.launcher3.R;
/**
* A container for RecyclerView to allow for the click shadow view to be shown behind an icon that
@@ -63,7 +65,8 @@
mTouchFeedbackView.setBitmap(null);
mTouchFeedbackView.animate().cancel();
} else if (mTouchFeedbackView.setBitmap(background)) {
- mTouchFeedbackView.alignWithIconView(icon, (ViewGroup) icon.getParent());
+ View rv = findViewById(R.id.apps_list_view);
+ mTouchFeedbackView.alignWithIconView(icon, (ViewGroup) icon.getParent(), rv);
mTouchFeedbackView.animateShadow();
}
}
diff --git a/src/com/android/launcher3/allapps/AllAppsTransitionController.java b/src/com/android/launcher3/allapps/AllAppsTransitionController.java
index 03b3107..136308b 100644
--- a/src/com/android/launcher3/allapps/AllAppsTransitionController.java
+++ b/src/com/android/launcher3/allapps/AllAppsTransitionController.java
@@ -22,6 +22,7 @@
import com.android.launcher3.R;
import com.android.launcher3.Workspace;
import com.android.launcher3.Workspace.Direction;
+import com.android.launcher3.userevent.nano.LauncherLogProto;
import com.android.launcher3.util.TouchController;
/**
@@ -210,6 +211,10 @@
calculateDuration(velocity, mAppsView.getTranslationY());
if (!mLauncher.isAllAppsVisible()) {
+ mLauncher.getUserEventDispatcher().logActionOnContainer(
+ LauncherLogProto.Action.FLING,
+ LauncherLogProto.Action.UP,
+ LauncherLogProto.HOTSEAT);
mLauncher.showAppsView(true, true, false, false);
} else {
animateToAllApps(mCurrentAnimation, mAnimationDuration, true);
@@ -234,6 +239,10 @@
} else {
calculateDuration(velocity, Math.abs(mAppsView.getTranslationY()));
if (!mLauncher.isAllAppsVisible()) {
+ mLauncher.getUserEventDispatcher().logActionOnContainer(
+ LauncherLogProto.Action.SWIPE,
+ LauncherLogProto.Action.UP,
+ LauncherLogProto.HOTSEAT);
mLauncher.showAppsView(true, true, false, false);
} else {
animateToAllApps(mCurrentAnimation, mAnimationDuration, true);
diff --git a/src/com/android/launcher3/logging/LoggerUtils.java b/src/com/android/launcher3/logging/LoggerUtils.java
index 584e38e..9e92721 100644
--- a/src/com/android/launcher3/logging/LoggerUtils.java
+++ b/src/com/android/launcher3/logging/LoggerUtils.java
@@ -1,15 +1,9 @@
package com.android.launcher3.logging;
-import android.os.Bundle;
-import android.util.Log;
-
-import com.android.launcher3.LauncherSettings;
-import com.android.launcher3.ShortcutInfo;
import com.android.launcher3.userevent.nano.LauncherLogProto;
import com.android.launcher3.userevent.nano.LauncherLogProto.Action;
import com.android.launcher3.userevent.nano.LauncherLogProto.Target;
-
/**
* Debugging helper methods.
* toString() cannot be overriden inside auto generated {@link LauncherLogProto}.
@@ -24,12 +18,17 @@
case Action.LONGPRESS: return "LONGPRESS";
case Action.DRAGDROP: return "DRAGDROP";
case Action.PINCH: return "PINCH";
+ case Action.SWIPE: return "SWIPE";
+ case Action.FLING: return "FLING";
default: return "UNKNOWN";
}
}
public static String getTargetStr(Target t) {
- String typeStr;
+ String typeStr = "";
+ if (t == null){
+ return typeStr;
+ }
switch (t.type) {
case Target.ITEM:
return getItemStr(t);
@@ -44,6 +43,9 @@
private static String getItemStr(Target t) {
String typeStr = "";
+ if (t == null){
+ return typeStr;
+ }
switch(t.itemType){
case LauncherLogProto.APP_ICON: typeStr = "ICON"; break;
case LauncherLogProto.SHORTCUT: typeStr = "SHORTCUT"; break;
@@ -58,6 +60,9 @@
}
private static String getControlStr(Target t) {
+ if (t == null){
+ return "";
+ }
switch(t.controlType) {
case LauncherLogProto.ALL_APPS_BUTTON: return "ALL_APPS_BUTTON";
case LauncherLogProto.WIDGETS_BUTTON: return "WIDGETS_BUTTON";
@@ -72,8 +77,10 @@
}
private static String getContainerStr(LauncherLogProto.Target t) {
- String str;
- Log.d(TAG, "t.containerType" + t.containerType);
+ String str = "";
+ if (t == null) {
+ return str;
+ }
switch (t.containerType) {
case LauncherLogProto.WORKSPACE:
str = "WORKSPACE";
@@ -122,4 +129,18 @@
event.action.type = actionType;
return event;
}
+
+ public static LauncherLogProto.LauncherEvent initLauncherEvent(
+ int actionType,
+ int childTargetType){
+ LauncherLogProto.LauncherEvent event = new LauncherLogProto.LauncherEvent();
+
+ event.srcTarget = new LauncherLogProto.Target[1];
+ event.srcTarget[0] = new LauncherLogProto.Target();
+ event.srcTarget[0].type = childTargetType;
+
+ event.action = new LauncherLogProto.Action();
+ event.action.type = actionType;
+ return event;
+ }
}
diff --git a/src/com/android/launcher3/logging/UserEventDispatcher.java b/src/com/android/launcher3/logging/UserEventDispatcher.java
index 0deee57..f67f487 100644
--- a/src/com/android/launcher3/logging/UserEventDispatcher.java
+++ b/src/com/android/launcher3/logging/UserEventDispatcher.java
@@ -37,8 +37,8 @@
public class UserEventDispatcher {
private static final boolean DEBUG_LOGGING = false;
-
private final static int MAXIMUM_VIEW_HIERARCHY_LEVEL = 5;
+
/**
* Implemented by containers to provide a launch source for a given child.
*/
@@ -46,10 +46,11 @@
/**
* Copies data from the source to the destination proto.
- * @param v source of the data
- * @param info source of the data
- * @param target dest of the data
- * @param targetParent dest of the data
+ *
+ * @param v source of the data
+ * @param info source of the data
+ * @param target dest of the data
+ * @param targetParent dest of the data
*/
void fillInLaunchSourceData(View v, ItemInfo info, Target target, Target targetParent);
}
@@ -126,12 +127,23 @@
dispatchUserEvent(createLauncherEvent(v, intent), intent);
}
- public void logTap(View v) {
- // TODO
+ public void logActionOnControl(int action, int controlType) {
+ LauncherEvent event = LoggerUtils.initLauncherEvent(Action.TOUCH, Target.CONTROL);
+ event.action.touch = action;
+ event.srcTarget[0].controlType = controlType;
+ event.elapsedContainerMillis = System.currentTimeMillis() - mElapsedContainerMillis;
+ event.elapsedSessionMillis = System.currentTimeMillis() - mElapsedSessionMillis;
+ dispatchUserEvent(event, null);
}
- public void logLongPress() {
- // TODO
+ public void logActionOnContainer(int action, int dir, int containerType) {
+ LauncherEvent event = LoggerUtils.initLauncherEvent(Action.TOUCH, Target.CONTAINER);
+ event.action.touch = action;
+ event.action.dir = dir;
+ event.srcTarget[0].containerType = containerType;
+ event.elapsedContainerMillis = System.currentTimeMillis() - mElapsedContainerMillis;
+ event.elapsedSessionMillis = System.currentTimeMillis() - mElapsedSessionMillis;
+ dispatchUserEvent(event, null);
}
public void logDragNDrop() {
@@ -152,7 +164,6 @@
public final void resetElapsedSessionMillis() {
mElapsedSessionMillis = System.currentTimeMillis();
mElapsedContainerMillis = System.currentTimeMillis();
-
}
public final void resetActionDurationMillis() {
@@ -164,8 +175,8 @@
Log.d("UserEvent", String.format(Locale.US,
"action:%s\nchild:%s\nparent:%s\nelapsed container %d ms session %d ms",
LoggerUtils.getActionStr(ev.action),
- LoggerUtils.getTargetStr(ev.srcTarget[0]),
- LoggerUtils.getTargetStr(ev.srcTarget[1]),
+ LoggerUtils.getTargetStr(ev.srcTarget != null ? ev.srcTarget[0] : null),
+ LoggerUtils.getTargetStr(ev.srcTarget.length > 1 ? ev.srcTarget[1] : null),
ev.elapsedContainerMillis,
ev.elapsedSessionMillis));
}
diff --git a/src/com/android/launcher3/shortcuts/DeepShortcutTextView.java b/src/com/android/launcher3/shortcuts/DeepShortcutTextView.java
new file mode 100644
index 0000000..c48d160
--- /dev/null
+++ b/src/com/android/launcher3/shortcuts/DeepShortcutTextView.java
@@ -0,0 +1,50 @@
+/*
+ * Copyright (C) 2016 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.launcher3.shortcuts;
+
+import android.content.Context;
+import android.graphics.drawable.Drawable;
+import android.util.AttributeSet;
+
+import com.android.launcher3.BubbleTextView;
+import com.android.launcher3.R;
+
+/**
+ * A {@link BubbleTextView} that has the shortcut icon on the left and drag handle on the right.
+ */
+public class DeepShortcutTextView extends BubbleTextView {
+
+ public DeepShortcutTextView(Context context) {
+ this(context, null, 0);
+ }
+
+ public DeepShortcutTextView(Context context, AttributeSet attrs) {
+ this(context, attrs, 0);
+ }
+
+ public DeepShortcutTextView(Context context, AttributeSet attrs, int defStyle) {
+ super(context, attrs, defStyle);
+ }
+
+ @Override
+ /** Use the BubbleTextView icon for the start and the drag handle for the end. */
+ protected void applyCompoundDrawables(Drawable icon) {
+ Drawable dragHandle = getResources().getDrawable(R.drawable.deep_shortcuts_drag_handle);
+ dragHandle.setBounds(0, 0, dragHandle.getIntrinsicWidth(), dragHandle.getIntrinsicHeight());
+ setCompoundDrawablesRelative(icon, null, dragHandle, null);
+ }
+}
diff --git a/src/com/android/launcher3/shortcuts/DeepShortcutsContainer.java b/src/com/android/launcher3/shortcuts/DeepShortcutsContainer.java
index 912f006..9f59e06 100644
--- a/src/com/android/launcher3/shortcuts/DeepShortcutsContainer.java
+++ b/src/com/android/launcher3/shortcuts/DeepShortcutsContainer.java
@@ -160,11 +160,10 @@
final ShortcutInfoCompat shortcut = shortcuts.get(i);
final ShortcutInfo launcherShortcutInfo = ShortcutInfo
.fromDeepShortcutInfo(shortcut, mLauncher);
- CharSequence label = shortcut.getLongLabel();
- if (TextUtils.isEmpty(label)) {
- label = shortcut.getShortLabel();
- }
- uiHandler.post(new UpdateShortcutChild(i, launcherShortcutInfo, label));
+ CharSequence shortLabel = shortcut.getShortLabel();
+ CharSequence longLabel = shortcut.getLongLabel();
+ uiHandler.post(new UpdateShortcutChild(i, launcherShortcutInfo,
+ shortLabel, longLabel));
}
}
});
@@ -174,13 +173,15 @@
private class UpdateShortcutChild implements Runnable {
private int mShortcutChildIndex;
private ShortcutInfo mShortcutChildInfo;
- private CharSequence mLabel;
+ private CharSequence mShortLabel;
+ private CharSequence mLongLabel;
public UpdateShortcutChild(int shortcutChildIndex, ShortcutInfo shortcutChildInfo,
- CharSequence label) {
+ CharSequence shortLabel, CharSequence longLabel) {
mShortcutChildIndex = shortcutChildIndex;
mShortcutChildInfo = shortcutChildInfo;
- mLabel = label;
+ mShortLabel = shortLabel;
+ mLongLabel = longLabel;
}
@Override
@@ -188,7 +189,12 @@
BubbleTextView shortcutView = getShortcutAt(mShortcutChildIndex).getBubbleText();
shortcutView.applyFromShortcutInfo(mShortcutChildInfo,
LauncherAppState.getInstance().getIconCache());
- shortcutView.setText(mLabel);
+ // Use the long label as long as it exists and fits.
+ int availableWidth = shortcutView.getWidth() - shortcutView.getTotalPaddingLeft()
+ - shortcutView.getTotalPaddingRight();
+ boolean usingLongLabel = !TextUtils.isEmpty(mLongLabel)
+ && shortcutView.getPaint().measureText(mLongLabel.toString()) <= availableWidth;
+ shortcutView.setText(usingLongLabel ? mLongLabel : mShortLabel);
shortcutView.setOnClickListener(mLauncher);
shortcutView.setOnLongClickListener(DeepShortcutsContainer.this);
shortcutView.setOnTouchListener(DeepShortcutsContainer.this);
@@ -480,10 +486,8 @@
@Override
public void fillInLaunchSourceData(View v, ItemInfo info, Target target, Target targetParent) {
- target.itemType = LauncherLogProto.SHORTCUT; // TODO: change to DYNAMIC_SHORTCUT
- target.gridX = info.cellX;
- target.gridY = info.cellY;
- target.pageIndex = 0;
- targetParent.containerType = LauncherLogProto.FOLDER; // TODO: change to DYNAMIC_SHORTCUTS
+ target.itemType = LauncherLogProto.DEEPSHORTCUT;
+ // TODO: add target.rank
+ targetParent.containerType = LauncherLogProto.DEEPSHORTCUTS;
}
}