137c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chung/* 237c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chung * Copyright (C) 2014 The Android Open Source Project 337c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chung * 437c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chung * Licensed under the Apache License, Version 2.0 (the "License"); 537c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chung * you may not use this file except in compliance with the License. 637c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chung * You may obtain a copy of the License at 737c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chung * 8b124d5607fb6bdfcc9e6c2e9ae24cadaf7f0b55bPeter Schiller * http://www.apache.org/licenses/LICENSE-2.0 937c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chung * 1037c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chung * Unless required by applicable law or agreed to in writing, software 1137c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chung * distributed under the License is distributed on an "AS IS" BASIS, 1237c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chung * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 1337c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chung * See the License for the specific language governing permissions and 1437c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chung * limitations under the License. 1537c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chung */ 1637c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chung 1737c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chungpackage com.android.systemui.recents.views; 1837c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chung 19c5ef63f4e95329158d88a6cbb05789b57098222dWinsonimport android.animation.Animator; 20c5ef63f4e95329158d88a6cbb05789b57098222dWinsonimport android.animation.AnimatorListenerAdapter; 2194a0e89adb30b050f4b3319d93753b34d48e8490Winsonimport android.annotation.Nullable; 22c5ef63f4e95329158d88a6cbb05789b57098222dWinsonimport android.content.ComponentName; 2337c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chungimport android.content.Context; 24c5ef63f4e95329158d88a6cbb05789b57098222dWinsonimport android.content.pm.ActivityInfo; 2594a0e89adb30b050f4b3319d93753b34d48e8490Winsonimport android.content.res.Resources; 26cd23c849afefe58b213d5abb1c581f15d3ad543aWinson Chungimport android.graphics.Canvas; 27a0e88b5013d708ac6ed6518817d83c64c87ae4b1Winson Chungimport android.graphics.Color; 2894a0e89adb30b050f4b3319d93753b34d48e8490Winsonimport android.graphics.ColorFilter; 29cd23c849afefe58b213d5abb1c581f15d3ad543aWinson Chungimport android.graphics.Paint; 3094a0e89adb30b050f4b3319d93753b34d48e8490Winsonimport android.graphics.PixelFormat; 31c5ef63f4e95329158d88a6cbb05789b57098222dWinsonimport android.graphics.PorterDuff; 328aa7d161a11965cd75eace74e1bcf15421bbea18Skuhneimport android.graphics.Rect; 3335f3050959e43bf378f9a0adcaef13729206c7e4Winsonimport android.graphics.drawable.Drawable; 3418227e483167c590121fd300d03c999dd057204cWinsonimport android.graphics.drawable.RippleDrawable; 35b124d5607fb6bdfcc9e6c2e9ae24cadaf7f0b55bPeter Schillerimport android.os.CountDownTimer; 36c5ef63f4e95329158d88a6cbb05789b57098222dWinsonimport android.support.v4.graphics.ColorUtils; 3737c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chungimport android.util.AttributeSet; 38217009356efa2b854ab3981dff8d315a0d679c73Winsonimport android.view.Gravity; 39d42a6cfe2bf632222617450a1ed340268e82f06cWinson Chungimport android.view.View; 40c5ef63f4e95329158d88a6cbb05789b57098222dWinsonimport android.view.ViewAnimationUtils; 41231bc9c54a48921f9c6a1ae187969c9bfe9d121fWinsonimport android.view.ViewDebug; 42217009356efa2b854ab3981dff8d315a0d679c73Winsonimport android.view.ViewGroup; 4337c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chungimport android.widget.FrameLayout; 4437c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chungimport android.widget.ImageView; 45b124d5607fb6bdfcc9e6c2e9ae24cadaf7f0b55bPeter Schillerimport android.widget.ProgressBar; 4637c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chungimport android.widget.TextView; 47c0d7058b14c24cd07912f5629c26b39b7b4673d5Winson 482536c7ed446203ea12b38cf05a88e603f8d1b768Winsonimport com.android.internal.logging.MetricsLogger; 49c0d7058b14c24cd07912f5629c26b39b7b4673d5Winsonimport com.android.systemui.Interpolators; 5037c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chungimport com.android.systemui.R; 51f5e22e71cb5f8699a4312c797af068f655cbe629Winson Chungimport com.android.systemui.recents.Constants; 52e7f138c7f0a190c86cec10fb32fa106aacae4093Winsonimport com.android.systemui.recents.Recents; 532536c7ed446203ea12b38cf05a88e603f8d1b768Winsonimport com.android.systemui.recents.events.EventBus; 5448f2cda829ddb761697a0efb0cad42a62480c130Winson Chungimport com.android.systemui.recents.events.activity.LaunchTaskEvent; 552536c7ed446203ea12b38cf05a88e603f8d1b768Winsonimport com.android.systemui.recents.events.ui.ShowApplicationInfoEvent; 568aa7d161a11965cd75eace74e1bcf15421bbea18Skuhneimport com.android.systemui.recents.misc.SystemServicesProxy; 57a0e88b5013d708ac6ed6518817d83c64c87ae4b1Winson Chungimport com.android.systemui.recents.misc.Utilities; 5837c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chungimport com.android.systemui.recents.model.Task; 5937c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chung 6048f2cda829ddb761697a0efb0cad42a62480c130Winson Chungimport static android.app.ActivityManager.StackId.FREEFORM_WORKSPACE_STACK_ID; 6148f2cda829ddb761697a0efb0cad42a62480c130Winson Chungimport static android.app.ActivityManager.StackId.FULLSCREEN_WORKSPACE_STACK_ID; 6248f2cda829ddb761697a0efb0cad42a62480c130Winson Chungimport static android.app.ActivityManager.StackId.INVALID_STACK_ID; 6348f2cda829ddb761697a0efb0cad42a62480c130Winson Chung 6437c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chung/* The task bar view */ 652536c7ed446203ea12b38cf05a88e603f8d1b768Winsonpublic class TaskViewHeader extends FrameLayout 662536c7ed446203ea12b38cf05a88e603f8d1b768Winson implements View.OnClickListener, View.OnLongClickListener { 67d42a6cfe2bf632222617450a1ed340268e82f06cWinson Chung 6812858a6eaea8ae85e7244bd904e1e31291ceea3cWinson private static final float HIGHLIGHT_LIGHTNESS_INCREMENT = 0.075f; 69c5ef63f4e95329158d88a6cbb05789b57098222dWinson private static final float OVERLAY_LIGHTNESS_INCREMENT = -0.0625f; 70c5ef63f4e95329158d88a6cbb05789b57098222dWinson private static final int OVERLAY_REVEAL_DURATION = 250; 71b124d5607fb6bdfcc9e6c2e9ae24cadaf7f0b55bPeter Schiller private static final long FOCUS_INDICATOR_INTERVAL_MS = 30; 7294a0e89adb30b050f4b3319d93753b34d48e8490Winson 7394a0e89adb30b050f4b3319d93753b34d48e8490Winson /** 7494a0e89adb30b050f4b3319d93753b34d48e8490Winson * A color drawable that draws a slight highlight at the top to help it stand out. 7594a0e89adb30b050f4b3319d93753b34d48e8490Winson */ 7694a0e89adb30b050f4b3319d93753b34d48e8490Winson private class HighlightColorDrawable extends Drawable { 7794a0e89adb30b050f4b3319d93753b34d48e8490Winson 7894a0e89adb30b050f4b3319d93753b34d48e8490Winson private Paint mHighlightPaint = new Paint(); 7994a0e89adb30b050f4b3319d93753b34d48e8490Winson private Paint mBackgroundPaint = new Paint(); 808be1634a543022bd6ee0c1e974d3201d452981e8Winson private int mColor; 818be1634a543022bd6ee0c1e974d3201d452981e8Winson private float mDimAlpha; 8294a0e89adb30b050f4b3319d93753b34d48e8490Winson 8394a0e89adb30b050f4b3319d93753b34d48e8490Winson public HighlightColorDrawable() { 8494a0e89adb30b050f4b3319d93753b34d48e8490Winson mBackgroundPaint.setColor(Color.argb(255, 0, 0, 0)); 8594a0e89adb30b050f4b3319d93753b34d48e8490Winson mBackgroundPaint.setAntiAlias(true); 8694a0e89adb30b050f4b3319d93753b34d48e8490Winson mHighlightPaint.setColor(Color.argb(255, 255, 255, 255)); 8794a0e89adb30b050f4b3319d93753b34d48e8490Winson mHighlightPaint.setAntiAlias(true); 8894a0e89adb30b050f4b3319d93753b34d48e8490Winson } 8994a0e89adb30b050f4b3319d93753b34d48e8490Winson 9094a0e89adb30b050f4b3319d93753b34d48e8490Winson public void setColorAndDim(int color, float dimAlpha) { 918be1634a543022bd6ee0c1e974d3201d452981e8Winson if (mColor != color || Float.compare(mDimAlpha, dimAlpha) != 0) { 928be1634a543022bd6ee0c1e974d3201d452981e8Winson mColor = color; 938be1634a543022bd6ee0c1e974d3201d452981e8Winson mDimAlpha = dimAlpha; 948be1634a543022bd6ee0c1e974d3201d452981e8Winson mBackgroundPaint.setColor(color); 958be1634a543022bd6ee0c1e974d3201d452981e8Winson 968be1634a543022bd6ee0c1e974d3201d452981e8Winson ColorUtils.colorToHSL(color, mTmpHSL); 978be1634a543022bd6ee0c1e974d3201d452981e8Winson // TODO: Consider using the saturation of the color to adjust the lightness as well 988be1634a543022bd6ee0c1e974d3201d452981e8Winson mTmpHSL[2] = Math.min(1f, 998be1634a543022bd6ee0c1e974d3201d452981e8Winson mTmpHSL[2] + HIGHLIGHT_LIGHTNESS_INCREMENT * (1.0f - dimAlpha)); 1008be1634a543022bd6ee0c1e974d3201d452981e8Winson mHighlightPaint.setColor(ColorUtils.HSLToColor(mTmpHSL)); 1018be1634a543022bd6ee0c1e974d3201d452981e8Winson 1028be1634a543022bd6ee0c1e974d3201d452981e8Winson invalidateSelf(); 1038be1634a543022bd6ee0c1e974d3201d452981e8Winson } 10494a0e89adb30b050f4b3319d93753b34d48e8490Winson } 10594a0e89adb30b050f4b3319d93753b34d48e8490Winson 10694a0e89adb30b050f4b3319d93753b34d48e8490Winson @Override 10794a0e89adb30b050f4b3319d93753b34d48e8490Winson public void setColorFilter(@Nullable ColorFilter colorFilter) { 10894a0e89adb30b050f4b3319d93753b34d48e8490Winson // Do nothing 10994a0e89adb30b050f4b3319d93753b34d48e8490Winson } 11094a0e89adb30b050f4b3319d93753b34d48e8490Winson 11194a0e89adb30b050f4b3319d93753b34d48e8490Winson @Override 11294a0e89adb30b050f4b3319d93753b34d48e8490Winson public void setAlpha(int alpha) { 11394a0e89adb30b050f4b3319d93753b34d48e8490Winson // Do nothing 11494a0e89adb30b050f4b3319d93753b34d48e8490Winson } 11594a0e89adb30b050f4b3319d93753b34d48e8490Winson 11694a0e89adb30b050f4b3319d93753b34d48e8490Winson @Override 11794a0e89adb30b050f4b3319d93753b34d48e8490Winson public void draw(Canvas canvas) { 11894a0e89adb30b050f4b3319d93753b34d48e8490Winson // Draw the highlight at the top edge (but put the bottom edge just out of view) 11994a0e89adb30b050f4b3319d93753b34d48e8490Winson canvas.drawRoundRect(0, 0, mTaskViewRect.width(), 12094a0e89adb30b050f4b3319d93753b34d48e8490Winson 2 * Math.max(mHighlightHeight, mCornerRadius), 12194a0e89adb30b050f4b3319d93753b34d48e8490Winson mCornerRadius, mCornerRadius, mHighlightPaint); 12294a0e89adb30b050f4b3319d93753b34d48e8490Winson 12394a0e89adb30b050f4b3319d93753b34d48e8490Winson // Draw the background with the rounded corners 12494a0e89adb30b050f4b3319d93753b34d48e8490Winson canvas.drawRoundRect(0, mHighlightHeight, mTaskViewRect.width(), 12594a0e89adb30b050f4b3319d93753b34d48e8490Winson getHeight() + mCornerRadius, 12694a0e89adb30b050f4b3319d93753b34d48e8490Winson mCornerRadius, mCornerRadius, mBackgroundPaint); 12794a0e89adb30b050f4b3319d93753b34d48e8490Winson } 12894a0e89adb30b050f4b3319d93753b34d48e8490Winson 12994a0e89adb30b050f4b3319d93753b34d48e8490Winson @Override 13094a0e89adb30b050f4b3319d93753b34d48e8490Winson public int getOpacity() { 13194a0e89adb30b050f4b3319d93753b34d48e8490Winson return PixelFormat.OPAQUE; 13294a0e89adb30b050f4b3319d93753b34d48e8490Winson } 1338be1634a543022bd6ee0c1e974d3201d452981e8Winson 1348be1634a543022bd6ee0c1e974d3201d452981e8Winson public int getColor() { 1358be1634a543022bd6ee0c1e974d3201d452981e8Winson return mColor; 1368be1634a543022bd6ee0c1e974d3201d452981e8Winson } 13794a0e89adb30b050f4b3319d93753b34d48e8490Winson } 13894a0e89adb30b050f4b3319d93753b34d48e8490Winson 1392536c7ed446203ea12b38cf05a88e603f8d1b768Winson Task mTask; 140d42a6cfe2bf632222617450a1ed340268e82f06cWinson Chung 141353c0b91daa97fa87f077be0f403fe7db8dedb40Winson Chung // Header views 142296278a0679375b8c43962a9e3c9bb4e8ab201e7Winson Chung ImageView mIconView; 143296278a0679375b8c43962a9e3c9bb4e8ab201e7Winson Chung TextView mTitleView; 144c5ef63f4e95329158d88a6cbb05789b57098222dWinson ImageView mMoveTaskButton; 145c5ef63f4e95329158d88a6cbb05789b57098222dWinson ImageView mDismissButton; 146c5ef63f4e95329158d88a6cbb05789b57098222dWinson FrameLayout mAppOverlayView; 147c5ef63f4e95329158d88a6cbb05789b57098222dWinson ImageView mAppIconView; 148c5ef63f4e95329158d88a6cbb05789b57098222dWinson ImageView mAppInfoView; 149c5ef63f4e95329158d88a6cbb05789b57098222dWinson TextView mAppTitleView; 150b124d5607fb6bdfcc9e6c2e9ae24cadaf7f0b55bPeter Schiller ProgressBar mFocusTimerIndicator; 15137c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chung 152353c0b91daa97fa87f077be0f403fe7db8dedb40Winson Chung // Header drawables 153231bc9c54a48921f9c6a1ae187969c9bfe9d121fWinson @ViewDebug.ExportedProperty(category="recents") 154de0591a0788c96757cce1eed93a7e8bc8bd0ef01Winson Rect mTaskViewRect = new Rect(); 155217009356efa2b854ab3981dff8d315a0d679c73Winson int mHeaderBarHeight; 156217009356efa2b854ab3981dff8d315a0d679c73Winson int mHeaderButtonPadding; 15735f3050959e43bf378f9a0adcaef13729206c7e4Winson int mCornerRadius; 15835f3050959e43bf378f9a0adcaef13729206c7e4Winson int mHighlightHeight; 159231bc9c54a48921f9c6a1ae187969c9bfe9d121fWinson @ViewDebug.ExportedProperty(category="recents") 16094a0e89adb30b050f4b3319d93753b34d48e8490Winson float mDimAlpha; 16154e297a5bb143e60e29fd7dfe87e04a8cc96c72cWinson Chung Drawable mLightDismissDrawable; 16254e297a5bb143e60e29fd7dfe87e04a8cc96c72cWinson Chung Drawable mDarkDismissDrawable; 1633e8747414520ee348cf4b9c4a6afd9ff80b5a8f8Winson Drawable mLightFreeformIcon; 1643e8747414520ee348cf4b9c4a6afd9ff80b5a8f8Winson Drawable mDarkFreeformIcon; 1653e8747414520ee348cf4b9c4a6afd9ff80b5a8f8Winson Drawable mLightFullscreenIcon; 1663e8747414520ee348cf4b9c4a6afd9ff80b5a8f8Winson Drawable mDarkFullscreenIcon; 167c5ef63f4e95329158d88a6cbb05789b57098222dWinson Drawable mLightInfoIcon; 168c5ef63f4e95329158d88a6cbb05789b57098222dWinson Drawable mDarkInfoIcon; 16994a0e89adb30b050f4b3319d93753b34d48e8490Winson int mTaskBarViewLightTextColor; 17094a0e89adb30b050f4b3319d93753b34d48e8490Winson int mTaskBarViewDarkTextColor; 1718be1634a543022bd6ee0c1e974d3201d452981e8Winson int mDisabledTaskBarBackgroundColor; 172c5ef63f4e95329158d88a6cbb05789b57098222dWinson int mMoveTaskTargetStackId = INVALID_STACK_ID; 173dcfa7976fa836ae90bb4a579892a18a0abf35b3cWinson Chung 17494a0e89adb30b050f4b3319d93753b34d48e8490Winson // Header background 17594a0e89adb30b050f4b3319d93753b34d48e8490Winson private HighlightColorDrawable mBackground; 176c5ef63f4e95329158d88a6cbb05789b57098222dWinson private HighlightColorDrawable mOverlayBackground; 177c5ef63f4e95329158d88a6cbb05789b57098222dWinson private float[] mTmpHSL = new float[3]; 178353c0b91daa97fa87f077be0f403fe7db8dedb40Winson Chung 179353c0b91daa97fa87f077be0f403fe7db8dedb40Winson Chung // Header dim, which is only used when task view hardware layers are not used 18094a0e89adb30b050f4b3319d93753b34d48e8490Winson private Paint mDimLayerPaint = new Paint(); 181cd23c849afefe58b213d5abb1c581f15d3ad543aWinson Chung 182b124d5607fb6bdfcc9e6c2e9ae24cadaf7f0b55bPeter Schiller private CountDownTimer mFocusTimerCountDown; 183b124d5607fb6bdfcc9e6c2e9ae24cadaf7f0b55bPeter Schiller 184ec396d6399c5c31d697d81e94aff459e9771b0c6Winson Chung public TaskViewHeader(Context context) { 18537c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chung this(context, null); 18637c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chung } 18737c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chung 188ec396d6399c5c31d697d81e94aff459e9771b0c6Winson Chung public TaskViewHeader(Context context, AttributeSet attrs) { 18937c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chung this(context, attrs, 0); 19037c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chung } 19137c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chung 192ec396d6399c5c31d697d81e94aff459e9771b0c6Winson Chung public TaskViewHeader(Context context, AttributeSet attrs, int defStyleAttr) { 19337c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chung this(context, attrs, defStyleAttr, 0); 19437c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chung } 19537c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chung 196ec396d6399c5c31d697d81e94aff459e9771b0c6Winson Chung public TaskViewHeader(Context context, AttributeSet attrs, int defStyleAttr, int defStyleRes) { 19737c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chung super(context, attrs, defStyleAttr, defStyleRes); 198cd23c849afefe58b213d5abb1c581f15d3ad543aWinson Chung setWillNotDraw(false); 199cd23c849afefe58b213d5abb1c581f15d3ad543aWinson Chung 200cd23c849afefe58b213d5abb1c581f15d3ad543aWinson Chung // Load the dismiss resources 20194a0e89adb30b050f4b3319d93753b34d48e8490Winson Resources res = context.getResources(); 202911f400c2eab4eb15e0491a2affd918901867d2eWinson Chung mLightDismissDrawable = context.getDrawable(R.drawable.recents_dismiss_light); 203911f400c2eab4eb15e0491a2affd918901867d2eWinson Chung mDarkDismissDrawable = context.getDrawable(R.drawable.recents_dismiss_dark); 20494a0e89adb30b050f4b3319d93753b34d48e8490Winson mCornerRadius = res.getDimensionPixelSize(R.dimen.recents_task_view_rounded_corners_radius); 20594a0e89adb30b050f4b3319d93753b34d48e8490Winson mHighlightHeight = res.getDimensionPixelSize(R.dimen.recents_task_view_highlight); 20694a0e89adb30b050f4b3319d93753b34d48e8490Winson mTaskBarViewLightTextColor = context.getColor(R.color.recents_task_bar_light_text_color); 20794a0e89adb30b050f4b3319d93753b34d48e8490Winson mTaskBarViewDarkTextColor = context.getColor(R.color.recents_task_bar_dark_text_color); 2083e8747414520ee348cf4b9c4a6afd9ff80b5a8f8Winson mLightFreeformIcon = context.getDrawable(R.drawable.recents_move_task_freeform_light); 2093e8747414520ee348cf4b9c4a6afd9ff80b5a8f8Winson mDarkFreeformIcon = context.getDrawable(R.drawable.recents_move_task_freeform_dark); 2103e8747414520ee348cf4b9c4a6afd9ff80b5a8f8Winson mLightFullscreenIcon = context.getDrawable(R.drawable.recents_move_task_fullscreen_light); 2113e8747414520ee348cf4b9c4a6afd9ff80b5a8f8Winson mDarkFullscreenIcon = context.getDrawable(R.drawable.recents_move_task_fullscreen_dark); 212c5ef63f4e95329158d88a6cbb05789b57098222dWinson mLightInfoIcon = context.getDrawable(R.drawable.recents_info_light); 213c5ef63f4e95329158d88a6cbb05789b57098222dWinson mDarkInfoIcon = context.getDrawable(R.drawable.recents_info_dark); 2148be1634a543022bd6ee0c1e974d3201d452981e8Winson mDisabledTaskBarBackgroundColor = 2158be1634a543022bd6ee0c1e974d3201d452981e8Winson context.getColor(R.color.recents_task_bar_disabled_background_color); 2163e8747414520ee348cf4b9c4a6afd9ff80b5a8f8Winson 21794a0e89adb30b050f4b3319d93753b34d48e8490Winson // Configure the background and dim 21894a0e89adb30b050f4b3319d93753b34d48e8490Winson mBackground = new HighlightColorDrawable(); 21994a0e89adb30b050f4b3319d93753b34d48e8490Winson mBackground.setColorAndDim(Color.argb(255, 0, 0, 0), 0f); 22094a0e89adb30b050f4b3319d93753b34d48e8490Winson setBackground(mBackground); 221c5ef63f4e95329158d88a6cbb05789b57098222dWinson mOverlayBackground = new HighlightColorDrawable(); 22294a0e89adb30b050f4b3319d93753b34d48e8490Winson mDimLayerPaint.setColor(Color.argb(255, 0, 0, 0)); 22394a0e89adb30b050f4b3319d93753b34d48e8490Winson mDimLayerPaint.setAntiAlias(true); 22437c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chung } 22537c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chung 226c5ef63f4e95329158d88a6cbb05789b57098222dWinson /** 227c5ef63f4e95329158d88a6cbb05789b57098222dWinson * Resets this header along with the TaskView. 228c5ef63f4e95329158d88a6cbb05789b57098222dWinson */ 229c5ef63f4e95329158d88a6cbb05789b57098222dWinson public void reset() { 230c5ef63f4e95329158d88a6cbb05789b57098222dWinson hideAppOverlay(true /* immediate */); 231c5ef63f4e95329158d88a6cbb05789b57098222dWinson } 232c5ef63f4e95329158d88a6cbb05789b57098222dWinson 23337c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chung @Override 23437c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chung protected void onFinishInflate() { 235bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung SystemServicesProxy ssp = Recents.getSystemServices(); 236bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung 23737c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chung // Initialize the icon and description views 238296278a0679375b8c43962a9e3c9bb4e8ab201e7Winson Chung mIconView = (ImageView) findViewById(R.id.icon); 239296278a0679375b8c43962a9e3c9bb4e8ab201e7Winson Chung mIconView.setOnLongClickListener(this); 240296278a0679375b8c43962a9e3c9bb4e8ab201e7Winson Chung mTitleView = (TextView) findViewById(R.id.title); 24154e297a5bb143e60e29fd7dfe87e04a8cc96c72cWinson Chung mDismissButton = (ImageView) findViewById(R.id.dismiss_task); 242bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung if (ssp.hasFreeformWorkspaceSupport()) { 243bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung mMoveTaskButton = (ImageView) findViewById(R.id.move_task); 244bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung } 245217009356efa2b854ab3981dff8d315a0d679c73Winson 246619e40cd56266a362ab7da80cb9e4eba6c33b204Winson onConfigurationChanged(); 247217009356efa2b854ab3981dff8d315a0d679c73Winson } 248217009356efa2b854ab3981dff8d315a0d679c73Winson 249217009356efa2b854ab3981dff8d315a0d679c73Winson /** 250217009356efa2b854ab3981dff8d315a0d679c73Winson * Programmatically sets the layout params for a header bar layout. This is necessary because 251217009356efa2b854ab3981dff8d315a0d679c73Winson * we can't get resources based on the current configuration, but instead need to get them 252217009356efa2b854ab3981dff8d315a0d679c73Winson * based on the device configuration. 253217009356efa2b854ab3981dff8d315a0d679c73Winson */ 254217009356efa2b854ab3981dff8d315a0d679c73Winson private void updateLayoutParams(View icon, View title, View secondaryButton, View button) { 255217009356efa2b854ab3981dff8d315a0d679c73Winson FrameLayout.LayoutParams lp = new FrameLayout.LayoutParams( 256217009356efa2b854ab3981dff8d315a0d679c73Winson ViewGroup.LayoutParams.MATCH_PARENT, mHeaderBarHeight, Gravity.TOP); 257217009356efa2b854ab3981dff8d315a0d679c73Winson setLayoutParams(lp); 258217009356efa2b854ab3981dff8d315a0d679c73Winson lp = new FrameLayout.LayoutParams(mHeaderBarHeight, mHeaderBarHeight, Gravity.START); 259217009356efa2b854ab3981dff8d315a0d679c73Winson icon.setLayoutParams(lp); 260217009356efa2b854ab3981dff8d315a0d679c73Winson lp = new FrameLayout.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, 261217009356efa2b854ab3981dff8d315a0d679c73Winson ViewGroup.LayoutParams.WRAP_CONTENT, Gravity.START | Gravity.CENTER_VERTICAL); 262a1ededd056d51532ab18354f17f8065ec1134535Winson lp.setMarginStart(mHeaderBarHeight); 263198523763af21c49d1d2c71fb65c1f7da356712bWinson lp.setMarginEnd(mMoveTaskButton != null 264217009356efa2b854ab3981dff8d315a0d679c73Winson ? 2 * mHeaderBarHeight 265198523763af21c49d1d2c71fb65c1f7da356712bWinson : mHeaderBarHeight); 266217009356efa2b854ab3981dff8d315a0d679c73Winson title.setLayoutParams(lp); 267217009356efa2b854ab3981dff8d315a0d679c73Winson if (secondaryButton != null) { 268217009356efa2b854ab3981dff8d315a0d679c73Winson lp = new FrameLayout.LayoutParams(mHeaderBarHeight, mHeaderBarHeight, Gravity.END); 269a1ededd056d51532ab18354f17f8065ec1134535Winson lp.setMarginEnd(mHeaderBarHeight); 270217009356efa2b854ab3981dff8d315a0d679c73Winson secondaryButton.setLayoutParams(lp); 271217009356efa2b854ab3981dff8d315a0d679c73Winson secondaryButton.setPadding(mHeaderButtonPadding, mHeaderButtonPadding, 272217009356efa2b854ab3981dff8d315a0d679c73Winson mHeaderButtonPadding, mHeaderButtonPadding); 273217009356efa2b854ab3981dff8d315a0d679c73Winson } 274217009356efa2b854ab3981dff8d315a0d679c73Winson lp = new FrameLayout.LayoutParams(mHeaderBarHeight, mHeaderBarHeight, Gravity.END); 275217009356efa2b854ab3981dff8d315a0d679c73Winson button.setLayoutParams(lp); 276217009356efa2b854ab3981dff8d315a0d679c73Winson button.setPadding(mHeaderButtonPadding, mHeaderButtonPadding, mHeaderButtonPadding, 277217009356efa2b854ab3981dff8d315a0d679c73Winson mHeaderButtonPadding); 27854e297a5bb143e60e29fd7dfe87e04a8cc96c72cWinson Chung } 27954e297a5bb143e60e29fd7dfe87e04a8cc96c72cWinson Chung 280619e40cd56266a362ab7da80cb9e4eba6c33b204Winson /** 281619e40cd56266a362ab7da80cb9e4eba6c33b204Winson * Update the header view when the configuration changes. 282619e40cd56266a362ab7da80cb9e4eba6c33b204Winson */ 283670ea71f1b4ae59a0cd6608ae44b0fb78a1144c4Winson public void onConfigurationChanged() { 284619e40cd56266a362ab7da80cb9e4eba6c33b204Winson // Update the dimensions of everything in the header. We do this because we need to use 285619e40cd56266a362ab7da80cb9e4eba6c33b204Winson // resources for the display, and not the current configuration. 286619e40cd56266a362ab7da80cb9e4eba6c33b204Winson Resources res = getResources(); 28725160db73f37619a26a3d87a06625925d881b0fdJorim Jaggi int headerBarHeight = TaskStackLayoutAlgorithm.getDimensionForDevice(getContext(), 288619e40cd56266a362ab7da80cb9e4eba6c33b204Winson R.dimen.recents_task_view_header_height, 289619e40cd56266a362ab7da80cb9e4eba6c33b204Winson R.dimen.recents_task_view_header_height, 290619e40cd56266a362ab7da80cb9e4eba6c33b204Winson R.dimen.recents_task_view_header_height, 291619e40cd56266a362ab7da80cb9e4eba6c33b204Winson R.dimen.recents_task_view_header_height_tablet_land, 292619e40cd56266a362ab7da80cb9e4eba6c33b204Winson R.dimen.recents_task_view_header_height, 293619e40cd56266a362ab7da80cb9e4eba6c33b204Winson R.dimen.recents_task_view_header_height_tablet_land); 29425160db73f37619a26a3d87a06625925d881b0fdJorim Jaggi int headerButtonPadding = TaskStackLayoutAlgorithm.getDimensionForDevice(getContext(), 295619e40cd56266a362ab7da80cb9e4eba6c33b204Winson R.dimen.recents_task_view_header_button_padding, 296619e40cd56266a362ab7da80cb9e4eba6c33b204Winson R.dimen.recents_task_view_header_button_padding, 297619e40cd56266a362ab7da80cb9e4eba6c33b204Winson R.dimen.recents_task_view_header_button_padding, 298619e40cd56266a362ab7da80cb9e4eba6c33b204Winson R.dimen.recents_task_view_header_button_padding_tablet_land, 299619e40cd56266a362ab7da80cb9e4eba6c33b204Winson R.dimen.recents_task_view_header_button_padding, 300619e40cd56266a362ab7da80cb9e4eba6c33b204Winson R.dimen.recents_task_view_header_button_padding_tablet_land); 301670ea71f1b4ae59a0cd6608ae44b0fb78a1144c4Winson if (headerBarHeight != mHeaderBarHeight || headerButtonPadding != mHeaderButtonPadding) { 302670ea71f1b4ae59a0cd6608ae44b0fb78a1144c4Winson mHeaderBarHeight = headerBarHeight; 303670ea71f1b4ae59a0cd6608ae44b0fb78a1144c4Winson mHeaderButtonPadding = headerButtonPadding; 304670ea71f1b4ae59a0cd6608ae44b0fb78a1144c4Winson updateLayoutParams(mIconView, mTitleView, mMoveTaskButton, mDismissButton); 305670ea71f1b4ae59a0cd6608ae44b0fb78a1144c4Winson if (mAppOverlayView != null) { 306670ea71f1b4ae59a0cd6608ae44b0fb78a1144c4Winson updateLayoutParams(mAppIconView, mAppTitleView, null, mAppInfoView); 307670ea71f1b4ae59a0cd6608ae44b0fb78a1144c4Winson } 308619e40cd56266a362ab7da80cb9e4eba6c33b204Winson } 309619e40cd56266a362ab7da80cb9e4eba6c33b204Winson } 310619e40cd56266a362ab7da80cb9e4eba6c33b204Winson 311bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung @Override 312bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung protected void onLayout(boolean changed, int left, int top, int right, int bottom) { 313bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung super.onLayout(changed, left, top, right, bottom); 314bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung 315bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung // Since we update the position of children based on the width of the parent and this view 316bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung // recompute these changes with the new view size 317bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung onTaskViewSizeChanged(mTaskViewRect.width(), mTaskViewRect.height()); 318bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung } 319bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung 320de0591a0788c96757cce1eed93a7e8bc8bd0ef01Winson /** 321de0591a0788c96757cce1eed93a7e8bc8bd0ef01Winson * Called when the task view frame changes, allowing us to move the contents of the header 322de0591a0788c96757cce1eed93a7e8bc8bd0ef01Winson * to match the frame changes. 323de0591a0788c96757cce1eed93a7e8bc8bd0ef01Winson */ 324de0591a0788c96757cce1eed93a7e8bc8bd0ef01Winson public void onTaskViewSizeChanged(int width, int height) { 325de0591a0788c96757cce1eed93a7e8bc8bd0ef01Winson mTaskViewRect.set(0, 0, width, height); 326bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung 327bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung boolean showTitle = true; 328bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung boolean showMoveIcon = true; 329bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung boolean showDismissIcon = true; 330bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung int rightInset = width - getMeasuredWidth(); 331bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung 332bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung if (mTask != null && mTask.isFreeformTask()) { 333bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung // For freeform tasks, we always show the app icon, and only show the title, move-task 334bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung // icon, and the dismiss icon if there is room 335bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung int appIconWidth = mIconView.getMeasuredWidth(); 336bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung int titleWidth = (int) mTitleView.getPaint().measureText(mTask.title); 337bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung int dismissWidth = mDismissButton.getMeasuredWidth(); 338bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung int moveTaskWidth = mMoveTaskButton != null 339bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung ? mMoveTaskButton.getMeasuredWidth() 340bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung : 0; 341bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung showTitle = width >= (appIconWidth + dismissWidth + moveTaskWidth + titleWidth); 342bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung showMoveIcon = width >= (appIconWidth + dismissWidth + moveTaskWidth); 343bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung showDismissIcon = width >= (appIconWidth + dismissWidth); 344de0591a0788c96757cce1eed93a7e8bc8bd0ef01Winson } 345bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung 346bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung mTitleView.setVisibility(showTitle ? View.VISIBLE : View.INVISIBLE); 347bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung if (mMoveTaskButton != null) { 348bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung mMoveTaskButton.setVisibility(showMoveIcon ? View.VISIBLE : View.INVISIBLE); 349bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung mMoveTaskButton.setTranslationX(rightInset); 350de0591a0788c96757cce1eed93a7e8bc8bd0ef01Winson } 351bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung mDismissButton.setVisibility(showDismissIcon ? View.VISIBLE : View.INVISIBLE); 352bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung mDismissButton.setTranslationX(rightInset); 35367c79578f94646bade5d336af0d4491179c1b37dWinson 35467c79578f94646bade5d336af0d4491179c1b37dWinson setLeftTopRightBottom(0, 0, width, getMeasuredHeight()); 355de0591a0788c96757cce1eed93a7e8bc8bd0ef01Winson } 356de0591a0788c96757cce1eed93a7e8bc8bd0ef01Winson 357cd23c849afefe58b213d5abb1c581f15d3ad543aWinson Chung @Override 358be8e696a1f40a61c52a74022f4f084fdc0600f90Winson public void onDrawForeground(Canvas canvas) { 359be8e696a1f40a61c52a74022f4f084fdc0600f90Winson super.onDrawForeground(canvas); 36094a0e89adb30b050f4b3319d93753b34d48e8490Winson 36194a0e89adb30b050f4b3319d93753b34d48e8490Winson // Draw the dim layer with the rounded corners 36294a0e89adb30b050f4b3319d93753b34d48e8490Winson canvas.drawRoundRect(0, 0, mTaskViewRect.width(), getHeight() + mCornerRadius, 36394a0e89adb30b050f4b3319d93753b34d48e8490Winson mCornerRadius, mCornerRadius, mDimLayerPaint); 364cd23c849afefe58b213d5abb1c581f15d3ad543aWinson Chung } 365cd23c849afefe58b213d5abb1c581f15d3ad543aWinson Chung 366b124d5607fb6bdfcc9e6c2e9ae24cadaf7f0b55bPeter Schiller /** Starts the focus timer. */ 3674b9cded14346a7d8781ee6549c44888eb4ec9d83Winson public void startFocusTimerIndicator(int duration) { 368c5ef63f4e95329158d88a6cbb05789b57098222dWinson if (mFocusTimerIndicator == null) { 369c5ef63f4e95329158d88a6cbb05789b57098222dWinson return; 370c5ef63f4e95329158d88a6cbb05789b57098222dWinson } 371c5ef63f4e95329158d88a6cbb05789b57098222dWinson 372b124d5607fb6bdfcc9e6c2e9ae24cadaf7f0b55bPeter Schiller mFocusTimerIndicator.setVisibility(View.VISIBLE); 3734b9cded14346a7d8781ee6549c44888eb4ec9d83Winson mFocusTimerIndicator.setMax(duration); 3744b9cded14346a7d8781ee6549c44888eb4ec9d83Winson mFocusTimerIndicator.setProgress(duration); 3754b9cded14346a7d8781ee6549c44888eb4ec9d83Winson if (mFocusTimerCountDown != null) { 3764b9cded14346a7d8781ee6549c44888eb4ec9d83Winson mFocusTimerCountDown.cancel(); 377b124d5607fb6bdfcc9e6c2e9ae24cadaf7f0b55bPeter Schiller } 3784b9cded14346a7d8781ee6549c44888eb4ec9d83Winson mFocusTimerCountDown = new CountDownTimer(duration, 3794b9cded14346a7d8781ee6549c44888eb4ec9d83Winson FOCUS_INDICATOR_INTERVAL_MS) { 3804b9cded14346a7d8781ee6549c44888eb4ec9d83Winson public void onTick(long millisUntilFinished) { 3814b9cded14346a7d8781ee6549c44888eb4ec9d83Winson mFocusTimerIndicator.setProgress((int) millisUntilFinished); 3824b9cded14346a7d8781ee6549c44888eb4ec9d83Winson } 3834b9cded14346a7d8781ee6549c44888eb4ec9d83Winson 3844b9cded14346a7d8781ee6549c44888eb4ec9d83Winson public void onFinish() { 3854b9cded14346a7d8781ee6549c44888eb4ec9d83Winson // Do nothing 3864b9cded14346a7d8781ee6549c44888eb4ec9d83Winson } 3874b9cded14346a7d8781ee6549c44888eb4ec9d83Winson }.start(); 388b124d5607fb6bdfcc9e6c2e9ae24cadaf7f0b55bPeter Schiller } 389b124d5607fb6bdfcc9e6c2e9ae24cadaf7f0b55bPeter Schiller 390b124d5607fb6bdfcc9e6c2e9ae24cadaf7f0b55bPeter Schiller /** Cancels the focus timer. */ 391b124d5607fb6bdfcc9e6c2e9ae24cadaf7f0b55bPeter Schiller public void cancelFocusTimerIndicator() { 392c5ef63f4e95329158d88a6cbb05789b57098222dWinson if (mFocusTimerIndicator == null) { 393c5ef63f4e95329158d88a6cbb05789b57098222dWinson return; 394c5ef63f4e95329158d88a6cbb05789b57098222dWinson } 395c5ef63f4e95329158d88a6cbb05789b57098222dWinson 396c5ef63f4e95329158d88a6cbb05789b57098222dWinson if (mFocusTimerCountDown != null) { 397b124d5607fb6bdfcc9e6c2e9ae24cadaf7f0b55bPeter Schiller mFocusTimerCountDown.cancel(); 398b124d5607fb6bdfcc9e6c2e9ae24cadaf7f0b55bPeter Schiller mFocusTimerIndicator.setProgress(0); 399b124d5607fb6bdfcc9e6c2e9ae24cadaf7f0b55bPeter Schiller mFocusTimerIndicator.setVisibility(View.INVISIBLE); 400b124d5607fb6bdfcc9e6c2e9ae24cadaf7f0b55bPeter Schiller } 401b124d5607fb6bdfcc9e6c2e9ae24cadaf7f0b55bPeter Schiller } 402b124d5607fb6bdfcc9e6c2e9ae24cadaf7f0b55bPeter Schiller 40322574afa00b7e32b7c4c5a1b98deebd67751b364Winson /** Only exposed for the workaround for b/27815919. */ 40422574afa00b7e32b7c4c5a1b98deebd67751b364Winson public ImageView getIconView() { 40522574afa00b7e32b7c4c5a1b98deebd67751b364Winson return mIconView; 40622574afa00b7e32b7c4c5a1b98deebd67751b364Winson } 40722574afa00b7e32b7c4c5a1b98deebd67751b364Winson 408b124d5607fb6bdfcc9e6c2e9ae24cadaf7f0b55bPeter Schiller /** Returns the secondary color for a primary color. */ 409b124d5607fb6bdfcc9e6c2e9ae24cadaf7f0b55bPeter Schiller int getSecondaryColor(int primaryColor, boolean useLightOverlayColor) { 410b124d5607fb6bdfcc9e6c2e9ae24cadaf7f0b55bPeter Schiller int overlayColor = useLightOverlayColor ? Color.WHITE : Color.BLACK; 411b124d5607fb6bdfcc9e6c2e9ae24cadaf7f0b55bPeter Schiller return Utilities.getColorWithOverlay(primaryColor, overlayColor, 0.8f); 412b124d5607fb6bdfcc9e6c2e9ae24cadaf7f0b55bPeter Schiller } 413b124d5607fb6bdfcc9e6c2e9ae24cadaf7f0b55bPeter Schiller 414353c0b91daa97fa87f077be0f403fe7db8dedb40Winson Chung /** 415353c0b91daa97fa87f077be0f403fe7db8dedb40Winson Chung * Sets the dim alpha, only used when we are not using hardware layers. 416353c0b91daa97fa87f077be0f403fe7db8dedb40Winson Chung * (see RecentsConfiguration.useHardwareLayers) 417353c0b91daa97fa87f077be0f403fe7db8dedb40Winson Chung */ 418e693aafe0511c2a7ffc571b22abeefba44046225Winson public void setDimAlpha(float dimAlpha) { 419e693aafe0511c2a7ffc571b22abeefba44046225Winson if (Float.compare(mDimAlpha, dimAlpha) != 0) { 420e693aafe0511c2a7ffc571b22abeefba44046225Winson mDimAlpha = dimAlpha; 42159924fe0d9136cf349759bea1e06b661603f95feWinson mTitleView.setAlpha(1f - dimAlpha); 422e693aafe0511c2a7ffc571b22abeefba44046225Winson updateBackgroundColor(mBackground.getColor(), dimAlpha); 423e693aafe0511c2a7ffc571b22abeefba44046225Winson } 424353c0b91daa97fa87f077be0f403fe7db8dedb40Winson Chung } 425353c0b91daa97fa87f077be0f403fe7db8dedb40Winson Chung 42694a0e89adb30b050f4b3319d93753b34d48e8490Winson /** 42794a0e89adb30b050f4b3319d93753b34d48e8490Winson * Updates the background and highlight colors for this header. 42894a0e89adb30b050f4b3319d93753b34d48e8490Winson */ 4298be1634a543022bd6ee0c1e974d3201d452981e8Winson private void updateBackgroundColor(int color, float dimAlpha) { 43094a0e89adb30b050f4b3319d93753b34d48e8490Winson if (mTask != null) { 4318be1634a543022bd6ee0c1e974d3201d452981e8Winson mBackground.setColorAndDim(color, dimAlpha); 432c5ef63f4e95329158d88a6cbb05789b57098222dWinson // TODO: Consider using the saturation of the color to adjust the lightness as well 4338be1634a543022bd6ee0c1e974d3201d452981e8Winson ColorUtils.colorToHSL(color, mTmpHSL); 434c5ef63f4e95329158d88a6cbb05789b57098222dWinson mTmpHSL[2] = Math.min(1f, mTmpHSL[2] + OVERLAY_LIGHTNESS_INCREMENT * (1.0f - dimAlpha)); 435c5ef63f4e95329158d88a6cbb05789b57098222dWinson mOverlayBackground.setColorAndDim(ColorUtils.HSLToColor(mTmpHSL), dimAlpha); 43694a0e89adb30b050f4b3319d93753b34d48e8490Winson mDimLayerPaint.setAlpha((int) (dimAlpha * 255)); 437bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung invalidate(); 43894a0e89adb30b050f4b3319d93753b34d48e8490Winson } 43994a0e89adb30b050f4b3319d93753b34d48e8490Winson } 44094a0e89adb30b050f4b3319d93753b34d48e8490Winson 441d2a030613154e2007d9816e090c39e9726e7adbaWinson /** 442d2a030613154e2007d9816e090c39e9726e7adbaWinson * Binds the bar view to the task. 443d2a030613154e2007d9816e090c39e9726e7adbaWinson */ 444d2a030613154e2007d9816e090c39e9726e7adbaWinson public void bindToTask(Task t, boolean touchExplorationEnabled, boolean disabledInSafeMode) { 4452536c7ed446203ea12b38cf05a88e603f8d1b768Winson mTask = t; 4462536c7ed446203ea12b38cf05a88e603f8d1b768Winson 4478be1634a543022bd6ee0c1e974d3201d452981e8Winson int primaryColor = disabledInSafeMode 4488be1634a543022bd6ee0c1e974d3201d452981e8Winson ? mDisabledTaskBarBackgroundColor 4498be1634a543022bd6ee0c1e974d3201d452981e8Winson : t.colorPrimary; 450e693aafe0511c2a7ffc571b22abeefba44046225Winson if (mBackground.getColor() != primaryColor) { 451e693aafe0511c2a7ffc571b22abeefba44046225Winson updateBackgroundColor(primaryColor, mDimAlpha); 452e693aafe0511c2a7ffc571b22abeefba44046225Winson } 453296278a0679375b8c43962a9e3c9bb4e8ab201e7Winson Chung if (!mTitleView.getText().toString().equals(t.title)) { 454296278a0679375b8c43962a9e3c9bb4e8ab201e7Winson Chung mTitleView.setText(t.title); 455bdbb87dd7410dda10be04e01ec3a7e8344919293Winson Chung } 456b92dd6358180eb7e6b7a57de1efa38e16597e650Winson mTitleView.setContentDescription(t.titleDescription); 457296278a0679375b8c43962a9e3c9bb4e8ab201e7Winson Chung mTitleView.setTextColor(t.useLightOnPrimaryColor ? 45894a0e89adb30b050f4b3319d93753b34d48e8490Winson mTaskBarViewLightTextColor : mTaskBarViewDarkTextColor); 45993748a11cba1b44edbc2e888c997533461355594Winson Chung mDismissButton.setImageDrawable(t.useLightOnPrimaryColor ? 46093748a11cba1b44edbc2e888c997533461355594Winson Chung mLightDismissDrawable : mDarkDismissDrawable); 4615500390a006f2bbea565068234774a36cea076c0Winson mDismissButton.setContentDescription(t.dismissDescription); 4623e5f0af085293004b378c07d2c52e51f1b32d1a2Winson mDismissButton.setOnClickListener(this); 4633e5f0af085293004b378c07d2c52e51f1b32d1a2Winson mDismissButton.setClickable(false); 46418227e483167c590121fd300d03c999dd057204cWinson ((RippleDrawable) mDismissButton.getBackground()).setForceSoftware(true); 46548f2cda829ddb761697a0efb0cad42a62480c130Winson Chung 46648f2cda829ddb761697a0efb0cad42a62480c130Winson Chung // When freeform workspaces are enabled, then update the move-task button depending on the 46748f2cda829ddb761697a0efb0cad42a62480c130Winson Chung // current task 468bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung if (mMoveTaskButton != null) { 46948f2cda829ddb761697a0efb0cad42a62480c130Winson Chung if (t.isFreeformTask()) { 47048f2cda829ddb761697a0efb0cad42a62480c130Winson Chung mMoveTaskTargetStackId = FULLSCREEN_WORKSPACE_STACK_ID; 4713e8747414520ee348cf4b9c4a6afd9ff80b5a8f8Winson mMoveTaskButton.setImageDrawable(t.useLightOnPrimaryColor 4723e8747414520ee348cf4b9c4a6afd9ff80b5a8f8Winson ? mLightFullscreenIcon 4733e8747414520ee348cf4b9c4a6afd9ff80b5a8f8Winson : mDarkFullscreenIcon); 47448f2cda829ddb761697a0efb0cad42a62480c130Winson Chung } else { 47548f2cda829ddb761697a0efb0cad42a62480c130Winson Chung mMoveTaskTargetStackId = FREEFORM_WORKSPACE_STACK_ID; 4763e8747414520ee348cf4b9c4a6afd9ff80b5a8f8Winson mMoveTaskButton.setImageDrawable(t.useLightOnPrimaryColor 4773e8747414520ee348cf4b9c4a6afd9ff80b5a8f8Winson ? mLightFreeformIcon 4783e8747414520ee348cf4b9c4a6afd9ff80b5a8f8Winson : mDarkFreeformIcon); 47948f2cda829ddb761697a0efb0cad42a62480c130Winson Chung } 4803e5f0af085293004b378c07d2c52e51f1b32d1a2Winson mMoveTaskButton.setOnClickListener(this); 4813e5f0af085293004b378c07d2c52e51f1b32d1a2Winson mMoveTaskButton.setClickable(false); 48218227e483167c590121fd300d03c999dd057204cWinson ((RippleDrawable) mMoveTaskButton.getBackground()).setForceSoftware(true); 48348f2cda829ddb761697a0efb0cad42a62480c130Winson Chung } 4842536c7ed446203ea12b38cf05a88e603f8d1b768Winson 4854b9cded14346a7d8781ee6549c44888eb4ec9d83Winson if (Recents.getDebugFlags().isFastToggleRecentsEnabled()) { 486c5ef63f4e95329158d88a6cbb05789b57098222dWinson if (mFocusTimerIndicator == null) { 4879b001396c26e5b5ee95e0a54213a8a421179e365Winson mFocusTimerIndicator = (ProgressBar) Utilities.findViewStubById(this, 4889b001396c26e5b5ee95e0a54213a8a421179e365Winson R.id.focus_timer_indicator_stub).inflate(); 489c5ef63f4e95329158d88a6cbb05789b57098222dWinson } 490c5ef63f4e95329158d88a6cbb05789b57098222dWinson mFocusTimerIndicator.getProgressDrawable() 491c5ef63f4e95329158d88a6cbb05789b57098222dWinson .setColorFilter( 492c5ef63f4e95329158d88a6cbb05789b57098222dWinson getSecondaryColor(t.colorPrimary, t.useLightOnPrimaryColor), 493c5ef63f4e95329158d88a6cbb05789b57098222dWinson PorterDuff.Mode.SRC_IN); 494c5ef63f4e95329158d88a6cbb05789b57098222dWinson } 495b124d5607fb6bdfcc9e6c2e9ae24cadaf7f0b55bPeter Schiller 4962536c7ed446203ea12b38cf05a88e603f8d1b768Winson // In accessibility, a single click on the focused app info button will show it 497bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung if (touchExplorationEnabled) { 498b92dd6358180eb7e6b7a57de1efa38e16597e650Winson mIconView.setContentDescription(t.appInfoDescription); 499296278a0679375b8c43962a9e3c9bb4e8ab201e7Winson Chung mIconView.setOnClickListener(this); 5003e5f0af085293004b378c07d2c52e51f1b32d1a2Winson mIconView.setClickable(true); 5012536c7ed446203ea12b38cf05a88e603f8d1b768Winson } 5022536c7ed446203ea12b38cf05a88e603f8d1b768Winson } 5032536c7ed446203ea12b38cf05a88e603f8d1b768Winson 504d2a030613154e2007d9816e090c39e9726e7adbaWinson /** 505d2a030613154e2007d9816e090c39e9726e7adbaWinson * Called when the bound task's data has loaded and this view should update to reflect the 506d2a030613154e2007d9816e090c39e9726e7adbaWinson * changes. 507d2a030613154e2007d9816e090c39e9726e7adbaWinson */ 508d2a030613154e2007d9816e090c39e9726e7adbaWinson public void onTaskDataLoaded() { 509d2a030613154e2007d9816e090c39e9726e7adbaWinson if (mTask.icon != null) { 510d2a030613154e2007d9816e090c39e9726e7adbaWinson mIconView.setImageDrawable(mTask.icon); 511d2a030613154e2007d9816e090c39e9726e7adbaWinson } 512d2a030613154e2007d9816e090c39e9726e7adbaWinson } 513d2a030613154e2007d9816e090c39e9726e7adbaWinson 5142536c7ed446203ea12b38cf05a88e603f8d1b768Winson /** Unbinds the bar view from the task */ 515bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung void unbindFromTask(boolean touchExplorationEnabled) { 5162536c7ed446203ea12b38cf05a88e603f8d1b768Winson mTask = null; 517296278a0679375b8c43962a9e3c9bb4e8ab201e7Winson Chung mIconView.setImageDrawable(null); 518bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung if (touchExplorationEnabled) { 5193e5f0af085293004b378c07d2c52e51f1b32d1a2Winson mIconView.setClickable(false); 520bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung } 521969f586533096999f10f5587f901949791154fa2Winson Chung } 522969f586533096999f10f5587f901949791154fa2Winson Chung 523a26fb7822ddf3511796279b847cc216bee9e7f70Winson Chung /** Animates this task bar if the user does not interact with the stack after a certain time. */ 524a0e88b5013d708ac6ed6518817d83c64c87ae4b1Winson Chung void startNoUserInteractionAnimation() { 525bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung int duration = getResources().getInteger(R.integer.recents_task_enter_from_app_duration); 526bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung mDismissButton.setVisibility(View.VISIBLE); 5273e5f0af085293004b378c07d2c52e51f1b32d1a2Winson mDismissButton.setClickable(true); 528bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung if (mDismissButton.getVisibility() == VISIBLE) { 529133ad44269e4b45e056793b579a7628aa4d91ccbWinson Chung mDismissButton.animate() 530133ad44269e4b45e056793b579a7628aa4d91ccbWinson Chung .alpha(1f) 531133ad44269e4b45e056793b579a7628aa4d91ccbWinson Chung .setInterpolator(Interpolators.FAST_OUT_LINEAR_IN) 532bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung .setDuration(duration) 533133ad44269e4b45e056793b579a7628aa4d91ccbWinson Chung .start(); 534bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung } else { 535bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung mDismissButton.setAlpha(1f); 536bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung } 537bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung if (mMoveTaskButton != null) { 538bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung if (mMoveTaskButton.getVisibility() == VISIBLE) { 539bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung mMoveTaskButton.setVisibility(View.VISIBLE); 5403e5f0af085293004b378c07d2c52e51f1b32d1a2Winson mMoveTaskButton.setClickable(true); 541bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung mMoveTaskButton.animate() 542bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung .alpha(1f) 543bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung .setInterpolator(Interpolators.FAST_OUT_LINEAR_IN) 544bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung .setDuration(duration) 545bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung .start(); 546bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung } else { 547bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung mMoveTaskButton.setAlpha(1f); 548bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung } 549133ad44269e4b45e056793b579a7628aa4d91ccbWinson Chung } 550a26fb7822ddf3511796279b847cc216bee9e7f70Winson Chung } 551a26fb7822ddf3511796279b847cc216bee9e7f70Winson Chung 552b124d5607fb6bdfcc9e6c2e9ae24cadaf7f0b55bPeter Schiller /** 553b124d5607fb6bdfcc9e6c2e9ae24cadaf7f0b55bPeter Schiller * Mark this task view that the user does has not interacted with the stack after a certain 554b124d5607fb6bdfcc9e6c2e9ae24cadaf7f0b55bPeter Schiller * time. 555b124d5607fb6bdfcc9e6c2e9ae24cadaf7f0b55bPeter Schiller */ 556a0e88b5013d708ac6ed6518817d83c64c87ae4b1Winson Chung void setNoUserInteractionState() { 557bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung mDismissButton.setVisibility(View.VISIBLE); 558bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung mDismissButton.animate().cancel(); 559bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung mDismissButton.setAlpha(1f); 5603e5f0af085293004b378c07d2c52e51f1b32d1a2Winson mDismissButton.setClickable(true); 561bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung if (mMoveTaskButton != null) { 562bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung mMoveTaskButton.setVisibility(View.VISIBLE); 563bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung mMoveTaskButton.animate().cancel(); 564bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung mMoveTaskButton.setAlpha(1f); 5653e5f0af085293004b378c07d2c52e51f1b32d1a2Winson mMoveTaskButton.setClickable(true); 566133ad44269e4b45e056793b579a7628aa4d91ccbWinson Chung } 567a26fb7822ddf3511796279b847cc216bee9e7f70Winson Chung } 568a0e88b5013d708ac6ed6518817d83c64c87ae4b1Winson Chung 569b124d5607fb6bdfcc9e6c2e9ae24cadaf7f0b55bPeter Schiller /** 570b124d5607fb6bdfcc9e6c2e9ae24cadaf7f0b55bPeter Schiller * Resets the state tracking that the user has not interacted with the stack after a certain 571b124d5607fb6bdfcc9e6c2e9ae24cadaf7f0b55bPeter Schiller * time. 572b124d5607fb6bdfcc9e6c2e9ae24cadaf7f0b55bPeter Schiller */ 573b0a28ea5d381cd3a8477cf7fd82797199c80ca67Winson Chung void resetNoUserInteractionState() { 574b0a28ea5d381cd3a8477cf7fd82797199c80ca67Winson Chung mDismissButton.setVisibility(View.INVISIBLE); 575bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung mDismissButton.setAlpha(0f); 5763e5f0af085293004b378c07d2c52e51f1b32d1a2Winson mDismissButton.setClickable(false); 577bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung if (mMoveTaskButton != null) { 578bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung mMoveTaskButton.setVisibility(View.INVISIBLE); 579bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung mMoveTaskButton.setAlpha(0f); 5803e5f0af085293004b378c07d2c52e51f1b32d1a2Winson mMoveTaskButton.setClickable(false); 581bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung } 582b0a28ea5d381cd3a8477cf7fd82797199c80ca67Winson Chung } 583b0a28ea5d381cd3a8477cf7fd82797199c80ca67Winson Chung 584bf5dbf1c151eb64f4068f233e72b0a867348bf8cWinson Chung @Override 585bf5dbf1c151eb64f4068f233e72b0a867348bf8cWinson Chung protected int[] onCreateDrawableState(int extraSpace) { 586bf5dbf1c151eb64f4068f233e72b0a867348bf8cWinson Chung 587bf5dbf1c151eb64f4068f233e72b0a867348bf8cWinson Chung // Don't forward our state to the drawable - we do it manually in onTaskViewFocusChanged. 588bf5dbf1c151eb64f4068f233e72b0a867348bf8cWinson Chung // This is to prevent layer trashing when the view is pressed. 589bf5dbf1c151eb64f4068f233e72b0a867348bf8cWinson Chung return new int[] {}; 590bf5dbf1c151eb64f4068f233e72b0a867348bf8cWinson Chung } 591bf5dbf1c151eb64f4068f233e72b0a867348bf8cWinson Chung 592900fb48d269e2fbf3baea995c6324e4c08ad7c22Jorim Jaggi @Override 5932536c7ed446203ea12b38cf05a88e603f8d1b768Winson public void onClick(View v) { 594296278a0679375b8c43962a9e3c9bb4e8ab201e7Winson Chung if (v == mIconView) { 595bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung // In accessibility, a single click on the focused app info button will show it 596bbb3d3de3c058f115ab1fba0ddb7238e54745c0bWinson Chung EventBus.getDefault().send(new ShowApplicationInfoEvent(mTask)); 5972536c7ed446203ea12b38cf05a88e603f8d1b768Winson } else if (v == mDismissButton) { 598be7607af8875236b9cf7bdb5f5aa089c207529afWinson TaskView tv = Utilities.findParent(this, TaskView.class); 5992536c7ed446203ea12b38cf05a88e603f8d1b768Winson tv.dismissTask(); 6002536c7ed446203ea12b38cf05a88e603f8d1b768Winson 6012536c7ed446203ea12b38cf05a88e603f8d1b768Winson // Keep track of deletions by the dismiss button 6022536c7ed446203ea12b38cf05a88e603f8d1b768Winson MetricsLogger.histogram(getContext(), "overview_task_dismissed_source", 6032536c7ed446203ea12b38cf05a88e603f8d1b768Winson Constants.Metrics.DismissSourceHeaderButton); 6042536c7ed446203ea12b38cf05a88e603f8d1b768Winson } else if (v == mMoveTaskButton) { 60548f2cda829ddb761697a0efb0cad42a62480c130Winson Chung TaskView tv = Utilities.findParent(this, TaskView.class); 60648f2cda829ddb761697a0efb0cad42a62480c130Winson Chung Rect bounds = mMoveTaskTargetStackId == FREEFORM_WORKSPACE_STACK_ID 60748f2cda829ddb761697a0efb0cad42a62480c130Winson Chung ? new Rect(mTaskViewRect) 60848f2cda829ddb761697a0efb0cad42a62480c130Winson Chung : new Rect(); 60948f2cda829ddb761697a0efb0cad42a62480c130Winson Chung EventBus.getDefault().send(new LaunchTaskEvent(tv, mTask, bounds, 61048f2cda829ddb761697a0efb0cad42a62480c130Winson Chung mMoveTaskTargetStackId, false)); 611c5ef63f4e95329158d88a6cbb05789b57098222dWinson } else if (v == mAppInfoView) { 612c5ef63f4e95329158d88a6cbb05789b57098222dWinson EventBus.getDefault().send(new ShowApplicationInfoEvent(mTask)); 613c5ef63f4e95329158d88a6cbb05789b57098222dWinson } else if (v == mAppIconView) { 614c5ef63f4e95329158d88a6cbb05789b57098222dWinson hideAppOverlay(false /* immediate */); 6152536c7ed446203ea12b38cf05a88e603f8d1b768Winson } 6162536c7ed446203ea12b38cf05a88e603f8d1b768Winson } 6172536c7ed446203ea12b38cf05a88e603f8d1b768Winson 6182536c7ed446203ea12b38cf05a88e603f8d1b768Winson @Override 6192536c7ed446203ea12b38cf05a88e603f8d1b768Winson public boolean onLongClick(View v) { 620296278a0679375b8c43962a9e3c9bb4e8ab201e7Winson Chung if (v == mIconView) { 621c5ef63f4e95329158d88a6cbb05789b57098222dWinson showAppOverlay(); 622c5ef63f4e95329158d88a6cbb05789b57098222dWinson return true; 623c5ef63f4e95329158d88a6cbb05789b57098222dWinson } else if (v == mAppIconView) { 624c5ef63f4e95329158d88a6cbb05789b57098222dWinson hideAppOverlay(false /* immediate */); 6252536c7ed446203ea12b38cf05a88e603f8d1b768Winson return true; 6262536c7ed446203ea12b38cf05a88e603f8d1b768Winson } 6272536c7ed446203ea12b38cf05a88e603f8d1b768Winson return false; 6282536c7ed446203ea12b38cf05a88e603f8d1b768Winson } 629c5ef63f4e95329158d88a6cbb05789b57098222dWinson 630c5ef63f4e95329158d88a6cbb05789b57098222dWinson /** 631c5ef63f4e95329158d88a6cbb05789b57098222dWinson * Shows the application overlay. 632c5ef63f4e95329158d88a6cbb05789b57098222dWinson */ 633c5ef63f4e95329158d88a6cbb05789b57098222dWinson private void showAppOverlay() { 634c5ef63f4e95329158d88a6cbb05789b57098222dWinson // Skip early if the task is invalid 635c5ef63f4e95329158d88a6cbb05789b57098222dWinson SystemServicesProxy ssp = Recents.getSystemServices(); 636c5ef63f4e95329158d88a6cbb05789b57098222dWinson ComponentName cn = mTask.key.getComponent(); 637c5ef63f4e95329158d88a6cbb05789b57098222dWinson int userId = mTask.key.userId; 638c5ef63f4e95329158d88a6cbb05789b57098222dWinson ActivityInfo activityInfo = ssp.getActivityInfo(cn, userId); 639c5ef63f4e95329158d88a6cbb05789b57098222dWinson if (activityInfo == null) { 640c5ef63f4e95329158d88a6cbb05789b57098222dWinson return; 641c5ef63f4e95329158d88a6cbb05789b57098222dWinson } 642c5ef63f4e95329158d88a6cbb05789b57098222dWinson 643c5ef63f4e95329158d88a6cbb05789b57098222dWinson // Inflate the overlay if necessary 644c5ef63f4e95329158d88a6cbb05789b57098222dWinson if (mAppOverlayView == null) { 6459b001396c26e5b5ee95e0a54213a8a421179e365Winson mAppOverlayView = (FrameLayout) Utilities.findViewStubById(this, 6469b001396c26e5b5ee95e0a54213a8a421179e365Winson R.id.app_overlay_stub).inflate(); 647c5ef63f4e95329158d88a6cbb05789b57098222dWinson mAppOverlayView.setBackground(mOverlayBackground); 648c5ef63f4e95329158d88a6cbb05789b57098222dWinson mAppIconView = (ImageView) mAppOverlayView.findViewById(R.id.app_icon); 649c5ef63f4e95329158d88a6cbb05789b57098222dWinson mAppIconView.setOnClickListener(this); 650c5ef63f4e95329158d88a6cbb05789b57098222dWinson mAppIconView.setOnLongClickListener(this); 651c5ef63f4e95329158d88a6cbb05789b57098222dWinson mAppInfoView = (ImageView) mAppOverlayView.findViewById(R.id.app_info); 652c5ef63f4e95329158d88a6cbb05789b57098222dWinson mAppInfoView.setOnClickListener(this); 653c5ef63f4e95329158d88a6cbb05789b57098222dWinson mAppTitleView = (TextView) mAppOverlayView.findViewById(R.id.app_title); 654217009356efa2b854ab3981dff8d315a0d679c73Winson updateLayoutParams(mAppIconView, mAppTitleView, null, mAppInfoView); 655c5ef63f4e95329158d88a6cbb05789b57098222dWinson } 656c5ef63f4e95329158d88a6cbb05789b57098222dWinson 657c5ef63f4e95329158d88a6cbb05789b57098222dWinson // Update the overlay contents for the current app 658c5ef63f4e95329158d88a6cbb05789b57098222dWinson mAppTitleView.setText(ssp.getBadgedApplicationLabel(activityInfo.applicationInfo, userId)); 6594c84a8c481093e81c2e27de4cecf92c41992f4a1Winson mAppTitleView.setTextColor(mTask.useLightOnPrimaryColor ? 6604c84a8c481093e81c2e27de4cecf92c41992f4a1Winson mTaskBarViewLightTextColor : mTaskBarViewDarkTextColor); 6614c84a8c481093e81c2e27de4cecf92c41992f4a1Winson mAppIconView.setImageDrawable(ssp.getBadgedApplicationIcon(activityInfo.applicationInfo, 6624c84a8c481093e81c2e27de4cecf92c41992f4a1Winson userId)); 663c5ef63f4e95329158d88a6cbb05789b57098222dWinson mAppInfoView.setImageDrawable(mTask.useLightOnPrimaryColor 664c5ef63f4e95329158d88a6cbb05789b57098222dWinson ? mLightInfoIcon 665c5ef63f4e95329158d88a6cbb05789b57098222dWinson : mDarkInfoIcon); 666c5ef63f4e95329158d88a6cbb05789b57098222dWinson mAppOverlayView.setVisibility(View.VISIBLE); 667c5ef63f4e95329158d88a6cbb05789b57098222dWinson 668c5ef63f4e95329158d88a6cbb05789b57098222dWinson int x = mIconView.getLeft() + mIconView.getWidth() / 2; 669c5ef63f4e95329158d88a6cbb05789b57098222dWinson int y = mIconView.getTop() + mIconView.getHeight() / 2; 670c5ef63f4e95329158d88a6cbb05789b57098222dWinson Animator revealAnim = ViewAnimationUtils.createCircularReveal(mAppOverlayView, x, y, 0, 671c5ef63f4e95329158d88a6cbb05789b57098222dWinson getWidth()); 672c5ef63f4e95329158d88a6cbb05789b57098222dWinson revealAnim.setDuration(OVERLAY_REVEAL_DURATION); 673c0d7058b14c24cd07912f5629c26b39b7b4673d5Winson revealAnim.setInterpolator(Interpolators.LINEAR_OUT_SLOW_IN); 674c5ef63f4e95329158d88a6cbb05789b57098222dWinson revealAnim.start(); 675c5ef63f4e95329158d88a6cbb05789b57098222dWinson } 676c5ef63f4e95329158d88a6cbb05789b57098222dWinson 677c5ef63f4e95329158d88a6cbb05789b57098222dWinson /** 678c5ef63f4e95329158d88a6cbb05789b57098222dWinson * Hide the application overlay. 679c5ef63f4e95329158d88a6cbb05789b57098222dWinson */ 680c5ef63f4e95329158d88a6cbb05789b57098222dWinson private void hideAppOverlay(boolean immediate) { 681c5ef63f4e95329158d88a6cbb05789b57098222dWinson // Skip if we haven't even loaded the overlay yet 682c5ef63f4e95329158d88a6cbb05789b57098222dWinson if (mAppOverlayView == null) { 683c5ef63f4e95329158d88a6cbb05789b57098222dWinson return; 684c5ef63f4e95329158d88a6cbb05789b57098222dWinson } 685c5ef63f4e95329158d88a6cbb05789b57098222dWinson 686c5ef63f4e95329158d88a6cbb05789b57098222dWinson if (immediate) { 687c5ef63f4e95329158d88a6cbb05789b57098222dWinson mAppOverlayView.setVisibility(View.GONE); 688c5ef63f4e95329158d88a6cbb05789b57098222dWinson } else { 689c5ef63f4e95329158d88a6cbb05789b57098222dWinson int x = mIconView.getLeft() + mIconView.getWidth() / 2; 690c5ef63f4e95329158d88a6cbb05789b57098222dWinson int y = mIconView.getTop() + mIconView.getHeight() / 2; 691c5ef63f4e95329158d88a6cbb05789b57098222dWinson Animator revealAnim = ViewAnimationUtils.createCircularReveal(mAppOverlayView, x, y, 692c5ef63f4e95329158d88a6cbb05789b57098222dWinson getWidth(), 0); 693c5ef63f4e95329158d88a6cbb05789b57098222dWinson revealAnim.setDuration(OVERLAY_REVEAL_DURATION); 694c0d7058b14c24cd07912f5629c26b39b7b4673d5Winson revealAnim.setInterpolator(Interpolators.LINEAR_OUT_SLOW_IN); 695c5ef63f4e95329158d88a6cbb05789b57098222dWinson revealAnim.addListener(new AnimatorListenerAdapter() { 696c5ef63f4e95329158d88a6cbb05789b57098222dWinson @Override 697c5ef63f4e95329158d88a6cbb05789b57098222dWinson public void onAnimationEnd(Animator animation) { 698c5ef63f4e95329158d88a6cbb05789b57098222dWinson mAppOverlayView.setVisibility(View.GONE); 699c5ef63f4e95329158d88a6cbb05789b57098222dWinson } 700c5ef63f4e95329158d88a6cbb05789b57098222dWinson }); 701c5ef63f4e95329158d88a6cbb05789b57098222dWinson revealAnim.start(); 702c5ef63f4e95329158d88a6cbb05789b57098222dWinson } 703c5ef63f4e95329158d88a6cbb05789b57098222dWinson } 70437c8d8ef855aacb074ee0b702a46dbc62b7551a2Winson Chung} 705