blob: dc61be36624e010f53585142e71e96cabaea5dcb [file] [log] [blame]
The Android Open Source Project31dd5032009-03-03 19:32:27 -08001/*
2 * Copyright (C) 2008 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
Joe Onoratoa5902522009-07-30 13:37:37 -070017package com.android.launcher2;
The Android Open Source Project31dd5032009-03-03 19:32:27 -080018
Mitsuru Oshima583ed3b2009-05-12 19:19:10 -070019import android.graphics.drawable.BitmapDrawable;
The Android Open Source Project31dd5032009-03-03 19:32:27 -080020import android.graphics.drawable.Drawable;
21import android.graphics.drawable.PaintDrawable;
22import android.graphics.Bitmap;
23import android.graphics.PixelFormat;
24import android.graphics.Canvas;
25import android.graphics.PaintFlagsDrawFilter;
26import android.graphics.Paint;
27import android.graphics.Rect;
Dianne Hackborn32ce7f12009-07-22 21:56:50 -070028import android.util.DisplayMetrics;
The Android Open Source Project31dd5032009-03-03 19:32:27 -080029import android.content.res.Resources;
30import android.content.Context;
31
32/**
33 * Various utilities shared amongst the Launcher's classes.
34 */
35final class Utilities {
36 private static int sIconWidth = -1;
37 private static int sIconHeight = -1;
38
39 private static final Paint sPaint = new Paint();
40 private static final Rect sBounds = new Rect();
41 private static final Rect sOldBounds = new Rect();
42 private static Canvas sCanvas = new Canvas();
43
44 static {
45 sCanvas.setDrawFilter(new PaintFlagsDrawFilter(Paint.DITHER_FLAG,
46 Paint.FILTER_BITMAP_FLAG));
47 }
48
49 static Bitmap centerToFit(Bitmap bitmap, int width, int height, Context context) {
50 final int bitmapWidth = bitmap.getWidth();
51 final int bitmapHeight = bitmap.getHeight();
52
53 if (bitmapWidth < width || bitmapHeight < height) {
54 int color = context.getResources().getColor(R.color.window_background);
55
56 Bitmap centered = Bitmap.createBitmap(bitmapWidth < width ? width : bitmapWidth,
57 bitmapHeight < height ? height : bitmapHeight, Bitmap.Config.RGB_565);
Dianne Hackborn32ce7f12009-07-22 21:56:50 -070058 centered.setDensity(bitmap.getDensity());
The Android Open Source Project31dd5032009-03-03 19:32:27 -080059 Canvas canvas = new Canvas(centered);
60 canvas.drawColor(color);
61 canvas.drawBitmap(bitmap, (width - bitmapWidth) / 2.0f, (height - bitmapHeight) / 2.0f,
62 null);
63
64 bitmap = centered;
65 }
66
67 return bitmap;
68 }
69
70 /**
71 * Returns a Drawable representing the thumbnail of the specified Drawable.
72 * The size of the thumbnail is defined by the dimension
73 * android.R.dimen.launcher_application_icon_size.
74 *
75 * This method is not thread-safe and should be invoked on the UI thread only.
76 *
77 * @param icon The icon to get a thumbnail of.
78 * @param context The application's context.
79 *
80 * @return A thumbnail for the specified icon or the icon itself if the
81 * thumbnail could not be created.
82 */
83 static Drawable createIconThumbnail(Drawable icon, Context context) {
84 if (sIconWidth == -1) {
85 final Resources resources = context.getResources();
Mitsuru Oshima583ed3b2009-05-12 19:19:10 -070086 sIconWidth = sIconHeight = (int) resources.getDimension(android.R.dimen.app_icon_size);
The Android Open Source Project31dd5032009-03-03 19:32:27 -080087 }
88
89 int width = sIconWidth;
90 int height = sIconHeight;
91
Mitsuru Oshima583ed3b2009-05-12 19:19:10 -070092 float scale = 1.0f;
The Android Open Source Project31dd5032009-03-03 19:32:27 -080093 if (icon instanceof PaintDrawable) {
94 PaintDrawable painter = (PaintDrawable) icon;
95 painter.setIntrinsicWidth(width);
96 painter.setIntrinsicHeight(height);
Mitsuru Oshima583ed3b2009-05-12 19:19:10 -070097 } else if (icon instanceof BitmapDrawable) {
Dianne Hackborn32ce7f12009-07-22 21:56:50 -070098 // Ensure the bitmap has a density.
Mitsuru Oshima583ed3b2009-05-12 19:19:10 -070099 BitmapDrawable bitmapDrawable = (BitmapDrawable) icon;
100 Bitmap bitmap = bitmapDrawable.getBitmap();
Dianne Hackborn32ce7f12009-07-22 21:56:50 -0700101 if (bitmap.getDensity() == Bitmap.DENSITY_NONE) {
102 bitmapDrawable.setTargetDensity(context.getResources().getDisplayMetrics());
Mitsuru Oshima583ed3b2009-05-12 19:19:10 -0700103 }
The Android Open Source Project31dd5032009-03-03 19:32:27 -0800104 }
Mitsuru Oshima583ed3b2009-05-12 19:19:10 -0700105 int iconWidth = icon.getIntrinsicWidth();
106 int iconHeight = icon.getIntrinsicHeight();
The Android Open Source Project31dd5032009-03-03 19:32:27 -0800107
108 if (width > 0 && height > 0) {
Mitsuru Oshima583ed3b2009-05-12 19:19:10 -0700109 if (width < iconWidth || height < iconHeight || scale != 1.0f) {
The Android Open Source Project31dd5032009-03-03 19:32:27 -0800110 final float ratio = (float) iconWidth / iconHeight;
111
112 if (iconWidth > iconHeight) {
113 height = (int) (width / ratio);
114 } else if (iconHeight > iconWidth) {
115 width = (int) (height * ratio);
116 }
117
118 final Bitmap.Config c = icon.getOpacity() != PixelFormat.OPAQUE ?
119 Bitmap.Config.ARGB_8888 : Bitmap.Config.RGB_565;
120 final Bitmap thumb = Bitmap.createBitmap(sIconWidth, sIconHeight, c);
121 final Canvas canvas = sCanvas;
122 canvas.setBitmap(thumb);
123 // Copy the old bounds to restore them later
124 // If we were to do oldBounds = icon.getBounds(),
125 // the call to setBounds() that follows would
126 // change the same instance and we would lose the
127 // old bounds
128 sOldBounds.set(icon.getBounds());
129 final int x = (sIconWidth - width) / 2;
130 final int y = (sIconHeight - height) / 2;
131 icon.setBounds(x, y, x + width, y + height);
132 icon.draw(canvas);
133 icon.setBounds(sOldBounds);
134 icon = new FastBitmapDrawable(thumb);
135 } else if (iconWidth < width && iconHeight < height) {
136 final Bitmap.Config c = Bitmap.Config.ARGB_8888;
137 final Bitmap thumb = Bitmap.createBitmap(sIconWidth, sIconHeight, c);
138 final Canvas canvas = sCanvas;
139 canvas.setBitmap(thumb);
140 sOldBounds.set(icon.getBounds());
141 final int x = (width - iconWidth) / 2;
142 final int y = (height - iconHeight) / 2;
143 icon.setBounds(x, y, x + iconWidth, y + iconHeight);
144 icon.draw(canvas);
145 icon.setBounds(sOldBounds);
146 icon = new FastBitmapDrawable(thumb);
147 }
148 }
149
150 return icon;
151 }
152
153 /**
154 * Returns a Bitmap representing the thumbnail of the specified Bitmap.
155 * The size of the thumbnail is defined by the dimension
156 * android.R.dimen.launcher_application_icon_size.
157 *
158 * This method is not thread-safe and should be invoked on the UI thread only.
159 *
160 * @param bitmap The bitmap to get a thumbnail of.
161 * @param context The application's context.
162 *
163 * @return A thumbnail for the specified bitmap or the bitmap itself if the
164 * thumbnail could not be created.
165 */
166 static Bitmap createBitmapThumbnail(Bitmap bitmap, Context context) {
167 if (sIconWidth == -1) {
168 final Resources resources = context.getResources();
169 sIconWidth = sIconHeight = (int) resources.getDimension(
170 android.R.dimen.app_icon_size);
171 }
172
173 int width = sIconWidth;
174 int height = sIconHeight;
175
176 final int bitmapWidth = bitmap.getWidth();
177 final int bitmapHeight = bitmap.getHeight();
178
179 if (width > 0 && height > 0 && (width < bitmapWidth || height < bitmapHeight)) {
180 final float ratio = (float) bitmapWidth / bitmapHeight;
181
182 if (bitmapWidth > bitmapHeight) {
183 height = (int) (width / ratio);
184 } else if (bitmapHeight > bitmapWidth) {
185 width = (int) (height * ratio);
186 }
187
188 final Bitmap.Config c = (width == sIconWidth && height == sIconHeight) ?
189 bitmap.getConfig() : Bitmap.Config.ARGB_8888;
190 final Bitmap thumb = Bitmap.createBitmap(sIconWidth, sIconHeight, c);
191 final Canvas canvas = sCanvas;
192 final Paint paint = sPaint;
193 canvas.setBitmap(thumb);
194 paint.setDither(false);
195 paint.setFilterBitmap(true);
196 sBounds.set((sIconWidth - width) / 2, (sIconHeight - height) / 2, width, height);
197 sOldBounds.set(0, 0, bitmapWidth, bitmapHeight);
198 canvas.drawBitmap(bitmap, sOldBounds, sBounds, paint);
199 return thumb;
200 }
201
202 return bitmap;
203 }
204}