Android用戶端中Bitmap的下載過程和緩衝機制

來源:互聯網
上載者:User

標籤:android   des   style   color   使用   strong   

載入流程:
if(記憶體命中){     從記憶體中讀取}else{     create AsyncTasks,task中的多個Runnable是通過堆棧先進後出的方式來調度,而非隊列式的先進先出,目的是最先載入使用者最近划到或開啟的圖片。     } AsyncTask: //do in background——該後台進程在使用者scroll列表的時候會暫停,從而減小了列表划動時cpu的overhead,此方法也被ImageLoader和facebook的官方app所使用。if(磁碟快取命中){     從緩衝中讀取    }else{     從網路下載  成功後,存入磁碟緩衝並且存入記憶體}  記憶體配置圖片管理LruCache,容量為1/10運行時記憶體。以nexus 4為例,記憶體2G,jvm為樣本app分配的可用記憶體為512MB,那麼記憶體中的圖片LruCache大小為51.2MB。當達到容量後,不要直接recycle bitmap,而是將bitmap加到一個WeakReference的Map中;否則在小記憶體手機上,很可能會recycle掉一些還被引用著的bitmap。  緩衝圖片管理ChocolateCache,策略類似於LruCache,但是對IO讀寫速度和命中率都做了最佳化(鳴謝 伯奎)  下載和解析圖片的注意事項黑圖問題:                             // 如果不根據這個固定的length來產生byte[],而是直接decode                            // inputstream ,會造成黑圖(圖片出現黑色的矩形)                            imgData =  new  byte[length];                              byte[] temp =  new  byte[512];                             int readLen = 0;                             int destPos = 0;                              while ((readLen = mInputStream.read(temp)) > 0) {                                System.arraycopy(temp, 0, imgData, destPos, readLen);                                destPos += readLen;                           } 機型和網路相容性問題:三星note3在CDMA網路下得到的是GZIPInputStream(length為-1),其他機型和情境都是FixedLengthInputStream(length為正常大小),所以當length=-1時,採用最基本的InputStream->OutputStream->ByteArray的方式產生映像的位元組數組 不同解析度顯示時的自動縮放問題(尤其是表情模組)解析圖片應採用BitmapFactory.decodeStream而不是BitmapFactory.decodeByteArray,因為後者在從source density到target density轉換時,不會自動縮放。例如,某250x250的圖片,預設的density是320,但是LG的G2手機density為480,所以此圖片應按照480/320=1.5的比例放大並顯示到G2手機上。但是decodeByteArray之後得到的圖片長寬仍然是250x250,但是如果使用decodeStream則會得到長寬均為250*1.5=375的圖片,從而實現了最佳的顯示效果。 根本原因詳見源碼:      public  static Bitmap decodeStream (InputStream is, Rect outPadding, Options opts) {       ... ...             if (opts ==  null || (opts. inScaled && opts. inBitmap ==  null)) {                 float scale = 1.0f;                 int targetDensity = 0;                 if (opts !=  null) {                     final  int density = opts. inDensity;                    targetDensity = opts. inTargetDensity;                     if (density != 0 && targetDensity != 0) {                        scale = targetDensity / (  float) density; //請注意這裡有計算縮放比例,而 decodeByteArray未進行此項操作
                    }                }                 bm =  nativeDecodeAsset(asset, outPadding, opts,  true, scale);                 if (bm !=  null && targetDensity != 0) bm.setDensity(targetDensity);                 finish =  false;            }  else {                bm =  nativeDecodeAsset(asset, outPadding, opts);            }        }   ... ...      public  static Bitmap decodeByteArray ( byte [] data,  int offset,  int length, Options opts) {         if ((offset | length) < 0 || data. length < offset + length) {             throw  new ArrayIndexOutOfBoundsException();        }        Bitmap bm =  nativeDecodeByteArray(data, offset, length, opts);          if (bm ==  null && opts !=  null && opts. inBitmap !=  null) {             throw  new IllegalArgumentException( "Problem decoding into existing bitmap");        }         return bm;    }   情境策略網狀圖片按原尺寸處理本地圖片或拍照圖片,因為經常是高清大圖,所以需要根據具體情況設定採樣率,減小decode bitmap和write to cache時的記憶體佔用(鳴謝 風念)   

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.