欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

Android中Glide加載庫(kù)的圖片緩存配置究極指南

 更新時(shí)間:2016年04月27日 16:09:11   作者:xx326664162  
這篇文章主要介紹了Android中Glide加載庫(kù)的圖片緩存配置究極指南,Glide是一款高人氣的安卓多媒體資源加載庫(kù),本文對(duì)其緩存設(shè)置和優(yōu)化作了詳細(xì)講解,需要的朋友可以參考下

零、選擇Glide
為什么圖片加載我首先推薦Glide?

圖片加載框架用了不少,從afinal框架的afinalBitmap,Xutils的BitmapUtils,老牌框架universalImageLoader,著名開源組織square的picasso,google推薦的glide到FaceBook推出的fresco。這些我前前后后都體驗(yàn)過(guò),那么面對(duì)這么多的框架,該如何選擇呢?下面簡(jiǎn)單分析下我的看法。

afinal和Xuils在github上作者已經(jīng)停止維護(hù)了,開源社區(qū)最新的框架要屬KJFramework,不過(guò)這種快速開發(fā)框架看似很好用,功能也應(yīng)有盡有,小型項(xiàng)目也罷,大型項(xiàng)目我不是很推薦,這樣做項(xiàng)目的耦合度太高,一旦出現(xiàn)停止維護(hù),而新的問(wèn)題不斷增加,沒(méi)人處理就麻煩了。

在glide和fresco還未出來(lái)的時(shí)候,當(dāng)時(shí)最火的莫過(guò)于universalImageLoader和picasso了,當(dāng)時(shí)覺(jué)得universalImageLoader配置相對(duì)picasso麻煩,雖然提供了各種配置,但是沒(méi)有實(shí)踐過(guò),根本不知道如何配置,還不如都采用默認(rèn)配置,就選擇了picasso作為圖片加載框架,用了近一年的時(shí)間,沒(méi)有太大的問(wèn)題,且使用簡(jiǎn)單,或許是因?yàn)橹暗捻?xiàng)目太過(guò)于簡(jiǎn)單,周期也并不是很長(zhǎng),還有使用eclipse開發(fā),一個(gè)很大的問(wèn)題一直都沒(méi)有暴露出來(lái),換上了最新的Android Studio可以清晰的看到各種性能相關(guān)的監(jiān)控,如cpu還有內(nèi)存監(jiān)控,終于知道了之前做的項(xiàng)目都那么的卡頓的罪魁禍?zhǔn)?,picasso加載稍微大一點(diǎn)的圖片就特別耗內(nèi)存,通常一個(gè)listView或者頂部滑動(dòng)廣告欄都含有多張圖片,這使得做出的頁(yè)面只要含圖片較多就異??D(之前的時(shí)候還把它歸結(jié)為測(cè)試機(jī)不好),知道這一點(diǎn)后我就有點(diǎn)想把picasso給替換掉,但這一次我不能那么粗心。

測(cè)試了picasso,glide,universalImageLoader,fresco這四個(gè)框架,測(cè)試內(nèi)容大概有以下幾項(xiàng),內(nèi)存測(cè)試,大圖片測(cè)試,小圖片測(cè)試,本地圖片,網(wǎng)絡(luò)圖片當(dāng)然還結(jié)合官方文檔體驗(yàn)其特色功能,內(nèi)存測(cè)試中,glide,universalImageLoader,fresco表現(xiàn)都非常優(yōu)秀,picasso這一點(diǎn)上實(shí)在是太糟糕了,小圖片差別也不是很大,稍微大點(diǎn)圖片內(nèi)存消耗就要比其他高出幾倍,這一點(diǎn)上證明了我的猜想,picasso不能再用了,下面一項(xiàng)項(xiàng)分析其他框架,在高于2M左右大圖測(cè)試中fresco的表現(xiàn)則和picasso一樣直接神馬都不顯示,項(xiàng)目中要實(shí)現(xiàn)大圖預(yù)覽功能,這點(diǎn)上是不行的,接著看universalImageLoader和glide在這幾項(xiàng)測(cè)試中成績(jī)都很好,到底該如何選擇呢?

