2012-03-23

AndroidでOutOfMemoryError: bitmap size exceeds VM budget

「java.lang.OutOfMemoryError: bitmap size exceeds VM budget」というエラーに悩まされています。
エラーログは、次のような具合です。
03-22 23:43:50.148: E/AndroidRuntime(15933): Caused by: java.lang.OutOfMemoryError: bitmap size exceeds VM budget
03-22 23:43:50.148: E/AndroidRuntime(15933):  at android.graphics.Bitmap.nativeCreate(Native Method)
03-22 23:43:50.148: E/AndroidRuntime(15933):  at android.graphics.Bitmap.createBitmap(Bitmap.java:477)
03-22 23:43:50.148: E/AndroidRuntime(15933):  at android.graphics.Bitmap.createBitmap(Bitmap.java:444)
03-22 23:43:50.148: E/AndroidRuntime(15933):  at android.graphics.Bitmap.createScaledBitmap(Bitmap.java:349)
03-22 23:43:50.148: E/AndroidRuntime(15933):  at android.graphics.BitmapFactory.finishDecode(BitmapFactory.java:498)
03-22 23:43:50.148: E/AndroidRuntime(15933):  at android.graphics.BitmapFactory.decodeStream(BitmapFactory.java:473)
03-22 23:43:50.148: E/AndroidRuntime(15933):  at android.graphics.BitmapFactory.decodeResourceStream(BitmapFactory.java:336)
03-22 23:43:50.148: E/AndroidRuntime(15933):  at android.graphics.BitmapFactory.decodeResource(BitmapFactory.java:359)
03-22 23:43:50.148: E/AndroidRuntime(15933):  at android.graphics.BitmapFactory.decodeResource(BitmapFactory.java:385)
03-22 23:43:50.148: E/AndroidRuntime(15933):  at android.graphics.drawable.BitmapDrawable.inflate(BitmapDrawable.java:373)
03-22 23:43:50.148: E/AndroidRuntime(15933):  at android.graphics.drawable.Drawable.createFromXmlInner(Drawable.java:787)
03-22 23:43:50.148: E/AndroidRuntime(15933):  at android.graphics.drawable.StateListDrawable.inflate(StateListDrawable.java:172)
起動と終了を2〜3回繰り返すとエラーになるので、メモリリークの可能性がありますが、コードを読み直してもさっぱり分かりません。単純に、Drawableのサイズが大きすぎるのかもしれません。
ログによれば、StateListDrawableを表示するときにメモリーが足りなくなっています。他のログから推察すると、エラーが生じているのは、500x740のpngファイルでステートを4つ定義してあるDrawableのようです。PNGファイルのサイズは、最大で56KBでした。
アプリを実行するとメモリを50MBくらい消費していました。

とりあえず次のような対策をとりました。

  • 画像のサイズを小さくする
  • StateListDrawableのステータスの数を減らす
  • 背景で9patchやtileを利用できるところは利用する
これで、OutOfMemoryErrorが発生することをいまのところ防げていますが、やはり、やっていることの割にメモリの消費量が多すぎるような気がします。

0 件のコメント: