Glide是google推荐的图片加载框架,很受开发者追捧,它提高了我们开发效率,减少了很多问题。优秀的框架就值得我们去学习,我们来看一下具体它是怎么实现的
我们使用glide的方式很简单,就这一行代码Glide.with(this).load(imageUrl).into(imageView),看似简单,但里面的实现特别复杂,我们就来一步步揭开它的面纱
本篇以glide 4.6.0版本来讲解
Glide.with(this)
先看一下Glide初始化
private static void initializeGlide(@NonNull Context context, @NonNull GlideBuilder builder) {
Context applicationContext = context.getApplicationContext();
RequestManagerRetriever.RequestManagerFactory factory =
annotationGeneratedModule != null
? annotationGeneratedModule.getRequestManagerFactory() : null;
builder.setRequestManagerFactory(factory);
//通过builder来创建
Glide glide = builder.build(applicationContext);
applicationContext.registerComponentCallbacks(glide);
Glide.glide = glide;
}
利用GlideBuilder进行创建
public Glide build(@NonNull Context context) {
if (sourceExecutor == null) {
sourceExecutor = GlideExecutor.newSourceExecutor();
}
if (diskCacheExecutor == null) {
diskCacheExecutor = GlideExecutor.newDiskCacheExecutor();
}
if (animationExecutor == null) {
animationExecutor = GlideExecutor.newAnimationExecutor();
}
if (memorySizeCalculator == null) {
memorySizeCalculator = new MemorySizeCalculator.Builder(context).build();
}
if (connectivityMonitorFactory == null) {
connectivityMonitorFactory = new DefaultConnectivityMonitorFactory();
}
if (bitmapPool == null) {
int size = memorySizeCalculator.getBitmapPoolSize();
if (size > 0) {
bitmapPool = new LruBitmapPool(size);
} else {
bitmapPool = new BitmapPoolAdapter();
}
}
if (arrayPool == null) {
arrayPool = new LruArrayPool(memorySizeCalculator.getArrayPoolSizeInBytes());
}
if (memoryCache == null) {
memoryCache = new LruResourceCache(memorySizeCalculator.getMemoryCacheSize());
}
if (diskCacheFactory == null) {
diskCacheFactory = new InternalCacheDiskCacheFactory(context);
}
if (engine == null) {
engine =
new Engine(
memoryCache,
diskCacheFactory,
diskCacheExecutor,
sourceExecutor,
GlideExecutor.newUnlimitedSourceExecutor(),
GlideExecutor.newAnimationExecutor(),
isActiveResourceRetentionAllowed);
}
RequestManagerRetriever requestManagerRetriever =
new RequestManagerRetriever(requestManagerFactory);
return new Glide(
context,
engine,
memoryCache,
bitmapPool,
arrayPool,
requestManagerRetriever,
connectivityMonitorFactory,
logLevel,
defaultRequestOptions.lock(),
defaultTransitionOptions);
}
Glide的真正初始化
Glide(
@NonNull Context context,
@NonNull Engine engine,
@NonNull MemoryCache memoryCache,
@NonNull BitmapPool bitmapPool,
@NonNull ArrayPool arrayPool,
@NonNull RequestManagerRetriever requestManagerRetriever,
@NonNull ConnectivityMonitorFactory connectivityMonitorFactory,
int logLevel,
@NonNull RequestOptions defaultRequestOptions,
@NonNull Map, TransitionOptions, ?>> defaultTransitionOptions) {
//请求管理器,在Glide.get(context).getRequestManagerRetriever()时候返回
this.requestManagerRetriever = requestManagerRetriever;
//这是注册表,数据的请求和解析都靠它,这里面有资源解码注册表,转码注册表,模型加载注册表,编码器
//加载网路图片用到了前面三个,这个很关键
registry = new Registry();
registry.register(new DefaultImageHeaderParser());
Downsampler downsampler = new Downsampler(registry.getImageHeaderParsers(),
resources.getDisplayMetrics(), bitmapPool, arrayPool);
ByteBufferBitmapDecoder byteBufferBitmapDecoder = new ByteBufferBitmapDecoder(downsampler);
StreamBitmapDecoder streamBitmapDecoder = new StreamBitmapDecoder(downsampler, arrayPool);
ResourceDrawableDecoder resourceDrawableDecoder =
new ResourceDrawableDecoder(context);
ResourceLoader.StreamFactory resourceLoaderStreamFactory =
new ResourceLoader.StreamFactory(resources);
BitmapEncoder bitmapEncoder = new BitmapEncoder();
BitmapBytesTranscoder bitmapBytesTranscoder = new BitmapBytesTranscoder();
ContentResolver contentResolver = context.getContentResolver();
//开始注册
registry
.append(ByteBuffer.class, new ByteBufferEncoder())
/* Bitmaps */
//注册资源解码器
.append(Registry.BUCKET_BITMAP, ByteBuffer.class, Bitmap.class, byteBufferBitmapDecoder)
/* Drawables */
.append(Uri.class, Drawable.class, resourceDrawableDecoder)
/* Models */
.register(new InputStreamRewinder.Factory(arrayPool))
//注册模块加载器
.append(String.class, InputStream.class, new StringLoader.StreamFactory())
.append(String.class, InputStream.class, new StringLoader.StreamFactory())
.append(Uri.class, InputStream.class, new HttpUriLoader.Factory())
.append(GlideUrl.class, InputStream.class, new HttpGlideUrlLoader.Factory())
/* Transcoders */
//注册转码器
.register(
Bitmap.class,
BitmapDrawable.class,
new BitmapDrawableTranscoder(resources))
ImageViewTargetFactory imageViewTargetFactory = new ImageViewTargetFactory();
glideContext =
new GlideContext(
context,
arrayPool,
registry,
imageViewTargetFactory,
defaultRequestOptions,
defaultTransitionOptions,
engine,
logLevel);
}
模型加载注册表 ModelLoaderRegistry
它的作用是将数据源解码成对于目标数据
/**
通过multiModelLoaderFactory来管理
*/
public class ModelLoaderRegistry {
private final MultiModelLoaderFactory multiModelLoaderFactory;
public ModelLoaderRegistry(@NonNull Pool> throwableListPool) {
this(new MultiModelLoaderFactory(throwableListPool));
}
private ModelLoaderRegistry(@NonNull MultiModelLoaderFactory multiModelLoaderFactory) {
this.multiModelLoaderFactory = multiModelLoaderFactory;
}
//将解码器加进来
public synchronized void append(
@NonNull Class modelClass,
@NonNull Class dataClass,
@NonNull ModelLoaderFactory extends Model, ? extends Data> factory) {
multiModelLoaderFactory.append(modelClass, dataClass, factory);
cache.clear();
}
//获取能够处理该model的loader
public synchronized List> getModelLoaders(@NonNull A model) {
//通过判断是否是model类型来初步获取loader
List> modelLoaders = getModelLoadersForClass(getClass(model));
int size = modelLoaders.size();
List> filteredLoaders = new ArrayList<>(size);
for (int i = 0; i < size; i++) {
ModelLoader loader = modelLoaders.get(i);
//再通过loader是能能够处理该model再过滤loader
if (loader.handles(model)) {
filteredLoaders.add(loader);
}
}
return filteredLoaders;
}
private List> getModelLoadersForClass(@NonNull Class modelClass) {
List> loaders = cache.get(modelClass);
if (loaders == null) {
//下面是multiModelLoaderFactory的build方法
loaders = Collections.unmodifiableList(multiModelLoaderFactory.build(modelClass));
cache.put(modelClass, loaders);
}
return loaders;
}
}
/**
1.存放解码器
2.根据数据源获取解码器 getModelLoaders
*/
public class MultiModelLoaderFactory {
//存放解码器
private final List> entries = new ArrayList<>();
synchronized void append(
@NonNull Class modelClass,
@NonNull Class dataClass,
@NonNull ModelLoaderFactory extends Model, ? extends Data> factory) {
add(modelClass, dataClass, factory, /*append=*/ true);
}
private void add(
@NonNull Class modelClass,
@NonNull Class dataClass,
@NonNull ModelLoaderFactory extends Model, ? extends Data> factory,
boolean append) {
Entry entry = new Entry<>(modelClass, dataClass, factory);
entries.add(append ? entries.size() : 0, entry);
}
//根据数据源类型返回loader的集合
synchronized List> build(@NonNull Class modelClass) {
try {
List> loaders = new ArrayList<>();
for (Entry, ?> entry : entries) {
if (alreadyUsedEntries.contains(entry)) {
continue;
}
if (entry.handles(modelClass)) {
alreadyUsedEntries.add(entry);
//通过factory生成loader
loaders.add(this.build(entry));
alreadyUsedEntries.remove(entry);
}
}
return loaders;
} catch (Throwable t) {
alreadyUsedEntries.clear();
throw t;
}
}
private static class Entry {
private final Class modelClass;
@Synthetic final Class dataClass;
@Synthetic final ModelLoaderFactory extends Model, ? extends Data> factory;
public Entry(
@NonNull Class modelClass,
@NonNull Class dataClass,
@NonNull ModelLoaderFactory extends Model, ? extends Data> factory) {
this.modelClass = modelClass;
this.dataClass = dataClass;
this.factory = factory;
}
public boolean handles(@NonNull Class> modelClass, @NonNull Class> dataClass) {
return handles(modelClass) && this.dataClass.isAssignableFrom(dataClass);
}
//这里判断待转换的类型是否一致
public boolean handles(@NonNull Class> modelClass) {
return this.modelClass.isAssignableFrom(modelClass);
}
}
}
以ByteBufferFileLoader为例
public class ByteBufferFileLoader implements ModelLoader {
@Override
public LoadData buildLoadData(@NonNull File file, int width, int height,
@NonNull Options options) {
return new LoadData<>(new ObjectKey(file), new ByteBufferFetcher(file));
}
@Override
public boolean handles(@NonNull File file) {
return true;
}
//工厂类,生成ModelLoader
public static class Factory implements ModelLoaderFactory {
public ModelLoader build(@NonNull MultiModelLoaderFactory multiFactory) {
return new ByteBufferFileLoader();
}
@Override
public void teardown() {
// Do nothing.
}
}
private static final class ByteBufferFetcher implements DataFetcher {
private final File file;
ByteBufferFetcher(File file) {
this.file = file;
}
@Override
public void loadData(@NonNull Priority priority,
@NonNull DataCallback super ByteBuffer> callback) {
ByteBuffer result;
try {
result = ByteBufferUtil.fromFile(file);
} catch (IOException e) {
if (Log.isLoggable(TAG, Log.DEBUG)) {
Log.d(TAG, "Failed to obtain ByteBuffer for file", e);
}
callback.onLoadFailed(e);
return;
}
callback.onDataReady(result);
}
}
看一下LoadData的实现
/**
加载数据的实体类,sourceKey是数据源,fetcher是数据获取器
*/
class LoadData {
public LoadData(@NonNull Key sourceKey, @NonNull List alternateKeys,
@NonNull DataFetcher fetcher) {
this.sourceKey = Preconditions.checkNotNull(sourceKey);
this.alternateKeys = Preconditions.checkNotNull(alternateKeys);
this.fetcher = Preconditions.checkNotNull(fetcher);
}
}
LoadData buildLoadData(@NonNull Model model, int width, int height,
@NonNull Options options);
boolean handles(@NonNull Model model);
}
可以看到,ByteBufferFileLoader的作用就是将file转换为ByteBuffer
我们再看一下append(String.class, InputStream.class, new StringLoader.StreamFactory()),它跟上面介绍的ByteBufferFileLoader有点不一样
public class StringLoader implements ModelLoader {
//看见没,StringLoader里面还包了一个uriLoader
private final ModelLoader uriLoader;
public StringLoader(ModelLoader uriLoader) {
this.uriLoader = uriLoader;
}
//实际在创建的时候,调用的是uriLoader.buildLoadData,它只是一个壳
public LoadData buildLoadData(@NonNull String model, int width, int height,
@NonNull Options options) {
Uri uri = parseUri(model);
return uri == null ? null : uriLoader.buildLoadData(uri, width, height, options);
}
@Override
public boolean handles(@NonNull String model) {
return true;
}
public static class StreamFactory implements ModelLoaderFactory {
public ModelLoader build(MultiModelLoaderFactory multiFactory) {
//调用multiFactory创建了另外一个loader,表示(String, InputStream)类型的,将会通过(Uri, InputStream)这个类型的loader处理
return new StringLoader<>(multiFactory.build(Uri.class, InputStream.class));
}
@Override
public void teardown() {
}
}
}
模型加载注册表就介绍完了。
总结一下,ModelLoaderRegistry有一个multiModelLoaderFactory,里面有一个entries的集合,里面放的是数据源对象和模型加载器工厂,通过build方法,能生成能处理该数据的模型加载器
资源解码注册表
将指定的数据解码成另一种类型
看一下ResourceDecoderRegistry的代码,以append(Registry.BUCKET_BITMAP, InputStream.class, Bitmap.class, streamBitmapDecoder)为例
public class ResourceDecoderRegistry {
//能解码的名称别名集合,这里是BUCKET_BITMAP
private final List bucketPriorityList = new ArrayList<>();
//将别名作为key存放,一个BUCKET_BITMAP可以有多个的解码器
private final Map>> decoders = new HashMap<>();
//bucket:数据名称,dataClass 数据类型,resourceClass 转换后的类型,decoder 解码器
public synchronized void append(@NonNull String bucket,
@NonNull ResourceDecoder decoder,
@NonNull Class dataClass, @NonNull Class resourceClass) {
getOrAddEntryList(bucket).add(new Entry<>(dataClass, resourceClass, decoder));
}
private synchronized List> getOrAddEntryList(@NonNull String bucket) {
if (!bucketPriorityList.contains(bucket)) {
// Add this unspecified bucket as a low priority bucket.
bucketPriorityList.add(bucket);
}
List> entries = decoders.get(bucket);
if (entries == null) {
entries = new ArrayList<>();
decoders.put(bucket, entries);
}
return entries;
}
private static class Entry {
private final Class dataClass;
@Synthetic final Class resourceClass;
@Synthetic final ResourceDecoder decoder;
public Entry(@NonNull Class dataClass, @NonNull Class resourceClass,
ResourceDecoder decoder) {
this.dataClass = dataClass;
this.resourceClass = resourceClass;
this.decoder = decoder;
}
public boolean handles(@NonNull Class> dataClass, @NonNull Class> resourceClass) {
return this.dataClass.isAssignableFrom(dataClass) && resourceClass
.isAssignableFrom(this.resourceClass);
}
}
}
看一下StreamBitmapDecoder streamBitmapDecoder = new StreamBitmapDecoder(downsampler, arrayPool)
public class StreamBitmapDecoder implements ResourceDecoder {
//能否处理
public boolean handles(@NonNull InputStream source, @NonNull Options options) {
return downsampler.handles(source);
}
public Resource decode(@NonNull InputStream source, int width, int height,
@NonNull Options options)
throws IOException {
try {
return downsampler.decode(invalidatingStream, width, height, options, callbacks);
} finally {
exceptionStream.release();
if (ownsBufferedStream) {
bufferedStream.release();
}
}
}
}
它就是将InputStream转换成Bitmap
转码注册表
也是将一种类型转换成另外一种类型,
以register(
Bitmap.class,
BitmapDrawable.class,
new BitmapDrawableTranscoder(resources))为例
public class TranscoderRegistry {
private final List> transcoders = new ArrayList<>();
public synchronized void register(
@NonNull Class decodedClass, @NonNull Class transcodedClass,
@NonNull ResourceTranscoder transcoder) {
transcoders.add(new Entry<>(decodedClass, transcodedClass, transcoder));
}
private static final class Entry {
private final Class fromClass;
private final Class toClass;
@Synthetic final ResourceTranscoder transcoder;
Entry(@NonNull Class fromClass, @NonNull Class toClass,
@NonNull ResourceTranscoder transcoder) {
this.fromClass = fromClass;
this.toClass = toClass;
this.transcoder = transcoder;
}
/**
* If we convert from a specific Drawable, we must get that specific Drawable class or a
* subclass of that Drawable. In contrast, if we we convert to a specific Drawable,
* we can fulfill requests for a more generic parent class (like Drawable). As a result, we
* check fromClass and toClass in different orders.
*/
public boolean handles(@NonNull Class> fromClass, @NonNull Class> toClass) {
return this.fromClass.isAssignableFrom(fromClass) && toClass.isAssignableFrom(this.toClass);
}
}
public class BitmapDrawableTranscoder implements ResourceTranscoder {
private final Resources resources;
@SuppressWarnings("unused")
public BitmapDrawableTranscoder(@NonNull Context context) {
this(context.getResources());
}
public BitmapDrawableTranscoder(
@NonNull Resources resources, @SuppressWarnings("unused") BitmapPool bitmapPool) {
this(resources);
}
public BitmapDrawableTranscoder(@NonNull Resources resources) {
this.resources = Preconditions.checkNotNull(resources);
}
@Override
public Resource transcode(Resource toTranscode, Options options) {
return LazyBitmapDrawableResource.obtain(resources, toTranscode);
}
}
这个更简单,就是将Bitmap转换成BitmapDrawable
注册表就介绍完了,上面介绍了三个注册表(ModelLoaderRegistry, ResourceDecoderRegistry,TranscoderRegistry),这个三个都是跟加载网络图片相关的。
注册表是glide的一个核心部分,理解了这个才能理解整个流程
初始化完成后,再回过头来看
public static RequestManager with(@NonNull Activity activity) {
return getRetriever(activity).get(activity);
}
@NonNull
public RequestManager get(@NonNull Activity activity) {
if (Util.isOnBackgroundThread()) {
return get(activity.getApplicationContext());
} else {
assertNotDestroyed(activity);
android.app.FragmentManager fm = activity.getFragmentManager();
return fragmentGet(activity, fm, null /*parentHint*/);
}
}
private RequestManager fragmentGet(@NonNull Context context,
@NonNull android.app.FragmentManager fm,
@Nullable android.app.Fragment parentHint) {
//这里会添加一个fragment到当前activity里面,用于管理当前页面的生命周期
RequestManagerFragment current = getRequestManagerFragment(fm, parentHint);
RequestManager requestManager = current.getRequestManager();
if (requestManager == null) {
Glide glide = Glide.get(context);
//创建requestManager,并将它设置到fragment中
requestManager =
factory.build(
glide, current.getGlideLifecycle(), current.getRequestManagerTreeNode(), context);
current.setRequestManager(requestManager);
}
return requestManager;
}
好了,我们现在来看一下glide是如何管理生命周期的
在RequestManagerFragment的构造方法里面
public class RequestManagerFragment extends Fragment {
public RequestManagerFragment() {
this(new ActivityFragmentLifecycle());
}
//保存生命周期监听器
RequestManagerFragment(ActivityFragmentLifecycle lifecycle) {
this.lifecycle = lifecycle;
}
}
看一下ActivityFragmentLifecycle的实现
class ActivityFragmentLifecycle implements Lifecycle {
private final Set lifecycleListeners =
Collections.newSetFromMap(new WeakHashMap());
@Override
public void addListener(LifecycleListener listener) {
lifecycleListeners.add(listener);
if (isDestroyed) {
listener.onDestroy();
} else if (isStarted) {
listener.onStart();
} else {
listener.onStop();
}
}
void onStart() {
isStarted = true;
for (LifecycleListener lifecycleListener : Util.getSnapshot(lifecycleListeners)) {
lifecycleListener.onStart();
}
}
void onStop() {
isStarted = false;
for (LifecycleListener lifecycleListener : Util.getSnapshot(lifecycleListeners)) {
lifecycleListener.onStop();
}
}
void onDestroy() {
isDestroyed = true;
for (LifecycleListener lifecycleListener : Util.getSnapshot(lifecycleListeners)) {
lifecycleListener.onDestroy();
}
}
}
这里可以添加监听器,fragment生命周期的变化,会依次回调这里的监听器
在看看创建RequestManager的方法
Glide glide = Glide.get(context);
requestManager =
factory.build(
glide, current.getGlideLifecycle(), current.getRequestManagerTreeNode(), context);
current.setRequestManager(requestManager);
factory是下面的DEFAULT_FACTORY
private static final RequestManagerFactory DEFAULT_FACTORY = new RequestManagerFactory() {
public RequestManager build(@NonNull Glide glide, @NonNull Lifecycle lifecycle,
@NonNull RequestManagerTreeNode requestManagerTreeNode, @NonNull Context context) {
return new RequestManager(glide, lifecycle, requestManagerTreeNode, context);
}
};
再看一下RequestManager就很清楚了
public class RequestManager implements LifecycleListener,
RequestManager(
Glide glide,
Lifecycle lifecycle,
RequestManagerTreeNode treeNode,
RequestTracker requestTracker,
ConnectivityMonitorFactory factory,
Context context) {
this.glide = glide;
this.lifecycle = lifecycle;
this.treeNode = treeNode;
this.requestTracker = requestTracker;
this.context = context;
connectivityMonitor =
factory.build(
context.getApplicationContext(),
new RequestManagerConnectivityListener(requestTracker));
//添加生命周期监听器
if (Util.isOnBackgroundThread()) {
mainHandler.post(addSelfToLifecycle);
} else {
lifecycle.addListener(this);
}
lifecycle.addListener(connectivityMonitor);
setRequestOptions(glide.getGlideContext().getDefaultRequestOptions());
glide.registerRequestManager(this);
}
@Override
public void onStart() {
resumeRequests();
targetTracker.onStart();
}
@Override
public void onStop() {
pauseRequests();
targetTracker.onStop();
}
@Override
public void onDestroy() {
targetTracker.onDestroy();
for (Target> target : targetTracker.getAll()) {
clear(target);
}
targetTracker.clear();
requestTracker.clearRequests();
lifecycle.removeListener(this);
lifecycle.removeListener(connectivityMonitor);
mainHandler.removeCallbacks(addSelfToLifecycle);
glide.unregisterRequestManager(this);
}
}
总结一下,fragment是一个被观察者,有生命周期回调的接口集合,RequestManager将自己加到了观察者的集合里面,实现了加载跟随生命周期的功能
说了这么多,这就是Glide.with(this).load(imageUrl).into(imageView);里面的Glide.with(this)方法,该方法最后获得RequestManager。
load(imageUrl)
public class RequestManager implements LifecycleListener,
ModelTypes> {
public RequestBuilder load(@Nullable String string) {
return asDrawable().load(string);
}
public RequestBuilder asDrawable() {
return as(Drawable.class);
}
public RequestBuilder as(
@NonNull Class resourceClass) {
return new RequestBuilder<>(glide, this, resourceClass, context);
}
}
最后创建的是RequestBuilder
public class RequestBuilder implements Cloneable,
ModelTypes> {
protected RequestBuilder(Glide glide, RequestManager requestManager,
Class transcodeClass, Context context) {
this.glide = glide;
this.requestManager = requestManager;
//要转换的目标类型
this.transcodeClass = transcodeClass;
this.defaultRequestOptions = requestManager.getDefaultRequestOptions();
this.context = context;
this.transitionOptions = requestManager.getDefaultTransitionOptions(transcodeClass);
this.requestOptions = defaultRequestOptions;
this.glideContext = glide.getGlideContext();
}
}
//执行完asDrawable()后,得到该RequestBuilder,然后执行该类中的load(string)方法
public RequestBuilder load(@Nullable String string) {
return loadGeneric(string);
}
//到此结束,总结一下,执行Glide.with(this).load(imageUrl)中的load(imageUrl)方法,生成了RequestBuilder.
//在该类里面,保存了最终要转换的类型transcodeClass(drawable),数据源model
private RequestBuilder loadGeneric(@Nullable Object model) {
this.model = model;
isModelSet = true;
return this;
}
总结一下,这里生成了RequestBuilder,里面有目标数据类型transcodeClass(drawable),有数据源model(string)
into(imageView)
Glide.with(this).load(imageUrl).into(imageView);中的into(imageView)方法。还是在RequestBuilder里面
public class RequestBuilder implements Cloneable,
ModelTypes> {
public ViewTarget into(@NonNull ImageView view) {
return into(
glideContext.buildImageViewTarget(view, transcodeClass),
/*targetListener=*/ null,
requestOptions);
}
我们看一下glideContext.buildImageViewTarget(view, transcodeClass)里面具体干了什么事情
最后会执行到下面的方法
public class ImageViewTargetFactory {
public ViewTarget buildTarget(@NonNull ImageView view,
@NonNull Class clazz) {
if (Bitmap.class.equals(clazz)) {
return (ViewTarget) new BitmapImageViewTarget(view);
} else if (Drawable.class.isAssignableFrom(clazz)) {
return (ViewTarget) new DrawableImageViewTarget(view);
} else {
throw new IllegalArgumentException(
"Unhandled class: " + clazz + ", try .as*(Class).transcode(ResourceTranscoder)");
}
}
}
因为我们传的值是drawable,所以最后到了DrawableImageViewTarget里面
public class DrawableImageViewTarget extends ImageViewTarget {
public DrawableImageViewTarget(ImageView view) {
super(view);
}
public DrawableImageViewTarget(ImageView view, boolean waitForLayout) {
super(view, waitForLayout);
}
protected void setResource(@Nullable Drawable resource) {
view.setImageDrawable(resource);
}
}
该类的作用是更新imageview内容
再回到 into()方法
public class RequestBuilder implements Cloneable,
ModelTypes> {
//Y是DrawableImageViewTarget,TranscodeType是目标类型,drawable
private > Y into(
@NonNull Y target,
@Nullable RequestListener targetListener,
@NonNull RequestOptions options) {
Request request = buildRequest(target, targetListener, options);
Request previous = target.getRequest();
requestManager.clear(target);
target.setRequest(request);
requestManager.track(target, request);
return target;
}
private Request buildRequest(
Target target,
@Nullable RequestListener targetListener,
RequestOptions requestOptions) {
return buildRequestRecursive(
target,
targetListener,
/*parentCoordinator=*/ null,
transitionOptions,
requestOptions.getPriority(),
requestOptions.getOverrideWidth(),
requestOptions.getOverrideHeight(),
requestOptions);
}
private Request buildRequestRecursive(
Target target,
@Nullable RequestListener targetListener,
@Nullable RequestCoordinator parentCoordinator,
TransitionOptions, ? super TranscodeType> transitionOptions,
Priority priority,
int overrideWidth,
int overrideHeight,
RequestOptions requestOptions) {
// Build the ErrorRequestCoordinator first if necessary so we can update parentCoordinator.
ErrorRequestCoordinator errorRequestCoordinator = null;
if (errorBuilder != null) {
errorRequestCoordinator = new ErrorRequestCoordinator(parentCoordinator);
parentCoordinator = errorRequestCoordinator;
}
Request mainRequest =
buildThumbnailRequestRecursive(
target,
targetListener,
parentCoordinator,
transitionOptions,
priority,
overrideWidth,
overrideHeight,
requestOptions);
if (errorRequestCoordinator == null) {
return mainRequest;
}
return errorRequestCoordinator;
}
private Request obtainRequest(
Target target,
RequestListener targetListener,
RequestOptions requestOptions,
RequestCoordinator requestCoordinator,
TransitionOptions, ? super TranscodeType> transitionOptions,
Priority priority,
int overrideWidth,
int overrideHeight) {
return SingleRequest.obtain(
context,
glideContext,
model,
transcodeClass,
requestOptions,
overrideWidth,
overrideHeight,
priority,
target,
targetListener,
requestListener,
requestCoordinator,
glideContext.getEngine(),
transitionOptions.getTransitionFactory());
}
}
现在看一下SingleRequest
public final class SingleRequest implements Request,
SizeReadyCallback,
ResourceCallback,
FactoryPools.Poolable {
private void init(
Context context,
GlideContext glideContext,
Object model,
Class transcodeClass,
RequestOptions requestOptions,
int overrideWidth,
int overrideHeight,
Priority priority,
Target target,
RequestListener targetListener,
RequestListener requestListener,
RequestCoordinator requestCoordinator,
Engine engine,
TransitionFactory super R> animationFactory) {
this.context = context;
this.glideContext = glideContext;
//数据源 url
this.model = model;
//目标数据类型
this.transcodeClass = transcodeClass;
status = Status.PENDING;
}
}
回到刚刚的into方法
public class RequestBuilder implements Cloneable,
ModelTypes> {
private > Y into(
@NonNull Y target,
@Nullable RequestListener targetListener,
@NonNull RequestOptions options) {
options = options.autoClone();
Request request = buildRequest(target, targetListener, options);
requestManager.clear(target);
//将request设置给DrawableImageViewTarget,该类里面有imageview,现在有了request,齐了
target.setRequest(request);
requestManager.track(target, request);
return target;
}
}
看一下requestManager.track(target, request);
public class RequestManager implements LifecycleListener,
ModelTypes> {
private final RequestTracker requestTracker;
private final TargetTracker targetTracker = new TargetTracker();
void track(Target> target, Request request) {
targetTracker.track(target);
requestTracker.runRequest(request);
}
}
看一下TargetTracker的类
public final class TargetTracker implements LifecycleListener {
private final Set> targets =
Collections.newSetFromMap(new WeakHashMap, Boolean>());
public void track(Target> target) {
targets.add(target);
}
public void onStart() {
for (Target> target : Util.getSnapshot(targets)) {
target.onStart();
}
}
public void onStop() {
for (Target> target : Util.getSnapshot(targets)) {
target.onStop();
}
}
public void onDestroy() {
for (Target> target : Util.getSnapshot(targets)) {
target.onDestroy();
}
}
}
再看一下RequestManager里面对TargetTracker的调用
public class RequestManager implements LifecycleListener,
ModelTypes> {
//fragment的生命周期会调用这里,会触发到这里,然后触发到DrawableImageViewTarget
public void onStart() {
resumeRequests();
targetTracker.onStart();
}
public void onStop() {
pauseRequests();
targetTracker.onStop();
}
public void onDestroy() {
targetTracker.onDestroy();
for (Target> target : targetTracker.getAll()) {
clear(target);
}
targetTracker.clear();
requestTracker.clearRequests();
lifecycle.removeListener(this);
lifecycle.removeListener(connectivityMonitor);
mainHandler.removeCallbacks(addSelfToLifecycle);
glide.unregisterRequestManager(this);
}
public void resumeRequests() {
Util.assertMainThread();
requestTracker.resumeRequests();
}
public void pauseRequests() {
Util.assertMainThread();
requestTracker.pauseRequests();
}
}
看一下RequestTracker
public class RequestTracker {
private final Set requests =
Collections.newSetFromMap(new WeakHashMap());
//等待加载到request list
private final List pendingRequests = new ArrayList<>();
public void runRequest(Request request) {
requests.add(request);
if (!isPaused) {
//开始请求
request.begin();
} else {
//缓存起来
pendingRequests.add(request);
}
}
}
总结一下,先在activity中添加了一个空的fragment,这样就有了生命周期,fragment里面有个ActivityFragmentLifecycle类,该类是生命周期回调的集合,fragment生命周期变化会调用该类,RequestManager实现了生命周期的接口,然后将它加到了ActivityFragmentLifecycle里面。
RequestManager里面有targetTracker,targetTracker是Target(里面有imageview)的集合,在页面开始加载,调用onstart方法时会调用Target里面的onstart方法,这样可以做一下图片加载的预处理,比如设置占位图等。
RequestManager里面还有requestTracker,调用RequestManager调用requestTracker的track时,会直接加载图片。同时在生命周期回调onstart方法时,resumeRequests方法,将没有加载的request重新开始
由于篇幅的限制,网路加载图片的内容请看第二篇文章