因?yàn)槲翼?xiàng)目之前用的picasso,glide從用法上幾乎就是另一個(gè)picasso,從picasso轉(zhuǎn)移到glide相對(duì)改動(dòng)較少,還有一點(diǎn)就是這個(gè)項(xiàng)目是google在維護(hù),我也能給它更多的信任,相比較universalImageLoader,glide可以支持gif和短視頻,后期也需要用到,這里不得不談一下glide優(yōu)秀的緩存機(jī)制了,glide圖片緩存默認(rèn)使用RGB565相當(dāng)于ARGB8888可以節(jié)省不少的空間,支持與activity,fragment,application生命周期的聯(lián)動(dòng),更智能管理圖片請(qǐng)求當(dāng)然還有其他的擴(kuò)展更多可以看?glide介紹?當(dāng)然,glide的方法數(shù)量比universalImageLoader多了1000多個(gè),遇到64k問(wèn)題的會(huì)比較關(guān)注這個(gè)。

剛才只是掠過(guò)fresco,其實(shí)我對(duì)他的期待還是蠻大的,因?yàn)閯偝鰜?lái)還有居多不穩(wěn)定的地方,里面存在著大量吸引著我的功能,支持webps格式(和jpg一樣都是有損壓縮格式,webps相同質(zhì)量圖片更節(jié)省空間),支持漸進(jìn)式j(luò)peg,可以輕松的定制image的各種屬性,支持多圖請(qǐng)求和圖片復(fù)用,并支持手勢(shì)縮放和旋轉(zhuǎn)等等,更多介紹?fresco,當(dāng)然,實(shí)際用的時(shí)候并沒(méi)有那么好,很多功能都有待完善。

還有一點(diǎn)細(xì)節(jié)的地方要注意的,最好不要直接拿來(lái)用,至少經(jīng)過(guò)自己簡(jiǎn)單的封裝,而不是直接在項(xiàng)目中使用,一個(gè)簡(jiǎn)單的例子,后期圖片過(guò)多,可能需要另外配置一臺(tái)機(jī)器單獨(dú)存放圖片,主機(jī)地址做成可配置,可不要因?yàn)橐粋€(gè)簡(jiǎn)單的需求又要加班了
更多。


一、Glide3.0以來(lái)的新特性

1.動(dòng)態(tài)的GIF圖片加載:

Glide.with(context).load(...).asBitmap() //顯示gif靜態(tài)圖片
Glide.with(context).load(...).asGif() //顯示gif動(dòng)態(tài)圖片

2.本地視頻快照:

Glide現(xiàn)在還可以把視頻解碼為一張圖片:

 Glide.with(context).load(“視頻路徑“)


(經(jīng)過(guò)我的測(cè)試,只能把手機(jī)本地的mp4視頻解析為一張圖片,把mp4文件放在raw文件中,不能解析)

3.對(duì)縮略圖的支持:

 //加載yourView1/10尺寸的縮略圖,然后加載全圖
Glide.with(yourFragment).load(yourUrl).thumbnail(0.1f).into(yourView)

4.生命周期集成

同時(shí)將Activity/Fragment作為with()參數(shù)的好處是:圖片加載會(huì)和Activity/Fragment的生命周期保持一致,

請(qǐng)求會(huì)在onStop的時(shí)候自動(dòng)暫停,

在onStart的時(shí)候重新啟動(dòng),gif的動(dòng)畫也會(huì)在onStop的時(shí)候停止,以免在后臺(tái)消耗電量。

5.轉(zhuǎn)碼

Glide的.toBytes()和.transcode()方法允許在后臺(tái)獲取、解碼和轉(zhuǎn)換一個(gè)圖片,你可以將一張圖片轉(zhuǎn)換成更多有用的圖片格式,比如,上傳一張250*250的圖片

 Glide.with(context)
  .load(“/user/profile/photo/path”)
  .asBitmap()
  .toBytes()
  .centerCrop()
  .into(new SimpleTarget<byte[]>(250, 250) {
    @Override
    public void onResourceReady(byte[] data, GlideAnimation anim) {
      // Post your bytes to a background thread and upload them here.
    }
  });

6.動(dòng)畫:3.x加入了cross fades和View的屬性動(dòng)畫的支持

比如

 (.animate(ViewPropertyAnimation.Animator))


7. 網(wǎng)絡(luò)模塊可以選擇OkHttp或者Volley的支持

You can now choose to use either OkHttp, or Volley, or Glide's HttpUrlConnection default as your network stack.

