少しoom対策
[ofnhwx.olib.git] / src / jp / gr / java_conf / ofnhwx / olib / utils / OBitmap.java
blobd20d55f79504aca41dfca891ad9c716e0936ea7d
1 package jp.gr.java_conf.ofnhwx.olib.utils;
3 import java.io.BufferedOutputStream;
4 import java.io.ByteArrayOutputStream;
5 import java.io.InputStream;
6 import java.io.OutputStream;
8 import android.content.Context;
9 import android.content.res.Resources;
10 import android.graphics.Bitmap;
11 import android.graphics.BitmapFactory;
12 import android.graphics.Canvas;
13 import android.graphics.drawable.BitmapDrawable;
14 import android.graphics.drawable.Drawable;
15 import android.net.Uri;
17 /**
18 * ビットマップを便利に使うための自分用クラス.
19 * @author yuta
21 public final class OBitmap {
23 private OBitmap() {}
25 /**
26 * Bitmapのサイズを取得するための{@link BitmapFactory.Options}を作成する.
27 * @return `<code>{@link BitmapFactory.Options#inJustDecodeBounds} = true</code>'が設定された<code>Options</code>
29 private static final BitmapFactory.Options createOptions() {
30 BitmapFactory.Options opt = new BitmapFactory.Options();
31 opt.inPurgeable = true;
32 opt.inJustDecodeBounds = true;
33 return opt;
36 /**
37 * Bitmapをリサイズして作成するための{@link BitmapFactory.Options}を作成する.
38 * @param base {@link #createOptions()}で作成した<code>Options</code>
39 * @param max 縦(or 横)の最大サイズ
40 * @return サイズ関連の設定を行った<code>Options</code>
42 private static final BitmapFactory.Options createOptions(BitmapFactory.Options base, float max) {
43 BitmapFactory.Options opt = new BitmapFactory.Options();
44 opt.inPurgeable = true;
45 opt.inInputShareable = true;
46 opt.inSampleSize = (int)Math.floor(Math.max(base.outHeight, base.outWidth) / max);
47 return opt;
50 /**
51 * DrawableからBitmap画像をリサイズして取得.
52 * @param drawable
53 * @return Bitmap画像(drawableが'null'なら'null'を返す)
55 public static final Bitmap getBitmap(Drawable drawable) {
56 if (drawable == null) {
57 return null;
59 if (drawable instanceof BitmapDrawable) {
60 return ((BitmapDrawable)drawable).getBitmap();
62 int w = drawable.getIntrinsicWidth();
63 int h = drawable.getIntrinsicHeight();
64 Bitmap b = Bitmap.createBitmap(w, h, Bitmap.Config.ARGB_4444);
65 Canvas canvas = new Canvas(b);
66 drawable.setBounds(0, 0, w, h);
67 drawable.draw(canvas);
68 return b;
71 /**
72 * DrawableからBitmap画像をリサイズして取得.
73 * @param drawable
74 * @param size リサイズ後のサイズ(幅・高さ)
75 * @return リサイズしたBitmap画像(drawableが'null'なら'null'を返す)
77 public static final Bitmap getBitmap(Drawable drawable, int size) {
78 Bitmap bitmap = getBitmap(drawable);
79 Bitmap result = resizeBitmap(bitmap, size);
80 bitmap.recycle();
81 bitmap = null;
82 return result;
85 /**
86 * リソースIDからBitmap画像を生成.
87 * @param context
88 * @param id Bitmap画像のリソースID
89 * @param max 縦・横の最大サイズ
90 * @return Bitmap画像
92 private static final Bitmap decodeResourceInternal(Context context, int id, int max) {
93 Resources res = context.getResources();
94 BitmapFactory.Options options = createOptions();
95 BitmapFactory.decodeResource(res, id, options);
96 return BitmapFactory.decodeResource(res, id, createOptions(options, max));
99 /**
100 * リソースIDからBitmap画像をリサイズして取得.
101 * @param context
102 * @param id Bitmap画像のリソースID
103 * @param width リサイズ後の幅
104 * @param height リサイズ後の高さ
105 * @return リサイズしたBitmap画像(bitmapが'null'なら'null'を返す)
107 public static final Bitmap decodeResource(Context context, int id, int width, int height) {
108 Bitmap bitmap = decodeResourceInternal(context, id, Math.max(width, height));
109 Bitmap result = resizeBitmap(bitmap, width, height);
110 bitmap.recycle();
111 bitmap = null;
112 return result;
116 * リソースIDからBitmap画像をリサイズして取得.
117 * @param context
118 * @param id Bitmap画像のリソースID
119 * @param size リサイズ後のサイズ(幅・高さ)
120 * @return リサイズしたBitmap画像(bitmapが'null'なら'null'を返す)
122 public static final Bitmap decodeResource(Context context, int id, int size) {
123 Bitmap bitmap = decodeResourceInternal(context, id, size);
124 Bitmap result = resizeBitmap(bitmap, size);
125 bitmap.recycle();
126 bitmap = null;
127 return result;
131 * リソースIDからBitmap画像をリサイズして取得.
132 * @param context
133 * @param id Bitmap画像のリソースID
134 * @param size リサイズ後のサイズ(幅・高さ)
135 * @param keepAspect アスペクト比を維持してリサイズするかどうか
136 * @return リサイズしたBitmap画像(bitmapが'null'なら'null'を返す)
138 public static final Bitmap decodeResource(Context context, int id, int size, boolean keepAspect) {
139 Bitmap bitmap = decodeResourceInternal(context, id, size);
140 Bitmap result = resizeBitmap(bitmap, size, keepAspect);
141 bitmap.recycle();
142 bitmap = null;
143 return result;
146 // ---------- Bitmap画像のリサイズ(バイトストリーム) ---------- //
149 * バイト配列からBitmap画像を生成.
150 * @param data Bitmap画像のバイト配列
151 * @param max
152 * @return Bitmap画像
154 private static final Bitmap decodeByteArrayInternal(byte[] data, float max) {
155 if (data == null) {
156 return null;
158 BitmapFactory.Options options = createOptions();
159 BitmapFactory.decodeByteArray(data, 0, data.length, options);
160 return BitmapFactory.decodeByteArray(data, 0, data.length, createOptions(options, max));
164 * バイト配列からBitmap画像をリサイズして取得.
165 * @param data Bitmap画像のバイト配列
166 * @param width リサイズ後の幅
167 * @param height リサイズ後の高さ
168 * @return リサイズしたBitmap画像(bitmapが'null'なら'null'を返す)
170 public static final Bitmap decodeByteArray(byte[] data, int width, int height) {
171 Bitmap bitmap = decodeByteArrayInternal(data, Math.max(width, height));
172 Bitmap result = resizeBitmap(bitmap, width, height);
173 bitmap.recycle();
174 bitmap = null;
175 return result;
179 * バイト配列からBitmap画像をリサイズして取得.
180 * @param data Bitmap画像のバイト配列
181 * @param size リサイズ後のサイズ(幅・高さ)
182 * @return リサイズしたBitmap画像(bitmapが'null'なら'null'を返す)
184 public static final Bitmap decodeByteArray(byte[] data, int size) {
185 Bitmap bitmap = decodeByteArrayInternal(data, size);
186 Bitmap result = resizeBitmap(bitmap, size);
187 bitmap.recycle();
188 bitmap = null;
189 return result;
193 * バイト配列からBitmap画像をリサイズして取得.
194 * @param data Bitmap画像のバイト配列
195 * @param size リサイズ後のサイズ(幅・高さ)
196 * @param keepAspect アスペクト比を維持してリサイズするかどうか
197 * @return リサイズしたBitmap画像(bitmapが'null'なら'null'を返す)
199 public static final Bitmap decodeByteArray(byte[] data, int size, boolean keepAspect) {
200 Bitmap bitmap = decodeByteArrayInternal(data, size);
201 Bitmap result = resizeBitmap(bitmap, size, keepAspect);
202 bitmap.recycle();
203 bitmap = null;
204 return result;
208 * Uriの指定する内容をバイト配列に格納して返す.
209 * @param context
210 * @return
212 private static final byte[] getBytesInternal(Context context, Uri uri) {
213 ByteArrayOutputStream result = new ByteArrayOutputStream();
214 OutputStream os = new BufferedOutputStream(result);
215 InputStream is = null;
216 try {
217 int c;
218 is = context.getContentResolver().openInputStream(uri);
219 while ((c = is.read()) != -1) {
220 os.write(c);
222 os.flush();
223 } catch (Exception e) {
224 return null;
225 } finally {
226 try {
227 is.close();
228 } catch (Exception e) {
231 return result.toByteArray();
235 * UriからBitmap画像をリサイズして取得.
236 * @param context
237 * @param uri
238 * @param width リサイズ後の幅
239 * @param height リサイズ後の高さ
240 * @return リサイズしたBitmap画像(bitmapが'null'なら'null'を返す)
242 public static final Bitmap decodeUri(Context context, Uri uri, int width, int height) {
243 byte[] bitmap = getBytesInternal(context, uri);
244 return decodeByteArray(bitmap, width, height);
248 * UriからBitmap画像をリサイズして取得.
249 * @param context
250 * @param uri
251 * @param size リサイズ後のサイズ(幅・高さ)
252 * @return リサイズしたBitmap画像(bitmapが'null'なら'null'を返す)
254 public static final Bitmap decodeUri(Context context, Uri uri, int size) {
255 byte[] bitmap = getBytesInternal(context, uri);
256 return decodeByteArray(bitmap, size);
260 * UriからBitmap画像をリサイズして取得.
261 * @param context
262 * @param uri
263 * @param size リサイズ後のサイズ(幅・高さ)
264 * @param keepAspect アスペクト比を維持してリサイズするかどうか
265 * @return リサイズしたBitmap画像(bitmapが'null'なら'null'を返す)
267 public static final Bitmap decodeUri(Context context, Uri uri, int size, boolean keepAspect) {
268 byte[] bitmap = getBytesInternal(context, uri);
269 return decodeByteArray(bitmap, size, keepAspect);
273 * Bitmap画像のリサイズ.
274 * @param bitmap リサイズするBitmap画像
275 * @param width リサイズ後の幅
276 * @param height リサイズ後の高さ
277 * @return リサイズしたBitmap画像(bitmapが'null'なら'null'を返す)
279 public static final Bitmap resizeBitmap(Bitmap bitmap, int width, int height) {
280 if (bitmap == null) {
281 return null;
283 // リサイズ前のチェック
284 int w = bitmap.getWidth();
285 int h = bitmap.getHeight();
286 if (w == width && h == height) {
287 return bitmap;
289 // リサイズ
290 return Bitmap.createScaledBitmap(bitmap, width, height, true);
294 * Bitmap画像のリサイズ.
295 * @param bitmap リサイズするBitmap画像
296 * @param size リサイズ後のサイズ(幅・高さ)
297 * @return リサイズしたBitmap画像(bitmapが'null'なら'null'を返す)
299 public static final Bitmap resizeBitmap(Bitmap bitmap, int size) {
300 return resizeBitmap(bitmap, size, size);
304 * Bitmap画像のリサイズ.
305 * @param bitmap リサイズするBitmap画像
306 * @param size リサイズ後のサイズ(幅・高さ)
307 * @param keepAspect アスペクト比を維持してリサイズするかどうか
308 * @return リサイズしたBitmap画像(bitmapが'null'なら'null'を返す)
310 public static final Bitmap resizeBitmap(Bitmap bitmap, int size, boolean keepAspect) {
311 if (bitmap == null) {
312 return null;
314 // アスペクト比関連でいろいろと作業
315 int width = bitmap.getWidth();
316 int height = bitmap.getHeight();
317 if (width == height || !keepAspect) {
318 return resizeBitmap(bitmap, size, size);
319 } else if (width > height) {
320 return resizeBitmap(bitmap, size, size * height / width);
321 } else if (width < height) {
322 return resizeBitmap(bitmap, size * width / height, size);
324 return null;