From 3c728fe61dcf49354ea761a3e4ef6032ec271630 Mon Sep 17 00:00:00 2001 From: Jim Miller Date: Thu, 7 Jul 2011 20:53:52 -0700 Subject: [PATCH] Fix 4689527: Improved curation for Recents + misc cleanup This sets a threshhold for both the curation animation as well as the snap back animation. It now limits these to 500ms and 250ms, respectively. Cleaned up misc log spew. Updated after review. Change-Id: Ie11a2fc4556b396257c33c3ebd7513c4c220ff95 --- .../android/systemui/recent/Constants.java | 24 +++++++++++ .../recent/RecentsHorizontalScrollView.java | 40 +++++++++++++------ .../systemui/recent/RecentsPanelView.java | 8 ++-- .../recent/RecentsVerticalScrollView.java | 38 ++++++++++++------ 4 files changed, 80 insertions(+), 30 deletions(-) create mode 100644 packages/SystemUI/src/com/android/systemui/recent/Constants.java diff --git a/packages/SystemUI/src/com/android/systemui/recent/Constants.java b/packages/SystemUI/src/com/android/systemui/recent/Constants.java new file mode 100644 index 0000000000000..66f929230b6d2 --- /dev/null +++ b/packages/SystemUI/src/com/android/systemui/recent/Constants.java @@ -0,0 +1,24 @@ +/* + * Copyright (C) 2011 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.systemui.recent; + +public class Constants { + static final int MAX_ESCAPE_ANIMATION_DURATION = 500; // in ms + static final float FADE_CONSTANT = 0.5f; // unitless + static final int SNAP_BACK_DURATION = 250; // in ms + static final int ESCAPE_VELOCITY = 100; // speed of item required to "curate" it in dp/s +} diff --git a/packages/SystemUI/src/com/android/systemui/recent/RecentsHorizontalScrollView.java b/packages/SystemUI/src/com/android/systemui/recent/RecentsHorizontalScrollView.java index 3dbcc5923fcf3..fb7a0a723ed57 100644 --- a/packages/SystemUI/src/com/android/systemui/recent/RecentsHorizontalScrollView.java +++ b/packages/SystemUI/src/com/android/systemui/recent/RecentsHorizontalScrollView.java @@ -25,6 +25,7 @@ import android.animation.ObjectAnimator; import android.animation.ValueAnimator; import android.animation.ValueAnimator.AnimatorUpdateListener; import android.content.Context; +import android.content.res.Configuration; import android.database.DataSetObserver; import android.graphics.RectF; import android.util.AttributeSet; @@ -33,6 +34,7 @@ import android.view.LayoutInflater; import android.view.MotionEvent; import android.view.VelocityTracker; import android.view.View; +import android.view.ViewConfiguration; import android.view.animation.DecelerateInterpolator; import android.view.animation.LinearInterpolator; import android.widget.HorizontalScrollView; @@ -42,12 +44,9 @@ import com.android.systemui.R; public class RecentsHorizontalScrollView extends HorizontalScrollView implements View.OnClickListener, View.OnTouchListener { - private static final float FADE_CONSTANT = 0.5f; - private static final int SNAP_BACK_DURATION = 250; - private static final int ESCAPE_VELOCITY = 100; // speed of item required to "curate" it - private static final String TAG = RecentsPanelView.TAG; - private static final float THRESHHOLD = 50; private static final boolean DEBUG_INVALIDATE = false; + private static final String TAG = RecentsPanelView.TAG; + private static final boolean DEBUG = RecentsPanelView.DEBUG; private LinearLayout mLinearLayout; private ActivityDescriptionAdapter mAdapter; private RecentsCallback mCallback; @@ -56,6 +55,8 @@ public class RecentsHorizontalScrollView extends HorizontalScrollView private float mLastY; private boolean mDragging; private VelocityTracker mVelocityTracker; + private float mDensityScale; + private float mPagingTouchSlop; public RecentsHorizontalScrollView(Context context) { this(context, null); @@ -63,6 +64,8 @@ public class RecentsHorizontalScrollView extends HorizontalScrollView public RecentsHorizontalScrollView(Context context, AttributeSet attrs) { super(context, attrs, 0); + mDensityScale = getResources().getDisplayMetrics().density; + mPagingTouchSlop = ViewConfiguration.get(mContext).getScaledPagingTouchSlop(); } private int scrollPositionOfMostRecent() { @@ -101,7 +104,8 @@ public class RecentsHorizontalScrollView extends HorizontalScrollView case MotionEvent.ACTION_MOVE: float delta = ev.getY() - mLastY; - if (Math.abs(delta) > THRESHHOLD) { + if (DEBUG) Log.v(TAG, "ACTION_MOVE : " + delta); + if (Math.abs(delta) > mPagingTouchSlop) { mDragging = true; } break; @@ -114,13 +118,14 @@ public class RecentsHorizontalScrollView extends HorizontalScrollView } private float getAlphaForOffset(View view, float thumbHeight) { - final float fadeHeight = FADE_CONSTANT * thumbHeight; + final float fadeHeight = Constants.FADE_CONSTANT * thumbHeight; float result = 1.0f; if (view.getY() >= thumbHeight) { result = 1.0f - (view.getY() - thumbHeight) / fadeHeight; } else if (view.getY() < 0.0f) { result = 1.0f + (thumbHeight + view.getY()) / fadeHeight; } + if (DEBUG) Log.v(TAG, "FADE AMOUNT: " + result); return result; } @@ -155,12 +160,13 @@ public class RecentsHorizontalScrollView extends HorizontalScrollView final float velocityY = velocityTracker.getYVelocity(); final float curY = animView.getY(); final float newY = (velocityY >= 0.0f ? 1 : -1) * animView.getHeight(); - + final float maxVelocity = Constants.ESCAPE_VELOCITY * mDensityScale; if (Math.abs(velocityY) > Math.abs(velocityX) - && Math.abs(velocityY) > ESCAPE_VELOCITY + && Math.abs(velocityY) > maxVelocity && (velocityY >= 0.0f) == (animView.getY() >= 0)) { - final long duration = + long duration = (long) (Math.abs(newY - curY) * 1000.0f / Math.abs(velocityY)); + duration = Math.min(duration, Constants.MAX_ESCAPE_ANIMATION_DURATION); anim = ObjectAnimator.ofFloat(animView, "y", curY, newY); anim.setInterpolator(new LinearInterpolator()); final int swipeDirection = animView.getY() >= 0.0f ? @@ -181,9 +187,10 @@ public class RecentsHorizontalScrollView extends HorizontalScrollView }); anim.setDuration(duration); } else { // Animate back to position - final long duration = Math.abs(velocityY) > 0.0f ? + long duration = Math.abs(velocityY) > 0.0f ? (long) (Math.abs(newY - curY) * 1000.0f / Math.abs(velocityY)) - : SNAP_BACK_DURATION; + : Constants.SNAP_BACK_DURATION; + duration = Math.min(duration, Constants.SNAP_BACK_DURATION); anim = ObjectAnimator.ofFloat(animView, "y", animView.getY(), 0.0f); anim.setInterpolator(new DecelerateInterpolator(2.0f)); anim.setDuration(duration); @@ -241,8 +248,15 @@ public class RecentsHorizontalScrollView extends HorizontalScrollView setOverScrollEffectPadding(leftPadding, 0); } + @Override + protected void onConfigurationChanged(Configuration newConfig) { + super.onConfigurationChanged(newConfig); + mDensityScale = getResources().getDisplayMetrics().density; + mPagingTouchSlop = ViewConfiguration.get(mContext).getScaledPagingTouchSlop(); + } + private void setOverScrollEffectPadding(int leftPadding, int i) { - // TODO Add to RecentsHorizontalScrollView + // TODO Add to (Vertical)ScrollView } @Override diff --git a/packages/SystemUI/src/com/android/systemui/recent/RecentsPanelView.java b/packages/SystemUI/src/com/android/systemui/recent/RecentsPanelView.java index 6190c9bbafc0b..a55fe9c0017ca 100644 --- a/packages/SystemUI/src/com/android/systemui/recent/RecentsPanelView.java +++ b/packages/SystemUI/src/com/android/systemui/recent/RecentsPanelView.java @@ -417,11 +417,11 @@ public class RecentsPanelView extends RelativeLayout mActivityDescriptions = getRecentTasks(); mListAdapter.notifyDataSetInvalidated(); if (mActivityDescriptions.size() > 0) { - Log.v(TAG, "Showing " + mActivityDescriptions.size() + " apps"); + if (DEBUG) Log.v(TAG, "Showing " + mActivityDescriptions.size() + " apps"); updateUiElements(getResources().getConfiguration()); } else { // Immediately hide this panel - Log.v(TAG, "Nothing to show"); + if (DEBUG) Log.v(TAG, "Nothing to show"); hide(false); } } @@ -436,7 +436,7 @@ public class RecentsPanelView extends RelativeLayout paint.setAlpha(255); final int srcWidth = thumbnail.getWidth(); final int srcHeight = thumbnail.getHeight(); - Log.v(TAG, "Source thumb: " + srcWidth + "x" + srcHeight); + if (DEBUG) Log.v(TAG, "Source thumb: " + srcWidth + "x" + srcHeight); canvas.drawBitmap(thumbnail, new Rect(0, 0, srcWidth-1, srcHeight-1), new RectF(mGlowBitmapPaddingLeftPx, mGlowBitmapPaddingTopPx, @@ -486,7 +486,7 @@ public class RecentsPanelView extends RelativeLayout public void handleSwipe(View view, int direction) { ActivityDescription ad = ((ViewHolder) view.getTag()).activityDescription; - Log.v(TAG, "Jettison " + ad.label); + if (DEBUG) Log.v(TAG, "Jettison " + ad.label); mActivityDescriptions.remove(ad); // Handled by widget containers to enable LayoutTransitions properly diff --git a/packages/SystemUI/src/com/android/systemui/recent/RecentsVerticalScrollView.java b/packages/SystemUI/src/com/android/systemui/recent/RecentsVerticalScrollView.java index 6a962cb8f5413..711ffa3edd881 100644 --- a/packages/SystemUI/src/com/android/systemui/recent/RecentsVerticalScrollView.java +++ b/packages/SystemUI/src/com/android/systemui/recent/RecentsVerticalScrollView.java @@ -25,6 +25,7 @@ import android.animation.ObjectAnimator; import android.animation.ValueAnimator; import android.animation.ValueAnimator.AnimatorUpdateListener; import android.content.Context; +import android.content.res.Configuration; import android.database.DataSetObserver; import android.graphics.RectF; import android.util.AttributeSet; @@ -33,6 +34,7 @@ import android.view.LayoutInflater; import android.view.MotionEvent; import android.view.VelocityTracker; import android.view.View; +import android.view.ViewConfiguration; import android.view.animation.DecelerateInterpolator; import android.view.animation.LinearInterpolator; import android.widget.LinearLayout; @@ -42,12 +44,9 @@ import com.android.systemui.R; public class RecentsVerticalScrollView extends ScrollView implements View.OnClickListener, View.OnTouchListener { - private static final float FADE_CONSTANT = 0.5f; - private static final int SNAP_BACK_DURATION = 250; - private static final int ESCAPE_VELOCITY = 100; // speed of item required to "curate" it private static final String TAG = RecentsPanelView.TAG; - private static final float THRESHHOLD = 50; private static final boolean DEBUG_INVALIDATE = false; + private static final boolean DEBUG = RecentsPanelView.DEBUG; private LinearLayout mLinearLayout; private ActivityDescriptionAdapter mAdapter; private RecentsCallback mCallback; @@ -56,6 +55,8 @@ public class RecentsVerticalScrollView extends ScrollView private float mLastX; private boolean mDragging; private VelocityTracker mVelocityTracker; + private float mDensityScale; + private float mPagingTouchSlop; public RecentsVerticalScrollView(Context context) { this(context, null); @@ -63,6 +64,8 @@ public class RecentsVerticalScrollView extends ScrollView public RecentsVerticalScrollView(Context context, AttributeSet attrs) { super(context, attrs, 0); + mDensityScale = getResources().getDisplayMetrics().density; + mPagingTouchSlop = ViewConfiguration.get(mContext).getScaledPagingTouchSlop(); } private int scrollPositionOfMostRecent() { @@ -101,8 +104,8 @@ public class RecentsVerticalScrollView extends ScrollView case MotionEvent.ACTION_MOVE: float delta = ev.getX() - mLastX; - Log.v(TAG, "ACTION_MOVE : " + delta); - if (Math.abs(delta) > THRESHHOLD) { + if (DEBUG) Log.v(TAG, "ACTION_MOVE : " + delta); + if (Math.abs(delta) > mPagingTouchSlop) { mDragging = true; } break; @@ -115,14 +118,14 @@ public class RecentsVerticalScrollView extends ScrollView } private float getAlphaForOffset(View view, float thumbWidth) { - final float fadeWidth = FADE_CONSTANT * thumbWidth; + final float fadeWidth = Constants.FADE_CONSTANT * thumbWidth; float result = 1.0f; if (view.getX() >= thumbWidth) { result = 1.0f - (view.getX() - thumbWidth) / fadeWidth; } else if (view.getX() < 0.0f) { result = 1.0f + (thumbWidth + view.getX()) / fadeWidth; } - Log.v(TAG, "FADE AMOUNT: " + result); + if (DEBUG) Log.v(TAG, "FADE AMOUNT: " + result); return result; } @@ -157,12 +160,13 @@ public class RecentsVerticalScrollView extends ScrollView final float velocityY = velocityTracker.getYVelocity(); final float curX = animView.getX(); final float newX = (velocityX >= 0.0f ? 1 : -1) * animView.getWidth(); - + final float maxVelocity = Constants.ESCAPE_VELOCITY * mDensityScale; if (Math.abs(velocityX) > Math.abs(velocityY) - && Math.abs(velocityX) > ESCAPE_VELOCITY + && Math.abs(velocityX) > maxVelocity && (velocityX > 0.0f) == (animView.getX() >= 0)) { - final long duration = + long duration = (long) (Math.abs(newX-curX) * 1000.0f / Math.abs(velocityX)); + duration = Math.min(duration, Constants.MAX_ESCAPE_ANIMATION_DURATION); anim = ObjectAnimator.ofFloat(animView, "x", curX, newX); anim.setInterpolator(new LinearInterpolator()); final int swipeDirection = animView.getX() >= 0.0f ? @@ -183,9 +187,10 @@ public class RecentsVerticalScrollView extends ScrollView }); anim.setDuration(duration); } else { // Animate back to position - final long duration = Math.abs(velocityX) > 0.0f ? + long duration = Math.abs(velocityX) > 0.0f ? (long) (Math.abs(newX-curX) * 1000.0f / Math.abs(velocityX)) - : SNAP_BACK_DURATION; + : Constants.SNAP_BACK_DURATION; + duration = Math.min(duration, Constants.SNAP_BACK_DURATION); anim = ObjectAnimator.ofFloat(animView, "x", animView.getX(), 0.0f); anim.setInterpolator(new DecelerateInterpolator(4.0f)); anim.setDuration(duration); @@ -243,6 +248,13 @@ public class RecentsVerticalScrollView extends ScrollView setOverScrollEffectPadding(leftPadding, 0); } + @Override + protected void onConfigurationChanged(Configuration newConfig) { + super.onConfigurationChanged(newConfig); + mDensityScale = getResources().getDisplayMetrics().density; + mPagingTouchSlop = ViewConfiguration.get(mContext).getScaledPagingTouchSlop(); + } + private void setOverScrollEffectPadding(int leftPadding, int i) { // TODO Add to (Vertical)ScrollView }