Glide定制化开发(一)实现网络下载拦截开关

用于App配置非wifi环境下是否自动加载图片的开关

我们的需求:拦截网络下载,但是复用glide原有的内存下载等优势

做法:在glide网络加载的DataFetcher做定制化开发

1. 定制化MyAppGlideModule

  • registerComponents中替换 ModelLoader ,替换我们自定义的okhtttp加载model
  • 定义我们标记的Option,作为开关参数
@GlideModule
class MyAppGlideModule : AppGlideModule() {
    companion object{
        /**
         * 是否使用 4g网络不主动加载图片的控制功能
         */
        val OPTION_NETWORK_LOAD_SWITH = Option.memory("option_network_load_swith", false)
        /**
         * 判断是否能从网络加载图片
         * @return Boolean
         */
        fun getLoadFromNetworkEnable():Boolean{
            return BaseData.isAllowCellularDownload||NetworkUtil.isWifi(appContext)
        }

    }

    override fun applyOptions(context: Context, builder: GlideBuilder) {
        super.applyOptions(context, builder)
    }

    override fun registerComponents(context: Context, glide: Glide, registry: Registry) {
        registry.replace(GlideUrl::class.java, InputStream::class.java,  MyOkHttpUrlLoader.Factory())
    }
}

2. 修改OkHttpUrlLoader为我们自定义的Loader

  • 这一步可以直接从glideOkHttp里面查找复制出来OkHttpUrlLoader,在MyOkHttpUrlLoader里面修改buildLoadData里面替换我们自定义的MyOkHttpStreamFetcher

  • 这里主要操作是从Options中查找我们自定义的开关值,并透传给MyOkHttpStreamFetcher构造函数

@Override
public LoadData buildLoadData(
    @NonNull GlideUrl model, int width, int height, @NonNull Options options) {
  boolean optionNetworkLoadSwith= options.get(MyAppGlideModule.Companion.getOPTION_NETWORK_LOAD_SWITH());
  return new LoadData<>(model, new MyOkHttpStreamFetcher(client, model,optionNetworkLoadSwith));
}

3. 自定义MyOkHttpStreamFetcher

  • 直接从glideOkHttp里面查找复制出来MyOkHttpStreamFetcher

  • 重写loadData方法,如果不满足我们的下载条件直接onFailure回调失败结果

// Public API.
@SuppressWarnings("WeakerAccess")
public MyOkHttpStreamFetcher(Call.Factory client, GlideUrl url, boolean optionNetworkLoadSwith) {
    this.client = client;
    this.url = url;
    this.mOptionNetworkLoadSwith = optionNetworkLoadSwith;
    IMLog.dTag("Felix","--------mOptionNetworkLoadSwith: "+mOptionNetworkLoadSwith);
}

@Override
public void loadData(
        @NonNull Priority priority, @NonNull final DataCallback callback) {
    this.callback = callback;
    if (!MyAppGlideModule.Companion.getLoadFromNetworkEnable() && mOptionNetworkLoadSwith) {
        onFailure(call, new IOException("[Felix]: Load Failed by Setting-Refused (sLoadImageNotWifiEnable)!!"));
    } else {
        Request.Builder requestBuilder = new Request.Builder().url(url.toStringUrl());
        for (Map.Entry headerEntry : url.getHeaders().entrySet()) {
            String key = headerEntry.getKey();
            requestBuilder.addHeader(key, headerEntry.getValue());
        }
        Request request = requestBuilder.build();
        call = client.newCall(request);
        call.enqueue(this);
    }

}

完成以上三步即可实现控制开关

4. 开关使用方法,在glide调用的时候通过在RequestOptions中设置我们定义的options开关即可在需要的地方使用网络下载拦截

val requestOptions = RequestOptions()
                .skipMemoryCache(isSkipMemoryCache) //是否允许内存缓存
                .diskCacheStrategy(DiskCacheStrategy.ALL) //禁止磁盘缓存
requestOptions.options.set(MyAppGlideModule.OPTION_NETWORK_LOAD_SWITH,true)
Glide.with(context).load(url).transition(DrawableTransitionOptions.withCrossFade()).apply(requestOptions).into(view)

你可能感兴趣的:(Glide定制化开发(一)实现网络下载拦截开关)