Volley和OkHttp可以在gradle文件當(dāng)中添加依賴,注冊(cè)相應(yīng)的ModelLoaderFactory

 

二、圖片的緩存和緩存的時(shí)效機(jī)制

1.圖片緩存的鍵值

圖片緩存的鍵值主要用于DiskCacheStrategy.RESULT,Glide當(dāng)中的鍵值主要包含三個(gè)部分:

通過(guò)DataFetcher.getId()方法返回的String數(shù)據(jù)作為鍵值。一般的DataFetchers會(huì)簡(jiǎn)單返回?cái)?shù)據(jù)模型data model的toString()結(jié)果,如果是URL/File會(huì)返回相應(yīng)的路徑

圖片的尺寸,主要是通過(guò)override(width,height)或者通過(guò)Target's getSize()方法確定的尺寸信息

包含一個(gè)可選的簽名所有的這些東西會(huì)通過(guò)一種散列算法生成一個(gè)獨(dú)有、安全的文件名,通過(guò)此文件名將圖片緩存在disk中

2.緩存失效

因?yàn)镚lide當(dāng)中圖片緩存key的生成是通過(guò)一個(gè)散列算法來(lái)實(shí)現(xiàn)的,所以很難手動(dòng)去確定哪些文件可以從緩存當(dāng)中進(jìn)行刪除

2.1 當(dāng)內(nèi)容(url,file path)改變的時(shí)候,改變相應(yīng)的標(biāo)識(shí)符就可以了,Glide當(dāng)中也提供了signature()方法,將一個(gè)附加的數(shù)據(jù)加入到緩存key當(dāng)中

多媒體存儲(chǔ)數(shù)據(jù),可用MediaStoreSignature類作為標(biāo)識(shí)符,會(huì)將文件的修改時(shí)間、mimeType等信息作為cacheKey的一部分

文件,使用StringSignature

Urls ,使用StringSignature

 Glide.with(yourFragment)
  .load(yourFileDataModel)
  .signature(new StringSignature(yourVersionMetadata))
  .into(yourImageView);


 Glide.with(fragment)
  .load(mediaStoreUri)
  .signature(new MediaStoreSignature(mimeType, dateModified, orientation))
  .into(view);

自定義標(biāo)識(shí)符:

 public class IntegerVersionSignature implements Key {
  private int currentVersion;
  public IntegerVersionSignature(int currentVersion) {
     this.currentVersion = currentVersion;
  }
  @Override
  public boolean equals(Object o) {
    if (o instanceof IntegerVersionSignature) {
      IntegerVersionSignature other = (IntegerVersionSignature) o;
      return currentVersion = other.currentVersion;
    }
    return false;
  }
  @Override
  public int hashCode() {
    return currentVersion;
  }
  @Override
  public void updateDiskCacheKey(MessageDigest md) {
    messageDigest.update(ByteBuffer.allocate(Integer.SIZE)
.putInt(signature).array());
  }
}

2.2、不緩存可以通過(guò)diskCacheStrategy(DiskCacheStrategy.NONE.)實(shí)現(xiàn)

 

三、配置GlideModules

可以通過(guò)GlideModule接口來(lái)配置Glide的配置文件,并且像ModelLoaders一樣注冊(cè)相關(guān)組件。

包含一個(gè)GlideMode :

第一步、To use and register a GlideModule, first implement the interface with your configuration and components:

 public class MyGlideModule implements GlideModule {
  @Override
  public void applyOptions(Context context, GlideBuilder builder) {
    // Apply options to the builder here.
  }
  @Override
  public void registerComponents(Context context, Glide glide) {
    // register ModelLoaders here.
  }
}

第二步、然后將上面的實(shí)現(xiàn)了加入到proguard.cfg當(dāng)中:

 -keepnames class * com.mypackage.MyGlideModule

第三步、在AndroidManifest.xml文件中添加meta-data,以便Glide能夠找到你的Module

 <meta-data
 android:name="com.bumptech.glide.samples.flickr.FlickrGlideModule"
  android:value="GlideModule" />


四、Library項(xiàng)目

一個(gè)Library項(xiàng)目可能會(huì)定義一個(gè)或者多個(gè)GlideModules,如果一個(gè)Library項(xiàng)目添加一個(gè)Module到Library項(xiàng)目的manifest當(dāng)中,依賴于此Library的應(yīng)用就會(huì)自動(dòng)加載依賴庫(kù)(Library項(xiàng)目)當(dāng)中的Module。

