summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--res/layout/apps_list_view.xml56
-rw-r--r--res/values/dimens.xml4
-rw-r--r--src/com/android/launcher3/AppsContainerRecyclerView.java4
-rw-r--r--src/com/android/launcher3/AppsContainerView.java123
4 files changed, 135 insertions, 52 deletions
diff --git a/res/layout/apps_list_view.xml b/res/layout/apps_list_view.xml
index 5e50191ea..03ba646ee 100644
--- a/res/layout/apps_list_view.xml
+++ b/res/layout/apps_list_view.xml
@@ -1,5 +1,6 @@
<?xml version="1.0" encoding="utf-8"?>
-<!-- Copyright (C) 2015 The Android Open Source Project
+<!--
+ Copyright (C) 2015 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.
@@ -13,44 +14,48 @@
See the License for the specific language governing permissions and
limitations under the License.
-->
-<FrameLayout
- xmlns:android="http://schemas.android.com/apk/res/android"
+<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="@+id/apps_list"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:elevation="15dp"
- android:visibility="gone"
- android:focusableInTouchMode="true">
+ android:focusableInTouchMode="true"
+ android:visibility="gone" >
+
<com.android.launcher3.AppsContainerRecyclerView
android:id="@+id/apps_list_view"
android:layout_width="match_parent"
android:layout_height="match_parent"
- android:layout_marginTop="@dimen/apps_search_bar_height"
android:layout_gravity="center_horizontal|top"
+ android:layout_marginTop="@dimen/apps_search_bar_height"
android:clipToPadding="false"
- android:focusable="true"
- android:descendantFocusability="afterDescendants" />
+ android:descendantFocusability="afterDescendants"
+ android:focusable="true" />
+
<LinearLayout
android:id="@+id/prediction_bar"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginTop="@dimen/apps_search_bar_height"
android:orientation="horizontal"
- android:visibility="invisible">
+ android:visibility="invisible" >
</LinearLayout>
<!-- We always want the search bar on top, so it goes last. -->
+
<FrameLayout
android:id="@+id/header"
android:layout_width="match_parent"
android:layout_height="@dimen/apps_search_bar_height"
- android:background="@drawable/apps_search_bg">
+ android:background="@drawable/apps_search_bg" >
+
<LinearLayout
android:id="@+id/app_search_container"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal"
- android:visibility="invisible">
+ android:visibility="invisible" >
+
<ImageView
android:id="@+id/dismiss_search_button"
android:layout_width="wrap_content"
@@ -58,29 +63,31 @@
android:layout_gravity="start|center_vertical"
android:layout_marginLeft="4dp"
android:layout_marginStart="4dp"
- android:paddingTop="13dp"
- android:paddingBottom="13dp"
android:contentDescription="@string/all_apps_button_label"
+ android:paddingBottom="13dp"
+ android:paddingTop="13dp"
android:src="@drawable/ic_arrow_back_grey" />
+
<com.android.launcher3.AppsContainerSearchEditTextView
android:id="@+id/app_search_box"
android:layout_width="match_parent"
android:layout_height="match_parent"
- android:paddingTop="16dp"
- android:paddingBottom="16dp"
- android:paddingLeft="8dp"
+ android:background="@android:color/transparent"
+ android:focusableInTouchMode="true"
+ android:gravity="fill_horizontal"
android:hint="@string/apps_view_search_bar_hint"
+ android:imeOptions="actionDone|flagNoExtractUi"
android:maxLines="1"
- android:singleLine="true"
+ android:paddingBottom="16dp"
+ android:paddingLeft="8dp"
+ android:paddingTop="16dp"
android:scrollHorizontally="true"
- android:gravity="fill_horizontal"
- android:textSize="16sp"
+ android:singleLine="true"
android:textColor="#4c4c4c"
android:textColorHint="#9c9c9c"
- android:imeOptions="actionDone|flagNoExtractUi"
- android:focusableInTouchMode="true"
- android:background="@android:color/transparent" />
+ android:textSize="16sp" />
</LinearLayout>
+
<ImageView
android:id="@+id/search_button"
android:layout_width="wrap_content"
@@ -88,9 +95,10 @@
android:layout_gravity="end|center_vertical"
android:layout_marginEnd="6dp"
android:layout_marginRight="6dp"
- android:paddingTop="13dp"
- android:paddingBottom="13dp"
android:contentDescription="@string/apps_view_search_bar_hint"
+ android:paddingBottom="13dp"
+ android:paddingTop="13dp"
android:src="@drawable/ic_search_grey" />
</FrameLayout>
+
</FrameLayout> \ No newline at end of file
diff --git a/res/values/dimens.xml b/res/values/dimens.xml
index 2fa16e7a2..b5acfbdc6 100644
--- a/res/values/dimens.xml
+++ b/res/values/dimens.xml
@@ -71,6 +71,10 @@
<dimen name="drop_target_drag_padding">14dp</dimen>
<dimen name="drop_target_text_size">14sp</dimen>
+ <dimen name="all_apps_header_max_elevation">4dp</dimen>
+ <dimen name="all_apps_header_scroll_to_elevation">16dp</dimen>
+ <dimen name="all_apps_header_shadow_height">6dp</dimen>
+
<!-- Dragging -->
<!-- the area at the edge of the screen that makes the workspace go left
or right while you're dragging. -->
diff --git a/src/com/android/launcher3/AppsContainerRecyclerView.java b/src/com/android/launcher3/AppsContainerRecyclerView.java
index 861767e80..95da48fcd 100644
--- a/src/com/android/launcher3/AppsContainerRecyclerView.java
+++ b/src/com/android/launcher3/AppsContainerRecyclerView.java
@@ -146,9 +146,7 @@ public class AppsContainerRecyclerView extends BaseContainerRecyclerView {
mNumPredictedAppsPerRow = numPredictedAppsPerRow;
}
- @Override
- public void setBackground(Drawable background) {
- super.setBackground(background);
+ public void updateBackgroundPadding(Drawable background) {
background.getPadding(mBackgroundPadding);
}
diff --git a/src/com/android/launcher3/AppsContainerView.java b/src/com/android/launcher3/AppsContainerView.java
index b752905a2..7c1aee228 100644
--- a/src/com/android/launcher3/AppsContainerView.java
+++ b/src/com/android/launcher3/AppsContainerView.java
@@ -22,6 +22,7 @@ import android.content.Context;
import android.content.res.Resources;
import android.graphics.Point;
import android.graphics.Rect;
+import android.graphics.drawable.GradientDrawable;
import android.graphics.drawable.InsetDrawable;
import android.os.Build;
import android.support.v7.widget.RecyclerView;
@@ -58,9 +59,7 @@ public class AppsContainerView extends BaseContainerView implements DragSource,
private static final boolean ALLOW_SINGLE_APP_LAUNCH = true;
private static final boolean DYNAMIC_HEADER_ELEVATION = true;
private static final boolean DISMISS_SEARCH_ON_BACK = true;
- private static final float HEADER_ELEVATION_DP = 4;
- // How far the user has to scroll in order to reach the full elevation
- private static final float HEADER_SCROLL_TO_ELEVATION_DP = 16;
+
private static final int FADE_IN_DURATION = 175;
private static final int FADE_OUT_DURATION = 100;
private static final int SEARCH_TRANSLATION_X_DP = 18;
@@ -83,6 +82,8 @@ public class AppsContainerView extends BaseContainerView implements DragSource,
private View mDismissSearchButtonView;
private AppsContainerSearchEditTextView mSearchBarEditView;
+ private HeaderElevationController mElevationController;
+
private int mNumAppsPerRow;
private int mNumPredictedAppsPerRow;
// This coordinate is relative to this container view
@@ -174,6 +175,7 @@ public class AppsContainerView extends BaseContainerView implements DragSource,
*/
public void hideHeaderBar() {
mHeaderView.setVisibility(View.GONE);
+ mElevationController.disable();
onUpdateBackgrounds();
onUpdatePaddings();
}
@@ -219,9 +221,13 @@ public class AppsContainerView extends BaseContainerView implements DragSource,
// Fix the header view elevation if not dynamically calculating it
mHeaderView = findViewById(R.id.header);
mHeaderView.setOnClickListener(this);
- if (Utilities.isLmpOrAbove() && !DYNAMIC_HEADER_ELEVATION) {
- mHeaderView.setElevation(DynamicGrid.pxFromDp(HEADER_ELEVATION_DP,
- getContext().getResources().getDisplayMetrics()));
+
+ mElevationController = Utilities.isLmpOrAbove() ?
+ new HeaderElevationControllerVL(mHeaderView) :
+ new HeaderElevationControllerV16(mHeaderView);
+ if (!DYNAMIC_HEADER_ELEVATION) {
+ mElevationController.onScroll(getResources()
+ .getDimensionPixelSize(R.dimen.all_apps_header_scroll_to_elevation));
}
// Fix the prediction bar size
@@ -335,6 +341,10 @@ public class AppsContainerView extends BaseContainerView implements DragSource,
boolean hasSearchBar = (mSearchBarEditView != null) &&
(mSearchBarEditView.getVisibility() == View.VISIBLE);
+ // Set the background on the container, but let the recyclerView extend the full screen,
+ // so that the fast-scroller works on the edge as well.
+ mContentView.setPadding(0, 0, 0, 0);
+
if (mFixedBounds.isEmpty()) {
// If there are no fixed bounds, then use the default padding and insets
setPadding(mInsets.left, mContainerInset + mInsets.top, mInsets.right,
@@ -377,19 +387,16 @@ public class AppsContainerView extends BaseContainerView implements DragSource,
@Override
protected void onUpdateBackgrounds() {
int inset = mFixedBounds.isEmpty() ? mContainerInset : mFixedBoundsContainerInset;
- boolean hasSearchBar = (mSearchBarEditView != null) &&
- (mSearchBarEditView.getVisibility() == View.VISIBLE);
// Update the background of the reveal view and list to be inset with the fixed bound
// insets instead of the default insets
// TODO: Use quantum_panel instead of quantum_panel_shape.
- mAppsRecyclerView.setBackground(new InsetDrawable(
- getContext().getResources().getDrawable(
- hasSearchBar ? R.drawable.apps_list_search_bg : R.drawable.quantum_panel_shape),
- inset, 0, inset, 0));
- getRevealView().setBackground(new InsetDrawable(
+ InsetDrawable background = new InsetDrawable(
getContext().getResources().getDrawable(R.drawable.quantum_panel_shape),
- inset, 0, inset, 0));
+ inset, 0, inset, 0);
+ mContentView.setBackground(background);
+ mAppsRecyclerView.updateBackgroundPadding(background);
+ getRevealView().setBackground(background.getConstantState().newDrawable());
}
@Override
@@ -619,17 +626,8 @@ public class AppsContainerView extends BaseContainerView implements DragSource,
*/
@TargetApi(Build.VERSION_CODES.LOLLIPOP)
private void onRecyclerViewScrolled() {
- if (DYNAMIC_HEADER_ELEVATION && Utilities.isLmpOrAbove()) {
- int elevation = DynamicGrid.pxFromDp(HEADER_ELEVATION_DP,
- getContext().getResources().getDisplayMetrics());
- int scrollToElevation = DynamicGrid.pxFromDp(HEADER_SCROLL_TO_ELEVATION_DP,
- getContext().getResources().getDisplayMetrics());
- float elevationPct = (float) Math.min(mRecyclerViewScrollY, scrollToElevation) /
- scrollToElevation;
- float newElevation = elevation * elevationPct;
- if (Float.compare(mHeaderView.getElevation(), newElevation) != 0) {
- mHeaderView.setElevation(newElevation);
- }
+ if (DYNAMIC_HEADER_ELEVATION) {
+ mElevationController.onScroll(mRecyclerViewScrollY);
}
mPredictionBarView.setTranslationY(-mRecyclerViewScrollY + mAppsRecyclerView.getPaddingTop());
@@ -839,4 +837,79 @@ public class AppsContainerView extends BaseContainerView implements DragSource,
private InputMethodManager getInputMethodManager() {
return (InputMethodManager) getContext().getSystemService(Context.INPUT_METHOD_SERVICE);
}
+
+ private static interface HeaderElevationController {
+
+ public void onScroll(int scrollY);
+
+ public void disable();
+ }
+
+ private static final class HeaderElevationControllerV16 implements HeaderElevationController {
+
+ private final View mShadow;
+
+ private final float mScrollToElevation;
+
+ public HeaderElevationControllerV16(View header) {
+ Resources res = header.getContext().getResources();
+ mScrollToElevation = res.getDimension(R.dimen.all_apps_header_scroll_to_elevation);
+
+ mShadow = new View(header.getContext());
+ mShadow.setBackground(new GradientDrawable(
+ GradientDrawable.Orientation.TOP_BOTTOM, new int[] {0x44000000, 0x00000000}));
+ mShadow.setAlpha(0);
+
+ FrameLayout.LayoutParams lp = new FrameLayout.LayoutParams(
+ LayoutParams.MATCH_PARENT,
+ res.getDimensionPixelSize(R.dimen.all_apps_header_shadow_height));
+ lp.topMargin = ((FrameLayout.LayoutParams) header.getLayoutParams()).height;
+
+ ((ViewGroup) header.getParent()).addView(mShadow, lp);
+ }
+
+ @Override
+ public void onScroll(int scrollY) {
+ float elevationPct = (float) Math.min(scrollY, mScrollToElevation) /
+ mScrollToElevation;
+ mShadow.setAlpha(elevationPct);
+ }
+
+ @Override
+ public void disable() {
+ ViewGroup parent = (ViewGroup) mShadow.getParent();
+ if (parent != null) {
+ parent.removeView(mShadow);
+ }
+ }
+ }
+
+ @TargetApi(Build.VERSION_CODES.LOLLIPOP)
+ private static final class HeaderElevationControllerVL implements HeaderElevationController {
+
+ private final View mHeader;
+ private final float mMaxElevation;
+ private final float mScrollToElevation;
+
+ public HeaderElevationControllerVL(View header) {
+ mHeader = header;
+
+ Resources res = header.getContext().getResources();
+ mMaxElevation = res.getDimension(R.dimen.all_apps_header_max_elevation);
+ mScrollToElevation = res.getDimension(R.dimen.all_apps_header_scroll_to_elevation);
+ }
+
+ @Override
+ public void onScroll(int scrollY) {
+ float elevationPct = (float) Math.min(scrollY, mScrollToElevation) /
+ mScrollToElevation;
+ float newElevation = mMaxElevation * elevationPct;
+ if (Float.compare(mHeader.getElevation(), newElevation) != 0) {
+ mHeader.setElevation(newElevation);
+ }
+ }
+
+ @Override
+ public void disable() { }
+ }
}