Android圖片三級緩衝策略

來源:互聯網
上載者:User

標籤:緩衝策略

1.簡介

Android緩衝原理都是一樣,可以自己封裝。

三級緩衝:

 1.記憶體緩衝:緩衝在記憶體中,基於LRU(least recently used )演算法,機器重啟消失。 2.本機快取。緩衝在本地中。一般索引值對形式。(url,filepath) 3.網路緩衝。從網路載入資源,然後緩衝在記憶體、本地中。

2.實現步驟

2.1 記憶體緩衝:

[java] view plain copy
public class MemoryCacheUtils {
private LruCache<String,Bitmap> mMemoryCache;
public MemoryCacheUtils(){
long maxMemory = Runtime.getRuntime().maxMemory()/8;//得到手機最大允許記憶體的1/8,即超過指定記憶體,則開始回收
//需要傳入允許的記憶體最大值,虛擬機器預設記憶體16M,真機不一定相同
mMemoryCache=new LruCache<String,Bitmap>((int) maxMemory){
//用於計算每個條目的大小
@Override
protected int sizeOf(String key, Bitmap value) {
int byteCount = value.getByteCount();
return byteCount;
}
};
}
/**

  • 從記憶體中讀圖片
  • @param url
    /
    public Bitmap getBitmapFromMemory(String url) {
    //Bitmap bitmap = mMemoryCache.get(url);//1.強引用方法
    /
    2.弱引用方法
    SoftReference<Bitmap> bitmapSoftReference = mMemoryCache.get(url);
    if (bitmapSoftReference != null) {
    Bitmap bitmap = bitmapSoftReference.get();
    return bitmap;
    }
    */
    if(url==null||"".equals(url)){
    return null;
    }
    Bitmap bitmap = mMemoryCache.get(url);

      return bitmap;  

    }
    /**

  • 往記憶體中寫圖片
  • @param url
  • @param bitmap
    /
    public void setBitmapToMemory(String url, Bitmap bitmap) {
    //mMemoryCache.put(url, bitmap);//1.強引用方法
    /
    2.弱引用方法
    mMemoryCache.put(url, new SoftReference<>(bitmap));
    */
    mMemoryCache.put(url,bitmap);
    }
    }
    2.2本機快取

[java] view plain copy
public class LocalCacheUtils {
private static final String CACHE_PATH= Environment.getExternalStorageDirectory().getAbsolutePath()+"/my/images";
/**

  • 從本地讀取圖片
  • @param url
    */
    public Bitmap getBitmapFromLocal(String url){
    String fileName = null;//把圖片的url當做檔案名稱,並進行MD5加密
    try {
    fileName = MD5Encoder.encode(url); //這裡加不加密無所謂
    File file=new File(CACHE_PATH,fileName);
    Bitmap bitmap = BitmapFactory.decodeStream(new FileInputStream(file));
    return bitmap;
    } catch (Exception e) {
    e.printStackTrace();
    }
    return null;
    }