當(dāng)然,如果manifest的合并不正確,那么Library里面Module就必須手動(dòng)地在應(yīng)用當(dāng)中添加進(jìn)去。

 

五、GlideModules沖突

雖然Glide允許一個(gè)應(yīng)用當(dāng)中存在多個(gè)GlideModules,Glide并不會(huì)按照一個(gè)特殊的順序去調(diào)用已注冊(cè)的GlideModules,如果一個(gè)應(yīng)用的多個(gè)依賴工程當(dāng)中有多個(gè)相同的Modules,就有可能會(huì)產(chǎn)生沖突。

如果一個(gè)沖突是不可避免的,應(yīng)用應(yīng)該默認(rèn)去定義一個(gè)自己的Module,用來(lái)手動(dòng)地處理這個(gè)沖突,在進(jìn)行Manifest合并的時(shí)候,可以用下面的標(biāo)簽排除沖突的module。

 <meta-data android:name=”com.mypackage.MyGlideModule” tools:node=”remove”/>


六、通過(guò)GlideBuilder配置全局配置文件

Glide允許開發(fā)者配置自定義的全局操作應(yīng)用于所有的請(qǐng)求,這個(gè)部分可以通過(guò)GlideModule接口中的applyOptions方法的GlideBuilder參數(shù)實(shí)現(xiàn) :

1.DiskCache

1.1、硬盤緩存是在一個(gè)后臺(tái)線程當(dāng)中,通過(guò)一個(gè)DiskCache.Factory接口進(jìn)行緩存的。

開發(fā)者能夠通過(guò)GlideBuilder的setDiskCache(DiskCache.Factory df)方法設(shè)置存儲(chǔ)的位置和大小

通過(guò)傳入DiskCacheAdapter來(lái)完全禁用緩存

自定義一個(gè)DiskCache來(lái)完全禁用緩存,

Glide默認(rèn)是用InternalCacheDiskCacheFactory類來(lái)創(chuàng)建硬盤緩存的,這個(gè)類會(huì)在應(yīng)用的內(nèi)部緩存目錄下面創(chuàng)建一個(gè)最大容量250MB的緩存文件夾,使用這個(gè)緩存目錄而不用sd卡,意味著除了本應(yīng)用之外,其他應(yīng)用是不能訪問(wèn)緩存的圖片文件的。

1.2.設(shè)置disk緩存的大小 : InternalCacheDiskCacheFactory

 builder.setDiskCache(new InternalCacheDiskCacheFactory(context, yourSizeInBytes));

1.3.設(shè)置緩存的路徑

可以通過(guò)實(shí)現(xiàn)DiskCache.Factory,然后使用DiskLruCacheWrapper創(chuàng)建一個(gè)新的緩存目錄,比如,可以通過(guò)如下方式在外存當(dāng)中創(chuàng)建緩存目錄:

  builder .setDiskCache(new DiskCache.Factory() {
    @Override
    public DiskCache build() { 
      // Careful: the external cache directory doesn't enforce permissions
      File cacheLocation = new File(context.getExternalCacheDir(), "cache_dir_name");
      cacheLocation.mkdirs();
      return DiskLruCacheWrapper.get(cacheLocation, yourSizeInBytes);
    }
  });


2.內(nèi)存當(dāng)中的緩存和POOLS

GlideBuilder當(dāng)中,允許開發(fā)者去設(shè)置內(nèi)存當(dāng)中圖片緩存區(qū)的大小,主要涉及到的類包括MemoryCache和BitmapPool

2.1 大小的設(shè)置

默認(rèn)內(nèi)存緩存的大小是用過(guò)MemorySizeCalculator來(lái)實(shí)現(xiàn)的,這個(gè)類會(huì)根據(jù)設(shè)備屏幕的大小,計(jì)算出一個(gè)合適的size,開發(fā)者可以獲取到相關(guān)的默認(rèn)設(shè)置信息:

 MemorySizeCalculator calculator = new MemorySizeCalculator(context);
int defaultMemoryCacheSize = calculator.getMemoryCacheSize();
int defaultBitmapPoolSize = calculator.getBitmapPoolSize();

