Winson Chung | 37c8d8e | 2014-03-24 14:53:07 -0700 | [diff] [blame] | 1 | /* |
| 2 | * Copyright (C) 2014 The Android Open Source Project |
| 3 | * |
| 4 | * Licensed under the Apache License, Version 2.0 (the "License"); |
| 5 | * you may not use this file except in compliance with the License. |
| 6 | * You may obtain a copy of the License at |
| 7 | * |
| 8 | * http://www.apache.org/licenses/LICENSE-2.0 |
| 9 | * |
| 10 | * Unless required by applicable law or agreed to in writing, software |
| 11 | * distributed under the License is distributed on an "AS IS" BASIS, |
| 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
| 13 | * See the License for the specific language governing permissions and |
| 14 | * limitations under the License. |
| 15 | */ |
| 16 | |
| 17 | package com.android.systemui.recents.views; |
| 18 | |
Winson | 2170093 | 2016-03-24 17:26:23 -0700 | [diff] [blame] | 19 | import android.app.ActivityManager; |
Winson Chung | 37c8d8e | 2014-03-24 14:53:07 -0700 | [diff] [blame] | 20 | import android.content.Context; |
Winson | 2170093 | 2016-03-24 17:26:23 -0700 | [diff] [blame] | 21 | import android.content.res.Configuration; |
Winson Chung | dcfa797 | 2014-07-22 12:27:13 -0700 | [diff] [blame] | 22 | import android.graphics.Bitmap; |
Selim Cinek | e8199c5 | 2014-09-17 04:03:52 +0200 | [diff] [blame] | 23 | import android.graphics.BitmapShader; |
| 24 | import android.graphics.Canvas; |
| 25 | import android.graphics.Color; |
Winson | 8be1634 | 2016-02-09 11:53:27 -0800 | [diff] [blame] | 26 | import android.graphics.ColorMatrix; |
| 27 | import android.graphics.ColorMatrixColorFilter; |
Selim Cinek | e8199c5 | 2014-09-17 04:03:52 +0200 | [diff] [blame] | 28 | import android.graphics.LightingColorFilter; |
| 29 | import android.graphics.Matrix; |
| 30 | import android.graphics.Paint; |
Winson Chung | 743d5c9 | 2014-06-13 10:14:53 -0700 | [diff] [blame] | 31 | import android.graphics.Rect; |
Winson Chung | 1af8eda | 2016-02-05 17:55:56 +0000 | [diff] [blame] | 32 | import android.graphics.Region; |
Selim Cinek | e8199c5 | 2014-09-17 04:03:52 +0200 | [diff] [blame] | 33 | import android.graphics.Shader; |
Winson Chung | 37c8d8e | 2014-03-24 14:53:07 -0700 | [diff] [blame] | 34 | import android.util.AttributeSet; |
Winson Chung | 743d5c9 | 2014-06-13 10:14:53 -0700 | [diff] [blame] | 35 | import android.view.View; |
Winson | 231bc9c | 2016-02-09 12:31:00 -0800 | [diff] [blame] | 36 | import android.view.ViewDebug; |
Winson | c0d7058 | 2016-01-29 10:24:39 -0800 | [diff] [blame] | 37 | |
Winson | 2536c7e | 2015-10-01 15:49:31 -0700 | [diff] [blame] | 38 | import com.android.systemui.R; |
Winson | 2170093 | 2016-03-24 17:26:23 -0700 | [diff] [blame] | 39 | import com.android.systemui.recents.Recents; |
| 40 | import com.android.systemui.recents.misc.SystemServicesProxy; |
Winson Chung | 37c8d8e | 2014-03-24 14:53:07 -0700 | [diff] [blame] | 41 | import com.android.systemui.recents.model.Task; |
| 42 | |
| 43 | |
Winson Chung | 353c0b9 | 2014-10-16 17:43:23 -0700 | [diff] [blame] | 44 | /** |
| 45 | * The task thumbnail view. It implements an image view that allows for animating the dim and |
| 46 | * alpha of the thumbnail image. |
| 47 | */ |
Selim Cinek | e8199c5 | 2014-09-17 04:03:52 +0200 | [diff] [blame] | 48 | public class TaskViewThumbnail extends View { |
Winson Chung | 743d5c9 | 2014-06-13 10:14:53 -0700 | [diff] [blame] | 49 | |
Winson | 8be1634 | 2016-02-09 11:53:27 -0800 | [diff] [blame] | 50 | private static final ColorMatrix TMP_FILTER_COLOR_MATRIX = new ColorMatrix(); |
| 51 | private static final ColorMatrix TMP_BRIGHTNESS_COLOR_MATRIX = new ColorMatrix(); |
| 52 | |
Winson | 778f495 | 2016-01-08 10:32:08 -0800 | [diff] [blame] | 53 | private Task mTask; |
Winson | 479f744 | 2015-11-25 15:16:27 -0800 | [diff] [blame] | 54 | |
Winson | 2170093 | 2016-03-24 17:26:23 -0700 | [diff] [blame] | 55 | private Rect mDisplayRect = new Rect(); |
| 56 | private int mOrientation = Configuration.ORIENTATION_UNDEFINED; |
| 57 | |
Winson Chung | 353c0b9 | 2014-10-16 17:43:23 -0700 | [diff] [blame] | 58 | // Drawing |
Winson | 231bc9c | 2016-02-09 12:31:00 -0800 | [diff] [blame] | 59 | @ViewDebug.ExportedProperty(category="recents") |
Winson | 2170093 | 2016-03-24 17:26:23 -0700 | [diff] [blame] | 60 | Rect mTaskViewRect = new Rect(); |
| 61 | @ViewDebug.ExportedProperty(category="recents") |
Winson | 778f495 | 2016-01-08 10:32:08 -0800 | [diff] [blame] | 62 | Rect mThumbnailRect = new Rect(); |
Winson | 231bc9c | 2016-02-09 12:31:00 -0800 | [diff] [blame] | 63 | @ViewDebug.ExportedProperty(category="recents") |
Winson | 2170093 | 2016-03-24 17:26:23 -0700 | [diff] [blame] | 64 | float mThumbnailScale; |
| 65 | float mFullscreenThumbnailScale; |
| 66 | ActivityManager.TaskThumbnailInfo mThumbnailInfo; |
| 67 | |
Winson | 35f3050 | 2015-09-28 11:24:36 -0700 | [diff] [blame] | 68 | int mCornerRadius; |
Winson | 231bc9c | 2016-02-09 12:31:00 -0800 | [diff] [blame] | 69 | @ViewDebug.ExportedProperty(category="recents") |
Winson Chung | 353c0b9 | 2014-10-16 17:43:23 -0700 | [diff] [blame] | 70 | float mDimAlpha; |
| 71 | Matrix mScaleMatrix = new Matrix(); |
Selim Cinek | e8199c5 | 2014-09-17 04:03:52 +0200 | [diff] [blame] | 72 | Paint mDrawPaint = new Paint(); |
Winson Chung | 1af8eda | 2016-02-05 17:55:56 +0000 | [diff] [blame] | 73 | Paint mBgFillPaint = new Paint(); |
Winson Chung | 353c0b9 | 2014-10-16 17:43:23 -0700 | [diff] [blame] | 74 | BitmapShader mBitmapShader; |
Selim Cinek | e8199c5 | 2014-09-17 04:03:52 +0200 | [diff] [blame] | 75 | LightingColorFilter mLightingColorFilter = new LightingColorFilter(0xffffffff, 0); |
Winson Chung | 353c0b9 | 2014-10-16 17:43:23 -0700 | [diff] [blame] | 76 | |
Winson Chung | 353c0b9 | 2014-10-16 17:43:23 -0700 | [diff] [blame] | 77 | // Task bar clipping, the top of this thumbnail can be clipped against the opaque header |
| 78 | // bar that overlaps this thumbnail |
| 79 | View mTaskBar; |
Winson | 231bc9c | 2016-02-09 12:31:00 -0800 | [diff] [blame] | 80 | @ViewDebug.ExportedProperty(category="recents") |
Winson Chung | 353c0b9 | 2014-10-16 17:43:23 -0700 | [diff] [blame] | 81 | Rect mClipRect = new Rect(); |
| 82 | |
| 83 | // Visibility optimization, if the thumbnail height is less than the height of the header |
| 84 | // bar for the task view, then just mark this thumbnail view as invisible |
Winson | 231bc9c | 2016-02-09 12:31:00 -0800 | [diff] [blame] | 85 | @ViewDebug.ExportedProperty(category="recents") |
Winson Chung | 353c0b9 | 2014-10-16 17:43:23 -0700 | [diff] [blame] | 86 | boolean mInvisible; |
| 87 | |
Winson | 231bc9c | 2016-02-09 12:31:00 -0800 | [diff] [blame] | 88 | @ViewDebug.ExportedProperty(category="recents") |
Winson | 8be1634 | 2016-02-09 11:53:27 -0800 | [diff] [blame] | 89 | boolean mDisabledInSafeMode; |
| 90 | |
Winson Chung | ec396d6 | 2014-08-06 17:08:00 -0700 | [diff] [blame] | 91 | public TaskViewThumbnail(Context context) { |
Winson Chung | 37c8d8e | 2014-03-24 14:53:07 -0700 | [diff] [blame] | 92 | this(context, null); |
| 93 | } |
| 94 | |
Winson Chung | ec396d6 | 2014-08-06 17:08:00 -0700 | [diff] [blame] | 95 | public TaskViewThumbnail(Context context, AttributeSet attrs) { |
Winson Chung | 37c8d8e | 2014-03-24 14:53:07 -0700 | [diff] [blame] | 96 | this(context, attrs, 0); |
| 97 | } |
| 98 | |
Winson Chung | ec396d6 | 2014-08-06 17:08:00 -0700 | [diff] [blame] | 99 | public TaskViewThumbnail(Context context, AttributeSet attrs, int defStyleAttr) { |
Winson Chung | 37c8d8e | 2014-03-24 14:53:07 -0700 | [diff] [blame] | 100 | this(context, attrs, defStyleAttr, 0); |
| 101 | } |
| 102 | |
Winson Chung | ec396d6 | 2014-08-06 17:08:00 -0700 | [diff] [blame] | 103 | public TaskViewThumbnail(Context context, AttributeSet attrs, int defStyleAttr, int defStyleRes) { |
Winson Chung | 37c8d8e | 2014-03-24 14:53:07 -0700 | [diff] [blame] | 104 | super(context, attrs, defStyleAttr, defStyleRes); |
Selim Cinek | e8199c5 | 2014-09-17 04:03:52 +0200 | [diff] [blame] | 105 | mDrawPaint.setColorFilter(mLightingColorFilter); |
| 106 | mDrawPaint.setFilterBitmap(true); |
| 107 | mDrawPaint.setAntiAlias(true); |
Winson | 35f3050 | 2015-09-28 11:24:36 -0700 | [diff] [blame] | 108 | mCornerRadius = getResources().getDimensionPixelSize( |
| 109 | R.dimen.recents_task_view_rounded_corners_radius); |
Winson Chung | 1af8eda | 2016-02-05 17:55:56 +0000 | [diff] [blame] | 110 | mBgFillPaint.setColor(Color.WHITE); |
Winson | 2170093 | 2016-03-24 17:26:23 -0700 | [diff] [blame] | 111 | mFullscreenThumbnailScale = context.getResources().getFraction( |
| 112 | com.android.internal.R.fraction.thumbnail_fullscreen_scale, 1, 1); |
Selim Cinek | e8199c5 | 2014-09-17 04:03:52 +0200 | [diff] [blame] | 113 | } |
| 114 | |
Winson | de0591a | 2015-12-04 17:24:35 -0800 | [diff] [blame] | 115 | /** |
| 116 | * Called when the task view frame changes, allowing us to move the contents of the header |
| 117 | * to match the frame changes. |
| 118 | */ |
| 119 | public void onTaskViewSizeChanged(int width, int height) { |
Winson | 94a0e89 | 2016-01-08 16:06:50 -0800 | [diff] [blame] | 120 | // Return early if the bounds have not changed |
| 121 | if (mTaskViewRect.width() == width && mTaskViewRect.height() == height) { |
| 122 | return; |
| 123 | } |
| 124 | |
Winson | de0591a | 2015-12-04 17:24:35 -0800 | [diff] [blame] | 125 | mTaskViewRect.set(0, 0, width, height); |
Winson | 778f495 | 2016-01-08 10:32:08 -0800 | [diff] [blame] | 126 | updateThumbnailScale(); |
Winson | de0591a | 2015-12-04 17:24:35 -0800 | [diff] [blame] | 127 | } |
| 128 | |
Selim Cinek | e8199c5 | 2014-09-17 04:03:52 +0200 | [diff] [blame] | 129 | @Override |
Winson | 2170093 | 2016-03-24 17:26:23 -0700 | [diff] [blame] | 130 | protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { |
| 131 | super.onMeasure(widthMeasureSpec, heightMeasureSpec); |
| 132 | |
| 133 | SystemServicesProxy ssp = Recents.getSystemServices(); |
| 134 | mOrientation = ssp.getDisplayOrientation(); |
| 135 | mDisplayRect = ssp.getDisplayRect(); |
| 136 | } |
| 137 | |
| 138 | @Override |
Winson Chung | 353c0b9 | 2014-10-16 17:43:23 -0700 | [diff] [blame] | 139 | protected void onDraw(Canvas canvas) { |
| 140 | if (mInvisible) { |
| 141 | return; |
| 142 | } |
Winson Chung | 1af8eda | 2016-02-05 17:55:56 +0000 | [diff] [blame] | 143 | |
Winson | 2170093 | 2016-03-24 17:26:23 -0700 | [diff] [blame] | 144 | if (mBitmapShader != null) { |
| 145 | int viewWidth = mTaskViewRect.width(); |
| 146 | int viewHeight = mTaskViewRect.height(); |
| 147 | |
| 148 | // We are drawing the thumbnail in the same orientation, so just fit the width |
| 149 | int thumbnailWidth = (int) (mThumbnailRect.width() * mThumbnailScale); |
| 150 | int thumbnailHeight = (int) (mThumbnailRect.height() * mThumbnailScale); |
| 151 | |
| 152 | if (thumbnailWidth >= viewWidth && thumbnailHeight >= viewHeight) { |
| 153 | // Thumbnail fills the full task view bounds, so just draw it |
| 154 | canvas.drawRoundRect(0, 0, viewWidth, viewHeight, mCornerRadius, mCornerRadius, |
| 155 | mDrawPaint); |
| 156 | } else { |
| 157 | // Thumbnail does not fill the full task view bounds, so just draw it and fill the |
| 158 | // empty areas with the background color |
| 159 | int count = canvas.save(); |
Winson Chung | 1af8eda | 2016-02-05 17:55:56 +0000 | [diff] [blame] | 160 | |
| 161 | // Since we only want the top corners to be rounded, draw slightly beyond the |
| 162 | // thumbnail height, but clip to the thumbnail height |
Winson | 2170093 | 2016-03-24 17:26:23 -0700 | [diff] [blame] | 163 | canvas.clipRect(0, 0, thumbnailWidth, thumbnailHeight, Region.Op.REPLACE); |
| 164 | canvas.drawRoundRect(0, 0, |
| 165 | thumbnailWidth + (thumbnailWidth < viewWidth ? mCornerRadius : 0), |
| 166 | thumbnailHeight + (thumbnailHeight < viewHeight ? mCornerRadius : 0), |
Winson Chung | 1af8eda | 2016-02-05 17:55:56 +0000 | [diff] [blame] | 167 | mCornerRadius, mCornerRadius, mDrawPaint); |
Winson Chung | 1af8eda | 2016-02-05 17:55:56 +0000 | [diff] [blame] | 168 | |
Winson | 2170093 | 2016-03-24 17:26:23 -0700 | [diff] [blame] | 169 | // In the remaining space, draw the background color |
| 170 | if (thumbnailWidth < viewWidth) { |
| 171 | canvas.clipRect(thumbnailWidth, 0, viewWidth, viewHeight, Region.Op.REPLACE); |
| 172 | canvas.drawRoundRect(Math.max(0, thumbnailWidth - mCornerRadius), 0, |
| 173 | viewWidth, viewHeight, mCornerRadius, mCornerRadius, mBgFillPaint); |
| 174 | } |
| 175 | if (thumbnailWidth > 0 && thumbnailHeight < viewHeight) { |
| 176 | canvas.clipRect(0, thumbnailHeight, viewWidth, viewHeight, Region.Op.REPLACE); |
| 177 | canvas.drawRoundRect(0, Math.max(0, thumbnailHeight - mCornerRadius), |
| 178 | viewWidth, viewHeight, mCornerRadius, mCornerRadius, mBgFillPaint); |
| 179 | } |
Winson Chung | 1af8eda | 2016-02-05 17:55:56 +0000 | [diff] [blame] | 180 | |
Winson Chung | 1af8eda | 2016-02-05 17:55:56 +0000 | [diff] [blame] | 181 | canvas.restoreToCount(count); |
| 182 | } |
| 183 | } |
Winson Chung | 353c0b9 | 2014-10-16 17:43:23 -0700 | [diff] [blame] | 184 | } |
| 185 | |
| 186 | /** Sets the thumbnail to a given bitmap. */ |
Winson | 2170093 | 2016-03-24 17:26:23 -0700 | [diff] [blame] | 187 | void setThumbnail(Bitmap bm, ActivityManager.TaskThumbnailInfo thumbnailInfo) { |
Winson Chung | 353c0b9 | 2014-10-16 17:43:23 -0700 | [diff] [blame] | 188 | if (bm != null) { |
Winson | 2170093 | 2016-03-24 17:26:23 -0700 | [diff] [blame] | 189 | mBitmapShader = new BitmapShader(bm, Shader.TileMode.CLAMP, Shader.TileMode.CLAMP); |
Winson Chung | 353c0b9 | 2014-10-16 17:43:23 -0700 | [diff] [blame] | 190 | mDrawPaint.setShader(mBitmapShader); |
Winson | 778f495 | 2016-01-08 10:32:08 -0800 | [diff] [blame] | 191 | mThumbnailRect.set(0, 0, bm.getWidth(), bm.getHeight()); |
Winson | 2170093 | 2016-03-24 17:26:23 -0700 | [diff] [blame] | 192 | mThumbnailInfo = thumbnailInfo; |
Winson | 778f495 | 2016-01-08 10:32:08 -0800 | [diff] [blame] | 193 | updateThumbnailScale(); |
Winson Chung | 353c0b9 | 2014-10-16 17:43:23 -0700 | [diff] [blame] | 194 | } else { |
| 195 | mBitmapShader = null; |
| 196 | mDrawPaint.setShader(null); |
Winson | 778f495 | 2016-01-08 10:32:08 -0800 | [diff] [blame] | 197 | mThumbnailRect.setEmpty(); |
Winson | 2170093 | 2016-03-24 17:26:23 -0700 | [diff] [blame] | 198 | mThumbnailInfo = null; |
Winson Chung | 353c0b9 | 2014-10-16 17:43:23 -0700 | [diff] [blame] | 199 | } |
Winson Chung | 353c0b9 | 2014-10-16 17:43:23 -0700 | [diff] [blame] | 200 | } |
| 201 | |
| 202 | /** Updates the paint to draw the thumbnail. */ |
| 203 | void updateThumbnailPaintFilter() { |
| 204 | if (mInvisible) { |
| 205 | return; |
| 206 | } |
Winson | 479f744 | 2015-11-25 15:16:27 -0800 | [diff] [blame] | 207 | int mul = (int) ((1.0f - mDimAlpha) * 255); |
Winson Chung | 353c0b9 | 2014-10-16 17:43:23 -0700 | [diff] [blame] | 208 | if (mBitmapShader != null) { |
Winson | 8be1634 | 2016-02-09 11:53:27 -0800 | [diff] [blame] | 209 | if (mDisabledInSafeMode) { |
| 210 | // Brightness: C-new = C-old*(1-amount) + amount |
| 211 | TMP_FILTER_COLOR_MATRIX.setSaturation(0); |
| 212 | float scale = 1f - mDimAlpha; |
| 213 | float[] mat = TMP_BRIGHTNESS_COLOR_MATRIX.getArray(); |
| 214 | mat[0] = scale; |
| 215 | mat[6] = scale; |
| 216 | mat[12] = scale; |
Winson | 12858a6 | 2016-02-24 11:06:01 -0800 | [diff] [blame] | 217 | mat[4] = mDimAlpha * 255f; |
| 218 | mat[9] = mDimAlpha * 255f; |
| 219 | mat[14] = mDimAlpha * 255f; |
Winson | 8be1634 | 2016-02-09 11:53:27 -0800 | [diff] [blame] | 220 | TMP_FILTER_COLOR_MATRIX.preConcat(TMP_BRIGHTNESS_COLOR_MATRIX); |
| 221 | ColorMatrixColorFilter filter = new ColorMatrixColorFilter(TMP_FILTER_COLOR_MATRIX); |
| 222 | mDrawPaint.setColorFilter(filter); |
| 223 | mBgFillPaint.setColorFilter(filter); |
| 224 | } else { |
| 225 | mLightingColorFilter.setColorMultiply(Color.argb(255, mul, mul, mul)); |
| 226 | mDrawPaint.setColorFilter(mLightingColorFilter); |
| 227 | mDrawPaint.setColor(0xFFffffff); |
| 228 | mBgFillPaint.setColorFilter(mLightingColorFilter); |
| 229 | } |
Winson Chung | 353c0b9 | 2014-10-16 17:43:23 -0700 | [diff] [blame] | 230 | } else { |
Winson | 479f744 | 2015-11-25 15:16:27 -0800 | [diff] [blame] | 231 | int grey = mul; |
Winson Chung | 353c0b9 | 2014-10-16 17:43:23 -0700 | [diff] [blame] | 232 | mDrawPaint.setColorFilter(null); |
| 233 | mDrawPaint.setColor(Color.argb(255, grey, grey, grey)); |
| 234 | } |
Winson Chung | bbb3d3d | 2016-01-30 01:09:20 +0000 | [diff] [blame] | 235 | if (!mInvisible) { |
| 236 | invalidate(); |
| 237 | } |
Winson Chung | 353c0b9 | 2014-10-16 17:43:23 -0700 | [diff] [blame] | 238 | } |
| 239 | |
Winson | 479f744 | 2015-11-25 15:16:27 -0800 | [diff] [blame] | 240 | /** |
Winson | 778f495 | 2016-01-08 10:32:08 -0800 | [diff] [blame] | 241 | * Updates the scale of the bitmap relative to this view. |
Winson | 479f744 | 2015-11-25 15:16:27 -0800 | [diff] [blame] | 242 | */ |
Winson | 778f495 | 2016-01-08 10:32:08 -0800 | [diff] [blame] | 243 | public void updateThumbnailScale() { |
Winson | 2170093 | 2016-03-24 17:26:23 -0700 | [diff] [blame] | 244 | mThumbnailScale = 1f; |
Winson | 479f744 | 2015-11-25 15:16:27 -0800 | [diff] [blame] | 245 | if (mBitmapShader != null) { |
Winson | 2170093 | 2016-03-24 17:26:23 -0700 | [diff] [blame] | 246 | |
| 247 | if (mThumbnailInfo != null) { |
| 248 | System.out.println(mTask.title + " bounds: " + mThumbnailInfo.taskWidth + "x" + mThumbnailInfo.taskHeight + ", " + mThumbnailInfo.screenOrientation); |
| 249 | } |
| 250 | |
| 251 | // We consider this a stack task if it is not freeform (ie. has no bounds) or has been |
| 252 | // dragged into the stack from the freeform workspace |
| 253 | boolean isStackTask = !mTask.isFreeformTask() || mTask.bounds == null; |
| 254 | if (mTaskViewRect.isEmpty() || mThumbnailInfo == null || |
| 255 | mThumbnailInfo.taskWidth == 0 || mThumbnailInfo.taskHeight == 0) { |
| 256 | // If we haven't measured or the thumbnail is invalid, skip the thumbnail drawing |
| 257 | // and only draw the background color |
| 258 | mThumbnailScale = 0f; |
| 259 | } else if (isStackTask) { |
| 260 | float invThumbnailScale = 1f / mFullscreenThumbnailScale; |
| 261 | if (mOrientation == Configuration.ORIENTATION_PORTRAIT) { |
| 262 | if (mThumbnailInfo.screenOrientation == Configuration.ORIENTATION_PORTRAIT) { |
| 263 | // If we are in the same orientation as the screenshot, just scale it to the |
| 264 | // width of the task view |
| 265 | mThumbnailScale = (float) mTaskViewRect.width() / mThumbnailRect.width(); |
| 266 | } else { |
| 267 | // Scale the landscape thumbnail up to app size, then scale that to the task |
| 268 | // view size to match other portrait screenshots |
| 269 | mThumbnailScale = invThumbnailScale * |
| 270 | ((float) mTaskViewRect.width() / mDisplayRect.width()); |
| 271 | } |
| 272 | } else { |
| 273 | // Otherwise, scale the screenshot to fit 1:1 in the current orientation |
| 274 | mThumbnailScale = invThumbnailScale; |
| 275 | } |
Winson | 778f495 | 2016-01-08 10:32:08 -0800 | [diff] [blame] | 276 | } else { |
| 277 | // Otherwise, if this is a freeform task with task bounds, then scale the thumbnail |
| 278 | // to fit the entire bitmap into the task bounds |
Winson | 2170093 | 2016-03-24 17:26:23 -0700 | [diff] [blame] | 279 | mThumbnailScale = Math.min( |
Winson | 778f495 | 2016-01-08 10:32:08 -0800 | [diff] [blame] | 280 | (float) mTaskViewRect.width() / mThumbnailRect.width(), |
| 281 | (float) mTaskViewRect.height() / mThumbnailRect.height()); |
| 282 | } |
Winson | 2170093 | 2016-03-24 17:26:23 -0700 | [diff] [blame] | 283 | mScaleMatrix.setScale(mThumbnailScale, mThumbnailScale); |
Selim Cinek | e8199c5 | 2014-09-17 04:03:52 +0200 | [diff] [blame] | 284 | mBitmapShader.setLocalMatrix(mScaleMatrix); |
| 285 | } |
Winson | 479f744 | 2015-11-25 15:16:27 -0800 | [diff] [blame] | 286 | if (!mInvisible) { |
| 287 | invalidate(); |
| 288 | } |
| 289 | } |
| 290 | |
Winson Chung | 353c0b9 | 2014-10-16 17:43:23 -0700 | [diff] [blame] | 291 | /** Updates the clip rect based on the given task bar. */ |
| 292 | void updateClipToTaskBar(View taskBar) { |
| 293 | mTaskBar = taskBar; |
| 294 | int top = (int) Math.max(0, taskBar.getTranslationY() + |
| 295 | taskBar.getMeasuredHeight() - 1); |
| 296 | mClipRect.set(0, top, getMeasuredWidth(), getMeasuredHeight()); |
| 297 | setClipBounds(mClipRect); |
| 298 | } |
| 299 | |
| 300 | /** Updates the visibility of the the thumbnail. */ |
| 301 | void updateThumbnailVisibility(int clipBottom) { |
| 302 | boolean invisible = mTaskBar != null && (getHeight() - clipBottom) <= mTaskBar.getHeight(); |
| 303 | if (invisible != mInvisible) { |
| 304 | mInvisible = invisible; |
| 305 | if (!mInvisible) { |
| 306 | updateThumbnailPaintFilter(); |
| 307 | } |
Winson Chung | 353c0b9 | 2014-10-16 17:43:23 -0700 | [diff] [blame] | 308 | } |
| 309 | } |
| 310 | |
| 311 | /** |
| 312 | * Sets the dim alpha, only used when we are not using hardware layers. |
| 313 | * (see RecentsConfiguration.useHardwareLayers) |
| 314 | */ |
Selim Cinek | e8199c5 | 2014-09-17 04:03:52 +0200 | [diff] [blame] | 315 | public void setDimAlpha(float dimAlpha) { |
| 316 | mDimAlpha = dimAlpha; |
Winson Chung | 353c0b9 | 2014-10-16 17:43:23 -0700 | [diff] [blame] | 317 | updateThumbnailPaintFilter(); |
| 318 | } |
| 319 | |
| 320 | /** Binds the thumbnail view to the task */ |
Winson | 2170093 | 2016-03-24 17:26:23 -0700 | [diff] [blame] | 321 | void rebindToTask(Task t, ActivityManager.TaskThumbnailInfo thumbnailInfo, |
| 322 | boolean disabledInSafeMode) { |
Winson | 778f495 | 2016-01-08 10:32:08 -0800 | [diff] [blame] | 323 | mTask = t; |
Winson | 8be1634 | 2016-02-09 11:53:27 -0800 | [diff] [blame] | 324 | mDisabledInSafeMode = disabledInSafeMode; |
Winson Chung | 353c0b9 | 2014-10-16 17:43:23 -0700 | [diff] [blame] | 325 | if (t.thumbnail != null) { |
Winson | 2170093 | 2016-03-24 17:26:23 -0700 | [diff] [blame] | 326 | setThumbnail(t.thumbnail, thumbnailInfo); |
Winson Chung | 1af8eda | 2016-02-05 17:55:56 +0000 | [diff] [blame] | 327 | if (t.colorBackground != 0) { |
| 328 | mBgFillPaint.setColor(t.colorBackground); |
| 329 | } |
Winson Chung | 353c0b9 | 2014-10-16 17:43:23 -0700 | [diff] [blame] | 330 | } else { |
Winson | 2170093 | 2016-03-24 17:26:23 -0700 | [diff] [blame] | 331 | setThumbnail(null, null); |
Winson Chung | 353c0b9 | 2014-10-16 17:43:23 -0700 | [diff] [blame] | 332 | } |
Selim Cinek | e8199c5 | 2014-09-17 04:03:52 +0200 | [diff] [blame] | 333 | } |
| 334 | |
Winson Chung | 37c8d8e | 2014-03-24 14:53:07 -0700 | [diff] [blame] | 335 | /** Unbinds the thumbnail view from the task */ |
| 336 | void unbindFromTask() { |
Winson | 778f495 | 2016-01-08 10:32:08 -0800 | [diff] [blame] | 337 | mTask = null; |
Winson | 2170093 | 2016-03-24 17:26:23 -0700 | [diff] [blame] | 338 | setThumbnail(null, null); |
Winson Chung | 37c8d8e | 2014-03-24 14:53:07 -0700 | [diff] [blame] | 339 | } |
Winson Chung | 37c8d8e | 2014-03-24 14:53:07 -0700 | [diff] [blame] | 340 | } |