2013年5月13日 星期一

Android智障的oom(out of memory)原因: 圖片讀進來超大!? 原來是放錯資料夾

這問題雖然低能, 但我相信一定很多人不知道, 卻又深受其苦.

Android 在load image的時候會自動做scale的動作, 舉個例子

如果我把圖片放在 drawable-ldpi或drawable中, 卻使用被歸類於hdpi的手機來讀這張圖片,

則在圖片decode的時候會順便再多做scale的動作.

像我這種懶人開發的時候通常只會針對一種resolution生一組圖片然後把它隨便找一個資料夾放, 

例如開一個drawable資料夾然後全都放裡面, 跑起來有看到圖就以為沒差. 

然後每次oom都在想android是搞毛啊沒幾張圖就亂噴.

其實是當代的手機幾乎都是hdpi以上,所以如果在drawable-ldpi中放大resolution的圖片,

則在圖片decode的時候會被沒有必要的scale到超級大. 所以memory很容易就爆了.

懶人解法是將圖片全部放到drawable-xdpi下面, 就能保證只會scale down了.



在網路上survey了很久, 有一堆解法都是自己在loading bitmap的時候手動scale, 不然就是自己做memory 控管寫了一堆扣.  結果搞了半天才發現是放對資料夾就沒事了.

話說雖然在android sdk document中似乎有提到會自動scale, 但誰會一個字一個字看完document在開始寫啊= =+

  

以上解法雖然輕鬆愉快, 但依然會有memory的浪費, 因為放進project的圖片不可能完全適合每一款手機的螢幕手機,

android document 中有提到如何在load bitmap的時候針對實際需求去scale


其中的 Loading Large Bitmaps Efficiently 段落就是在說這個.
流程大概是先讀出image的大小 -> 再根據實際需要大小算出比例 -> 在實際decode bitmap的時候做scale.  雖然不難但是有點煩.

我個人只覺得只要能避免掉將high resolution image 放到 較低的資料夾所導致的多餘scale
對基本app來說已經很足夠了 ^.<

沒有留言:

張貼留言