如果在應(yīng)用當(dāng)中想要調(diào)整內(nèi)存緩存的大小,開發(fā)者可以通過(guò)如下方式:

Glide.get(context).setMemoryCategory(MemoryCategory.HIGH);

2.2 Memory Cache

Glide內(nèi)存緩存的目的是減少I/O,提高效率

可以通過(guò)GlideBuidler的setMemoryCache(MemoryCache memoryCache)去設(shè)置緩存的大小,開發(fā)者可以通過(guò)LruResourceCache類去設(shè)置緩存區(qū)的大小

builder.setMemoryCache(new LruResourceCache(yourSizeInBytes));

2.3 Bitmap Pool

可以通過(guò)GlideBuilder的setBitmapPool()方法設(shè)置池子的大小,LruBitmapPool是Glide的默認(rèn)實(shí)現(xiàn),使用如下:

 builder.setBitmapPool(new LruBitmapPool(sizeInBytes));

.圖片格式

GlideBuilder允許開發(fā)者設(shè)置一個(gè)全局的默認(rèn)圖片格式,

在默認(rèn)情況下,Glide使用RGB_565格式加載圖片,如果想要使用高質(zhì)量的圖片,可以通過(guò)如下方式設(shè)置系統(tǒng)的圖片格式:

 

builder.setDecodeFormat(DecodeFormat.ALWAYS_ARGB_8888);


七、自定義顯示控件

除了可以將圖片、視頻快照和GIFS顯示在View上面之外,開發(fā)者也可以在自定義的Target上面顯示這些媒體文件

1.SimpleTarget

重點(diǎn)內(nèi)容

如果你想簡(jiǎn)單地加載一個(gè)Bitmap,你可以通過(guò)以下簡(jiǎn)單的方式而不是直接地顯示給用戶,可能是顯示一個(gè)notification,或者上傳一個(gè)頭像,Glide都能很好地實(shí)現(xiàn)

SimpleTarget提供了對(duì)Target的簡(jiǎn)單實(shí)現(xiàn),并且讓你專注于對(duì)加載結(jié)果的處理

為了使用SimpleTarget,開發(fā)者需要提供一個(gè)寬和高的像素值,用來(lái)加載你的資源文件,并且你需要去實(shí)現(xiàn)

 onResourceReady(R resource,GlideAnimation<? super R> glideAnimation)
int myWidth = 512;
int myHeight = 384;

Glide.with(yourApplicationContext))
  .load(youUrl)
  .asBitmap()
  .into(new SimpleTarget<Bitmap>(myWidth, myHeight) {
    @Override
    public void onResourceReady(Bitmap bitmap, GlideAnimation anim) {
      // Do something with bitmap here.
    }
  };

說(shuō)明:

通常你去加載資源的時(shí)候,是將他們加載到一個(gè)view當(dāng)中,當(dāng)fragment或者activity失去焦點(diǎn)或者distroyed的時(shí)候,Glide會(huì)自動(dòng)停止加載相關(guān)資源,確保資源不會(huì)被浪費(fèi)

在大多數(shù)SimpleTarget的實(shí)現(xiàn)當(dāng)中,如果需要資源的加載不受組件生命周期的影響,Glide.width(context)當(dāng)中的context是application context而不是fragment或者activity

另外,由于一些long running operations可能會(huì)導(dǎo)致內(nèi)存泄露,如果你打算使用一個(gè)這樣的操作,可以考慮使用一個(gè)靜態(tài)的內(nèi)部類而不是一個(gè)動(dòng)態(tài)的內(nèi)部類。

2.ViewTarget

如果你想加載一張圖片到一個(gè)view當(dāng)中,但是又想改變或者監(jiān)聽(tīng)Glide默認(rèn)的部分設(shè)置,就可以通過(guò)重寫ViewTarget或者他的子類來(lái)實(shí)現(xiàn)

如果你想Gidle加載圖片的時(shí)候可以自定義圖片的大小,或者想要設(shè)置一個(gè)自定義的顯示動(dòng)畫,就可以通過(guò)ViewTarget來(lái)實(shí)現(xiàn),可以通過(guò)一個(gè)靜態(tài)的ViewTarget或者動(dòng)態(tài)的內(nèi)部類來(lái)實(shí)現(xiàn)相關(guān)的功能

 Glide.with(yourFragment)
  .load(yourUrl)
  .into(new ViewTarget<YourViewClass, GlideDrawable>(yourViewObject) {
    @Override
    public void onResourceReady(GlideDrawable resource, GlideAnimation anim) {
      YourViewClass myView = this.view;
      // Set your resource on myView and/or start your animation here.
    }
  });

說(shuō)明:

加載一張靜態(tài)的圖片或者一張GIF動(dòng)態(tài)圖,可以在load后面加上asBitmap()/asGif()

.Load(url)會(huì)通過(guò)asXXX()替換ViewTarget當(dāng)中的GlideDrawable參數(shù),也可以通過(guò)實(shí)現(xiàn)LifecycleLisener,給target設(shè)置一個(gè)回調(diào)。

3.覆蓋默認(rèn)的相關(guān)設(shè)置

如果只是想使用Glide的默認(rèn)配置,可以使用Glide當(dāng)中ImageViewTargets的兩個(gè)子類:

GlideDrawableImageViewTarget 默認(rèn)的實(shí)現(xiàn),可以通過(guò)asGif()加載動(dòng)態(tài)圖片

BitmapImageViewTarget 可以通過(guò)asBitmap()加載靜態(tài)圖片

如果想要使用Glide默認(rèn)實(shí)現(xiàn),可以在他們的子類方法當(dāng)中使用super.xx()即可,例如:

 Glide.with(yourFragment)
  .load(yourUrl)
  .asBitmap()
  .into(new BitmapImageViewTarget(yourImageView)) {
    @Override
    public void onResourceReady(Bitmap bitmap, GlideAnimation anim) {
      super.onResourceReady(bitmap, anim);
      Palette.generateAsync(bitmap, new Palette.PaletteAsyncListener() { 
        @Override
        public void onGenerated(Palette palette) {
          // Here's your generated palette
        }
      });
    }
  });

