1. 程式人生 > >Android 技術之Picasso圖片快取

Android 技術之Picasso圖片快取

Picasso圖片快取技術有必要了解一下,在日常的專案是經常用到的,以前我們會想到使用HttpUrlConnection和AsyncTask實現遠端圖片下載,,然後如果每次都是這樣的,程式碼量會增加,這樣不好,不好!
首先我們先來了解一下Picasso到底是一個什麼,又是怎樣用的呢??
picasso是Square公司開源的一個Android圖形快取庫,地址http://square.github.io/picasso/,可以實現圖片下載和快取功能。僅僅只需要一行程式碼就能完全實現圖片的非同步載入:

Picasso.with(context).load("這裡是你的圖片地址或者。。。(後面有驚喜)"
).into(imageView);
就是這麼簡單的一句話,然後我們來對比一下剛才說HttpUrlConnection和AsyncTask的實現方法:

ublic class MainActivity extends Activity {
private ImageView imageView;

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);
    imageView = (ImageView) findViewById(R.id.image);
    String url = "http://www.jycoder.com/json/Image/1.jpg";

    // 執行Task
    new ImageDownloadTask(ivBasicImage).execute(url);
}

//自定義獲取圖片Task
private class ImageDownloadTask extends AsyncTask<String, Void, Bitmap> {
    ImageView imageView;

    public ImageDownloadTask(ImageView imageView) {
        this.imageView = imageView;
    }

    protected Bitmap doInBackground(String... addresses) {
        Bitmap bitmap = null;
        InputStream in;
        try {
            // 建立URL連線
            URL url = new URL(addresses[0]);
            HttpURLConnection conn = (HttpURLConnection) url.openConnection();
            // 開啟輸入流
            conn.connect();
            in = conn.getInputStream();
            // 編碼輸入流
            bitmap = BitmapFactory.decodeStream(in);
        } catch (IOException e) {
            e.printStackTrace();
        } finally {
          if(in != null)
             in.close();
        }
        return bitmap;
    }

    // Task執行完畢,返回bitmap
    @Override
    protected void onPostExecute(Bitmap result) {
        // Set bitmap image for the result
        imageView.setImageBitmap(result);
    }
}
}
是不是覺得弱爆了,不過如果你倒是可以對這段程式碼進行封裝嘛,個人喜好啊,然後寫成一個帶引數的方法,然後帶入引數請求也是可以的啊,可是從一些優化的角度角度來說,還是今天的主角比較OK的啦!

接下來了解一下 Picasso的其他用法:
(1)介面卡:介面卡自動發現和重用以前取消的下載:

@Override
public void getView(int position, View convertView, ViewGroup parent) {
SquaredImageView view = (SquaredImageView) convertView;
if (view == null) {
view = new SquaredImageView(context);
}
String url = getItem(position);

  Picasso.with(context).load(url).into(view);
}
(2)影象格式轉換:很多時候需要將圖片進行格式轉換或者剪裁以節省記憶體或者達到我們的佈局效果:

Picasso.with(context).load(imageUrl).resize(50,50).centerCrop().into(imageView

其中resize(50,50)根據自己的要求給圖片一定的大小:
(3)自定義格式轉換:為了實現更多你想要圖片轉換的效果,你可以自己實現一個實現了Transformation介面的類,然後將其物件傳遞給transform()方法:

public calss myTransformation implements Transformation{
@Overrride
public Bitmap transform(Bitmap source){
//對source實現自定義裁剪
}
@Override
public String key(){
return “square()”;
}

}

將myTransformation 的物件傳遞給transform 方法即可

Picasso.with(this).load("http://i.imgur.com/DvpvklR.png")                 .transform(new myTransformation ()).into(iv_test2); 

(4)Place holders-空白或者錯誤佔位圖片:picasso提供了兩種佔位圖片,未載入完成或者載入發生錯誤的時需要一張圖片作為提示。

Picasso.with(this) .load("http://i.imgur.com/DvpvklR.png") .placeholder(R.drawable.abc) .error(R.drawable.ic_launcher) .transform(new myTransformation ()) .into(iv_test1);

其中placeholder(R.drawable.abc)就是載入前的圖片 ,error(R.drawable.ic_launcher)載入錯誤的時候圖片

(5)資原始檔的載入:除了載入網路圖片picasso還支援載入Resources, assets, files, content providers中的資原始檔。

Picasso.with(context).load(R.drawable.landing_screen).into(imageView1);
Picasso.with(context).load(new File(...)).into(imageView2);

這就是剛才上面說的驚喜,你可以自己選擇一個 R.drawable.landing_screen
,同時你也可以選擇一個檔案的圖片路徑。

在我們的實際專案中可能需要用到adapter介面卡(半夜了,偷下懶,不過你們可以借鑑一下其他大神):
ListView顯示網路圖片
自定義GridView

還有一篇是對Picass的深入理解,想研究的去看看,一時半會看不太懂;
Picasso深入理解