picasso是Square公司開源的一個Android圖形緩存庫
Picasso不僅實現了圖片異步加載的功能,還解決了android中加載圖片時需要解決的一些常見問題:
1.在adapter中需要取消已經不在視野范圍的ImageView圖片資源的加載,否則會導致圖片錯位,Picasso已經解決了這個問題。
2.使用復雜的圖片壓縮轉換來盡可能的減少內存消耗
3.自帶內存和硬盤二級緩存功能
Picasso(畢加索)內部采用了LRUCache類進行內存緩存處理,最大內存分配值為當前手機可用內存的1/7.將近15%。
Picasso的文件緩存,目錄在當前的應用的目錄下面的picasso-cache這個文件夾下面,默認文件緩存最大不能超過50M,最小不低於5M,
當然,如果當前手機的可用的本地存儲小於5M,那么已當前手機的所剩的本地存儲的大小作為文件緩存的大小。
使用之前需要添加依賴:
compile 'com.squareup.picasso:picasso:2.5.2'
1.使用Picasso下載網絡圖片
//使用Picasso下載網絡圖片,當你給一個控件設置了一個fit()方法后,后面就不可以調用resize()方法 Picasso.with(this).load(url) //圖片地址 .config(Bitmap.Config.RGB_565) .placeholder(R.mipmap.ic_launcher) //設置占位圖,下載圖片時顯示的 .error(R.mipmap.ic_launcher) //下載出錯顯示的圖片 .fit() //控件不能設置成wrap_content,必須有大小fit()才讓圖片的寬高等於控件的寬高,設置fit(),不能再調用resize() .into(imageView); //顯示圖片的目標控件
2.加載sd卡上的圖片
//加載sd卡上的圖片,將上面的網址改為file對象就可以了 File file=new File("路徑"); Picasso.with(this).load(file).config(Bitmap.Config.RGB_565) .placeholder(R.mipmap.ic_launcher).error(R.mipmap.ic_launcher).fit().into(imageView);
3.監聽Picasso加載圖片的結果
//監聽Picasso加載圖片的結果 Picasso.with(this).load(url).config(Bitmap.Config.RGB_565) .placeholder(R.mipmap.ic_launcher).error(R.mipmap.ic_launcher) .fit() .into(imageView, new Callback() { @Override public void onSuccess() { Log.i("tag", "圖片下載成功,如果是從緩存中獲取不會執行"); } @Override public void onError() { Log.i("tag", "onError: "); } });
4.將下載的圖片變為圓形圖片顯示
//將下載的圖片變為圓形圖片顯示 Picasso.with(this).load(url) .transform(new CircleTransform()) //轉換的方式,可以自定義類實現Transformation接口,重寫轉換方法就行 .placeholder(R.mipmap.ic_launcher).error(R.mipmap.ic_launcher) .fit().into(imageView);
需要的轉換類:
import android.graphics.Bitmap; import android.graphics.BitmapShader; import android.graphics.Canvas; import android.graphics.Paint; import com.squareup.picasso.Transformation; /** * 將圖片轉換為圓形,需要實現picasso.Transformation接口 */ public class CircleTransform implements Transformation { @Override //對Bitmap進行轉換操作,需要定義自己的轉換方式,都可以重寫這個方法 public Bitmap transform(Bitmap source) { //獲取最小邊長 int size=Math.min(source.getWidth(),source.getHeight()); //獲取圓形圖片的寬度和高度 int x=(source.getWidth()-size)/2; int y=(source.getHeight()-size)/2; //創建一個正方形區域的Btimap Bitmap squaredBitmap=Bitmap.createBitmap(source,x,y,size,size); if(squaredBitmap!=source){ source.recycle(); } //創建一張可以操作的正方形圖片的位圖 Bitmap bitmap=Bitmap.createBitmap(size,size,source.getConfig()); //創建一個畫布Canvas Canvas canvas=new Canvas(bitmap); //創建畫筆 Paint paint=new Paint(); BitmapShader shader=new BitmapShader(squaredBitmap,BitmapShader.TileMode.CLAMP,BitmapShader.TileMode.CLAMP); paint.setShader(shader); paint.setAntiAlias(true); //圓形半徑 float r=size/2f; canvas.drawCircle(r,r,r,paint); squaredBitmap.recycle(); return bitmap; } @Override //一個key,主要是緩存的key的生成和它有關 public String key() { return "circle"; } }
5.滑動ListView停止下載圖片的實現:
ListView listView = new ListView(this); //在滑動listview時,不會進行圖片的加載,停止滑動時,才會繼續進行加載圖片 listView.setOnScrollListener(new AbsListView.OnScrollListener() { @Override public void onScrollStateChanged(AbsListView view, int scrollState) { final Picasso picasso = Picasso.with(MainActivity.this); if (scrollState == SCROLL_STATE_IDLE || scrollState == SCROLL_STATE_TOUCH_SCROLL) { picasso.resumeTag(MainActivity.this);//恢復tag } else { picasso.pauseTag(MainActivity.this);//暫停tag } } @Override public void onScroll(AbsListView view, int firstVisibleItem, int visibleItemCount, int totalItemCount) { } });
6.控制需不需要從緩存中獲取圖片:
//1.需求:每次請求網絡都是走網絡,永遠不使用內存緩存和文件緩存 Picasso.with(this) .load("地址") .fit() .networkPolicy(NetworkPolicy.NO_STORE,NetworkPolicy.NO_CACHE) .memoryPolicy(MemoryPolicy.NO_STORE,MemoryPolicy.NO_CACHE) .into(imageView); //2.需求:每次請求網絡,只啟用內存緩存,不啟用二級緩存文件緩存(DiskCache) Picasso.with(this) .load("地址") .fit() .networkPolicy(NetworkPolicy.NO_STORE,NetworkPolicy.NO_CACHE) .into(imageView); //3.需求:每次請求網絡,只啟用二級緩存(DiskCache),不啟用一級緩存(LRUCache) Picasso.with(this) .load("地址") .fit() .memoryPolicy(MemoryPolicy.NO_STORE,MemoryPolicy.NO_CACHE) .into(imageView); //當然,如果你什么都沒有配置,Picasso默認是內存緩存和文件緩存都是啟用的。
7.修改緩存位置與調試:
public class MyApplication extends Application { @Override public void onCreate() { super.onCreate(); initPicasso(); } /** * 設置Picasso框架的圖片緩存路徑,默認在data/data/包名/cache/picasso-cache文件夾下 * 會報找不到OkHttpDownloader類的異常,這就是不匹配的問題了 */ private void initPicasso(){ String imageCacheDir = Environment.getExternalStorageDirectory() .getPath()+ File.separator+"Picasso的緩存路徑"; File cacheFile=new File(imageCacheDir); if(!cacheFile.exists()){ cacheFile.mkdirs(); } Picasso picasso = new Picasso.Builder(this).downloader(new OkHttpDownloader(cacheFile)).build(); Picasso.setSingletonInstance(picasso); /** * 這行代碼會將你加載的圖片的來源通過顏色的方式在圖片的左上角有展示: * 紅色:代表從網絡下載的圖片 * 黃色:代表從磁盤緩存加載的圖片 * 綠色:代表從內存緩存中加載的圖片 */ Picasso.with(this).setIndicatorsEnabled(true); } }