八、使用Glide下載自定義尺寸的圖片

Glide的ModelLoader接口為開發(fā)者提供了裝載圖片的view的尺寸,并且允許開發(fā)者使用這些尺寸信息去選擇合適的URL去下載圖片。選用適當(dāng)?shù)某叽缈梢怨?jié)省寬帶和設(shè)備的空間開銷,提高app的性能

2014年googleI/o大會(huì)發(fā)表了一篇文章,闡述了他們?nèi)绾问褂肕odelLoader接口去適配圖片的尺寸,見(jiàn)下面的連接:https://github.com/google/iosched/blob/master/doc/IMAGES.md

1、通過(guò)http/https下載圖片,可以通過(guò)繼承BaseGlideUtlLoader來(lái)實(shí)現(xiàn):

 public interface MyDataModel {
  public String buildUrl(int width, int height);
} 
public class MyUrlLoader extends BaseGlideUrlLoader<MyDataModel> {
  @Override
  protected String getUrl(MyDataModel model, int width, int height) {
    // Construct the url for the correct size here.
    return model.buildUrl(width, height);
  }
}


2、可以使用你自定義的ModelLoader去加載圖片了

 Glide.with(yourFragment)
  .using(new MyUrlLoader())
  .load(yourModel)
  .into(yourView);

如果你想避免每次加載圖片都要使用.using(new MyUrlLoader()) ,可以實(shí)現(xiàn)是一個(gè)

ModelLoaderFactory然后使用Glide將它注冊(cè)到GlideModule當(dāng)中

 public class MyGlideModule implements GlideModule {
  ...
  @Override
  public void registerComponents(Context context, Glide glide) {
    glide.register(MyDataModel.class, InputStream.class, 
      new MyUrlLoader.Factory());
  }
}

這樣你就可以跳過(guò).using()了

 Glide.with(yourFragment)
  .load(yourModel)
  .into(yourView);


九、集成庫(kù)

1.什么是集成庫(kù)

Glide包含一些小的、可選的集成庫(kù),目前Glide集成庫(kù)當(dāng)中包含了訪問(wèn)網(wǎng)絡(luò)操作的Volley和OkHttp

2.為什么要包含集成庫(kù)

這些集成庫(kù),和Glide的ModelLoader系統(tǒng)允許開發(fā)者使用一致地框架去進(jìn)行網(wǎng)絡(luò)相關(guān)的操作

3.如何將一個(gè)庫(kù)集成到Glide當(dāng)中,

將一個(gè)庫(kù)集成到Glide當(dāng)中需要兩步操作,