    /**

  • 從網路擷取圖片後,儲存至本機快取
  • @param url
  • @param bitmap
    */
    public void setBitmapToLocal(String url,Bitmap bitmap){
    try {

         String fileName = MD5Encoder.encode(url);//把圖片的url當做檔案名稱,並進行MD5加密       File file=new File(CACHE_PATH,fileName);       //通過得到檔案的父檔案,判斷父檔案是否存在       File parentFile = file.getParentFile();       if (!parentFile.exists()){           parentFile.mkdirs();       }       //把圖片儲存至本地       bitmap.compress(Bitmap.CompressFormat.JPEG,100,new FileOutputStream(file));   } catch (Exception e) {       e.printStackTrace();   }  

    }
    }
    2.3網路緩衝

[java] view plain copy
public class NetCacheUtils {
private LocalCacheUtils mLocalCacheUtils;
private MemoryCacheUtils mMemoryCacheUtils;

public NetCacheUtils(LocalCacheUtils localCacheUtils, MemoryCacheUtils memoryCacheUtils) {      mLocalCacheUtils = localCacheUtils;      mMemoryCacheUtils = memoryCacheUtils;  }  public NetCacheUtils(){  }  /**  * 從網路下載圖片  * @param ivPic 顯示圖片的imageview  * @param url   下載圖片的網路地址  */  public void getBitmapFromNet(ImageView ivPic, String url) {      new BitmapTask().execute(ivPic, url);//啟動AsyncTask  }  public void getBitmapFromNet(View ivPic, String url) {      new BitmapTask_view().execute(ivPic, url);//啟動AsyncTask  }  public Bitmap getBitmapFromNet(final String url) {      //啟動AsyncTask      return null;  }  /**  * AsyncTask就是對handler和線程池的封裝  * 第一個泛型:參數類型  * 第二個泛型:更新進度的泛型  * 第三個泛型:onPostExecute的返回結果  */  class BitmapTask extends AsyncTask<Object, Void, Bitmap> {      private ImageView ivPic;      private String url;      /**      * 後台耗時操作,存在於子線程中      * @param params      * @return      */      @Override      protected Bitmap doInBackground(Object[] params) {          ivPic = (ImageView) params[0];          url = (String) params[1];          return downLoadBitmap(url);      }      /**      * 更新進度,在主線程中      * @param values      */      @Override      protected void onProgressUpdate(Void[] values) {          super.onProgressUpdate(values);      }      /**      * 耗時方法結束後執行該方法,主線程中      * @param result      */      @Override      protected void onPostExecute(Bitmap result) {          if (result != null) {              ivPic.setImageBitmap(result);              System.out.println("從網路緩衝圖片啦.....");              //從網路擷取圖片後,儲存至本機快取              mLocalCacheUtils.setBitmapToLocal(url, result);              //儲存至記憶體中              mMemoryCacheUtils.setBitmapToMemory(url, result);          }      }  }  /**  * AsyncTask就是對handler和線程池的封裝  * 第一個泛型:參數類型  * 第二個泛型:更新進度的泛型  * 第三個泛型:onPostExecute的返回結果  */  @SuppressLint("NewApi")  class BitmapTask_view extends AsyncTask<Object, Void, Bitmap> {      private View ivPic;      private String url;      /**      * 後台耗時操作,存在於子線程中      * @param params      * @return      */      @Override      protected Bitmap doInBackground(Object[] params) {          ivPic = (View) params[0];          url = (String) params[1];          return downLoadBitmap(url);      }      /**      * 更新進度,在主線程中      * @param values      */      @Override      protected void onProgressUpdate(Void[] values) {          super.onProgressUpdate(values);      }      /**      * 耗時方法結束後執行該方法,主線程中      * @param result      */      @Override      protected void onPostExecute(Bitmap result) {          if (result != null) {              //ivPic.setImageBitmap(result);              if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {                    //Android系統大於等於API16,使用setBackground                    ivPic.setBackground(new BitmapDrawable(result));              } else {                    //Android系統小於API16,使用setBackground                    ivPic.setBackgroundDrawable(new BitmapDrawable(result));              }                System.out.println("從網路緩衝圖片啦.....");              //從網路擷取圖片後,儲存至本機快取              mLocalCacheUtils.setBitmapToLocal(url, result);              //儲存至記憶體中              mMemoryCacheUtils.setBitmapToMemory(url, result);          }      }  }  /**  * 網路下載圖片  * @param url  * @return  */  public Bitmap downLoadBitmap(String url) {      HttpURLConnection conn = null;      try {          conn = (HttpURLConnection) new URL(url).openConnection();          conn.setConnectTimeout(5000);          conn.setReadTimeout(5000);          conn.setRequestMethod("GET");          int responseCode = conn.getResponseCode();          if (responseCode == 200) {              //圖片壓縮              BitmapFactory.Options options = new BitmapFactory.Options();              options.inSampleSize=2;//寬高壓縮為原來的1/2              options.inPreferredConfig=Bitmap.Config.ARGB_4444;              //Bitmap bitmap = BitmapFactory.decodeStream(conn.getInputStream(),null,options);              Bitmap bitmap=BitmapFactory.decodeStream(conn.getInputStream());              return bitmap;          }      } catch (IOException e) {          e.printStackTrace();      }catch (Exception e) {      } finally {          if(conn!=null){              conn.disconnect();          }      }      return null;  }  

}
2.4外部寫一個bitmapUtils來調用它們。

[java] view plain copy
public class MyBitmapUtils {
private NetCacheUtils mNetCacheUtils;
private LocalCacheUtils mLocalCacheUtils;
private MemoryCacheUtils mMemoryCacheUtils;

public MyBitmapUtils(){      mMemoryCacheUtils=new MemoryCacheUtils();      mLocalCacheUtils=new LocalCacheUtils();      mNetCacheUtils=new NetCacheUtils(mLocalCacheUtils,mMemoryCacheUtils);  }  public Bitmap getBitmap(String url){      Bitmap bitmap=null;       bitmap=mMemoryCacheUtils.getBitmapFromMemory(url);      if(bitmap!=null){          return bitmap;      }      bitmap = mLocalCacheUtils.getBitmapFromLocal(url);      if(bitmap!=null){           mMemoryCacheUtils.setBitmapToMemory(url,bitmap);           return bitmap;      }       return bitmap;  }  public void disPlay(ImageView ivPic, String url) {      Bitmap bitmap;      //記憶體緩衝      bitmap=mMemoryCacheUtils.getBitmapFromMemory(url);      if (bitmap!=null){          ivPic.setImageBitmap(bitmap);         Log.d("iamgecache","從記憶體擷取圖片啦.....--->"+url);          return;      }      //本機快取      bitmap = mLocalCacheUtils.getBitmapFromLocal(url);      if(bitmap !=null){          ivPic.setImageBitmap(bitmap);          Log.d("iamgecache","從本地擷取圖片啦.....-->"+url);          //從本地擷取圖片後,儲存至記憶體中          mMemoryCacheUtils.setBitmapToMemory(url,bitmap);          return;      }      //網路緩衝      mNetCacheUtils.getBitmapFromNet(ivPic,url);      Log.d("iamgecache","從網路擷取圖片啦.....-->"+url);  }  @SuppressLint("NewApi")  public void disPlay(View ivPic, String url) {      Bitmap bitmap;      //記憶體緩衝      bitmap=mMemoryCacheUtils.getBitmapFromMemory(url);      if (bitmap!=null){          //ivPic.setImageBitmap(bitmap);          if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {                //Android系統大於等於API16,使用setBackground                ivPic.setBackground(new BitmapDrawable(bitmap));          } else {                //Android系統小於API16,使用setBackground                ivPic.setBackgroundDrawable(new BitmapDrawable(bitmap));          }            //ivPic.setBackground(new BitmapDrawable(bitmap));          Log.d("iamgecache","從記憶體擷取圖片啦.....--->"+url);          return;      }      //本機快取      bitmap = mLocalCacheUtils.getBitmapFromLocal(url);      if(bitmap !=null){      //    ivPic.setImageBitmap(bitmap);          if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {                //Android系統大於等於API16,使用setBackground                ivPic.setBackground(new BitmapDrawable(bitmap));          } else {                //Android系統小於API16,使用setBackground                ivPic.setBackgroundDrawable(new BitmapDrawable(bitmap));          }            //ivPic.setBackground(new BitmapDrawable(bitmap));          Log.d("iamgecache","從本地擷取圖片啦.....-->"+url);          //從本地擷取圖片後,儲存至記憶體中          mMemoryCacheUtils.setBitmapToMemory(url,bitmap);          return;      }      //網路緩衝      mNetCacheUtils.getBitmapFromNet(ivPic,url);    //  ivPic.setBackground(new BitmapDrawable(bitmap));      Log.d("iamgecache","從網路擷取圖片啦....-->"+url);  }  

}
個人封裝的網路緩衝架構的好處是便於修改,自己清楚流程.適合於一些對圖片品質沒那麼高要求而又需要緩衝減少網路訪問的情景.

Android圖片三級緩衝策略

相關文章

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在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.