包含正確的dependency,

確保創(chuàng)建了該集成庫(kù)的GlideModule,比如,

將Volley集成到Glide當(dāng)中

第一步、添加依賴

 dependencies {
  compile 'com.github.bumptech.glide:volley-integration:1.2.2'
  compile 'com.mcxiaoke.volley:library:1.0.5'
}


第二步、創(chuàng)建Volley集成庫(kù)的GlideModule

 <meta-data
 android:name="com.bumptech.glide.integration.volley.VolleyGlideModule"
  android:value="GlideModule" />


然后改變混淆文件:

 -keep class com.bumptech.glide.integration.volley.VolleyGlideModule
#or
-keep public class * implements com.bumptech.glide.module.GlideModule


將OkHttp集成到Glide當(dāng)中:

第一步、添加依賴

 dependencies {
  compile 'com.github.bumptech.glide:okhttp-integration:1.2.2'
  compile 'com.squareup.okhttp:okhttp:2.0.0'
}


第二步、創(chuàng)建OkHttp集成庫(kù)的GlideModule

 <meta-data
  android:name="com.bumptech.glide.integration.okhttp.OkHttpGlideModule"
android:value="GlideModule" />

-keep class com.bumptech.glide.integration.okhttp.OkHttpGlideModule
#or
-keep public class * implements com.bumptech.glide.module.GlideModule


十、在后臺(tái)線程當(dāng)中進(jìn)行加載和緩存

為了保證Glide在后臺(tái)線程當(dāng)中加載資源文件更加容易,Glide除了Glide.with(fragment).load(url).into(view)之外還提供了

 downloadOnly(int width, int height)
downloadOnly(Y target)// Y extends Target<File>
into(int width, int height)


1.downloadOnly

Glide的downloadOnly()允許開發(fā)者將Image的二進(jìn)制文件下載到硬盤緩存當(dāng)中,以便在后續(xù)使用,

在UI線程當(dāng)中異步下載,在異步線程當(dāng)中則是使用width和height

在異步線程當(dāng)中同步調(diào)用下載,在同步線程當(dāng)中,

downloadOnly使用一個(gè)target作為參數(shù)

(1)在后臺(tái)線程當(dāng)中下載圖片,可以通過(guò)如下的方式:

 FutureTarget<File> future = Glide.with(applicationContext)
  .load(yourUrl)
  .downloadOnly(500, 500);
File cacheFile = future.get();

當(dāng)future返回的時(shí)候,image的二進(jìn)制文件信息就存入了disk緩存了,值得注意的是downloadOnly API只是保證圖片個(gè)bytes數(shù)據(jù)在disk當(dāng)中是有效的。

(2)下載完畢之后如果想要進(jìn)行顯示,可以通過(guò)如下方式進(jìn)行調(diào)用:

 Glide.with(yourFragment)
  .load(yourUrl)
  .diskCacheStrategy(DiskCacheStrategy.ALL)
  .into(yourView);

通過(guò)DiskCacheStrategy.ALL或者DiskCacheStrategy.SOURCE,可以保證程序會(huì)去讀取緩存文件

2. 如果想要在后臺(tái)線程當(dāng)中獲取某個(gè)URL對(duì)應(yīng)的Bitmap

不通過(guò)downloadOnly,可以使用into(),會(huì)返回一個(gè)FutureTarget對(duì)象,比如,想要得到一個(gè)URL對(duì)應(yīng)的500*500的centerCrop裁剪圖片,可以通過(guò)如下方式實(shí)現(xiàn):

 Bitmap myBitmap = Glide.with(applicationContext)
  .load(yourUrl)
  .asBitmap()
  .centerCrop()
  .into(500, 500)
  .get()


注意:上面的調(diào)用只能在異步線程當(dāng)中,如果在main Thread當(dāng)中調(diào)用.get(),會(huì)阻塞主線

十一、轉(zhuǎn)換器

1.默認(rèn)的轉(zhuǎn)換器

Glide兩個(gè)默認(rèn)的轉(zhuǎn)換器,fitCenter和CenterCrop,其他的轉(zhuǎn)換器詳見(jiàn)https://github.com/wasabeef/glide-transformations,可以將圖片轉(zhuǎn)為各種形狀,例如圓形,圓角型等等

用法:

 

Glide.with(yourFragment)
  .load(yourUrl)
  .fitCenter()
  .into(yourView);


 Glide.with(yourFragment)
  .load(yourUrl)
  .centerCrop()
  .into(yourView);


 // For Bitmaps:
Glide.with(yourFragment)
  .load(yourUrl)
  .asBitmap()
  .centerCrop()
  .into(yourView);
// For gifs:
Glide.with(yourFragment)
  .load(yourUrl)
  .asGif()
  .fitCenter()
  .into(yourView);



甚至可以在兩幅圖片進(jìn)行類型轉(zhuǎn)換的時(shí)候進(jìn)行transformed

 Glide.with(yourFragment)
  .load(yourUrl)
  .asBitmap()
  .toBytes()
  .centerCrop()
  .into(new SimpleTarget<byte[]>(...) { ... });


2.自定義轉(zhuǎn)換器

方法:

第一步、編寫轉(zhuǎn)換器類 ,繼承BitmapTransformation:

 

private static class MyTransformation extends BitmapTransformation {
  public MyTransformation(Context context) {
    super(context);
  }
  @Override
  protected Bitmap transform(BitmapPool pool, Bitmap toTransform, 
      int outWidth, int outHeight) {
    Bitmap myTransformedBitmap = ... // apply some transformation here.
    return myTransformedBitmap;
  }
  @Override
  public String getId() {
    // Return some id that uniquely identifies your transformation.
    return "com.example.myapp.MyTransformation";
  }
}


第二步、在Glide方法鏈當(dāng)中用.transform(…)替換fitCenter()/centerCrop()

 Glide.with(yourFragment)
  .load(yourUrl)
  .transform(new MyTransformation(context))
  .into(yourView);
// For Bitmaps:
Glide.with(yourFragment)
  .load(yourUrl)
  .asBitmap()
  .transform(new MyTransformation(context))
  .into(yourView);
// For Gifs:
Glide.with(yourFragment)
  .load(yourUrl)
  .asGif()
  .transform(new MyTransformation(context))
  .into(yourView);


3.自定義轉(zhuǎn)換器的尺寸

在上面使用過(guò)程當(dāng)中沒(méi)有設(shè)置尺寸值,那么轉(zhuǎn)換器轉(zhuǎn)換的圖片尺寸怎么確定呢,

Glide實(shí)際上已經(jīng)足夠智能根據(jù)view的尺寸來(lái)確定轉(zhuǎn)換圖片的尺寸了

如果需要自定義尺寸,而不是用view和target當(dāng)中的尺寸,那么可以使用override(int,int)設(shè)置相關(guān)的寬和高

4. Bitmap 再利用

為了減少垃圾收集,可以通過(guò)BitmapPool接口去釋放不需要的Bitmaps,當(dāng)然也可以對(duì)里面的bitmap進(jìn)行再利用。

例如在一次轉(zhuǎn)換中,

從pool當(dāng)中得到一個(gè)bitmap

將Bitmap回設(shè)給Canvas

使用Matrix、Paint在Canvas上面繪制原始的Bitmap,或者通過(guò)一個(gè)Shader來(lái)轉(zhuǎn)換一個(gè)image

4.1 不要手動(dòng)地去釋放一個(gè)轉(zhuǎn)換的bitmap資源,也不要將transform()之后的Bitmap重新放置到BitmapPool當(dāng)中去

 protected Bitmap transform(BitmapPool bitmapPool, Bitmap original, int width, int height) {
  Bitmap result = bitmapPool.get(width, height, Bitmap.Config.ARGB_8888);
  // If no matching Bitmap is in the pool, get will return null, so we should //allocate.
  if (result == null) {
    // Use ARGB_8888 since we're going to add alpha to the image.
    result = Bitmap.createBitmap(width, height, Bitmap.Config.ARGB_8888);
  }
  // Create a Canvas backed by the result Bitmap.
  Canvas canvas = new Canvas(result);
  Paint paint = new Paint();
  paint.setAlpha(128);
  // Draw the original Bitmap onto the result Bitmap with a transformation.
  canvas.drawBitmap(original, 0, 0, paint);
  // Since we've replaced our original Bitmap, we return our new Bitmap here. Glide will
  // will take care of returning our original Bitmap to the BitmapPool for us. 
  return result;
}

相關(guān)文章

最新評(píng)論