寫在前面
有一段時(shí)間沒有寫過博客了,中間了看了一些雜七雜八的東西,也過了一部分的面試題,順帶提一句面試題我都是在鴻洋的https://www.wanandroid.com/ 看的,里面分類很多也比較的全,建議收藏
打開百度搜索Gilde源碼會(huì)出現(xiàn)幾百萬的搜索結(jié)果,但是我為什么還要再寫這篇博客呢?
第一 可以給后來的人指路。第二 可以都在哪怕是復(fù)述的時(shí)候,提高自己表達(dá)溝通的能力,第三 在加強(qiáng)自己的理解,哪怕是后面忘了也可以通過這篇文章在快速的回想起代碼中的一切。
這三點(diǎn)來說 第一點(diǎn)反而是最小的一點(diǎn),重點(diǎn)在第二第三點(diǎn)。
對(duì)于Glide來講,代碼中用了大量的復(fù)用,轉(zhuǎn)型等,所以建議大家在看源碼時(shí)把自己看的代碼用云筆記保存起來,方便回溯
對(duì)于Glide源碼來講,這應(yīng)該也是一個(gè)新坑,由于篇幅肯定不會(huì)一次性全部講完,具體要分幾節(jié)可能還要看具體的情況
對(duì)于第一篇Glide源碼解析來講,最主要的還是走一遍完整的網(wǎng)絡(luò)請(qǐng)求的流程,選用Glide版本是3.7.0。因?yàn)檫@個(gè)是我第一次接觸Glide使用的版本,之前也看過一部分的代碼,為了省事,我還是選用了這個(gè)版本
首先我們現(xiàn)在看一下Glide的使用方法
String s = "https://ss0.baidu.com/6ONWsjip0QIZ8tyhnq/it/u=1066881363,1963636720&fm=173&app=25&f=JPEG?w=639&h=426&s=BF104C810E535FD624B4D89F0300C080";
Glide.with(MainActivity.this).load(s).into(imageView);
這個(gè)是最基本的使用方法,分為with,load,into三個(gè)步驟,我們一個(gè)個(gè)看過來
with
public static RequestManager with(FragmentActivity activity) {
RequestManagerRetriever retriever = RequestManagerRetriever.get();
return retriever.get(activity);
}
public RequestManager get(FragmentActivity activity) {
if (Util.isOnBackgroundThread()) {
//如果不在主線程復(fù)用get(context)的方法
return get(activity.getApplicationContext());
} else {
assertNotDestroyed(activity);
//獲取出一個(gè)FragmentManager來監(jiān)聽Activity的生命周期
FragmentManager fm = activity.getSupportFragmentManager();
return supportFragmentGet(activity, fm);
}
}
//關(guān)鍵代碼
RequestManager supportFragmentGet(Context context, FragmentManager fm) {
//需要關(guān)注這個(gè)方法
SupportRequestManagerFragment current = getSupportRequestManagerFragment(fm);
RequestManager requestManager = current.getRequestManager();
if (requestManager == null) {
requestManager = new RequestManager(context, current.getLifecycle(), current.getRequestManagerTreeNode());
current.setRequestManager(requestManager);
}
return requestManager;
}
通過fm獲取出來一個(gè)SupportRequestManagerFragment對(duì)象,看一下這個(gè)是怎么獲取的
SupportRequestManagerFragment getSupportRequestManagerFragment(final FragmentManager fm) {
SupportRequestManagerFragment current = (SupportRequestManagerFragment) fm.findFragmentByTag(
FRAGMENT_TAG);
if (current == null) {
current = pendingSupportRequestManagerFragments.get(fm);
if (current == null) {
current = new SupportRequestManagerFragment();
pendingSupportRequestManagerFragments.put(fm, current);
fm.beginTransaction().add(current, FRAGMENT_TAG).commitAllowingStateLoss();
handler.obtainMessage(ID_REMOVE_SUPPORT_FRAGMENT_MANAGER, fm).sendToTarget();
}
}
return current;
}
這里的邏輯比較清晰了,通過fm創(chuàng)建了一個(gè)空白的Fragment,并溝通過接口的方式監(jiān)聽了這個(gè)Fragment的生命周期,具體的實(shí)現(xiàn)可以通過看SupportRequestManagerFragment構(gòu)造器得知。
繼續(xù)看下去
RequestManager supportFragmentGet(Context context, FragmentManager fm) {
//需要關(guān)注這個(gè)方法
SupportRequestManagerFragment current = getSupportRequestManagerFragment(fm);
RequestManager requestManager = current.getRequestManager();
if (requestManager == null) {
requestManager = new RequestManager(context, current.getLifecycle(), current.getRequestManagerTreeNode());
current.setRequestManager(requestManager);
}
return requestManager;
}
初始話了一個(gè)RequestManager對(duì)象并返回,我們看一下RequestManager的構(gòu)造器
public RequestManager(Context context, Lifecycle lifecycle, RequestManagerTreeNode treeNode) {
this(context, lifecycle, treeNode, new RequestTracker(), new ConnectivityMonitorFactory());
}
RequestManager(Context context, final Lifecycle lifecycle, RequestManagerTreeNode treeNode,
RequestTracker requestTracker, ConnectivityMonitorFactory factory) {
this.context = context.getApplicationContext();
this.lifecycle = lifecycle;
this.treeNode = treeNode;
this.requestTracker = requestTracker;
//初始話了Glide
this.glide = Glide.get(context);
this.optionsApplier = new OptionsApplier();
ConnectivityMonitor connectivityMonitor = factory.build(context,
new RequestManagerConnectivityListener(requestTracker));
if (Util.isOnBackgroundThread()) {
new Handler(Looper.getMainLooper()).post(new Runnable() {
@Override
public void run() {
lifecycle.addListener(RequestManager.this);
}
});
} else {
lifecycle.addListener(this);
}
lifecycle.addListener(connectivityMonitor);
}
可以看到這里面做了部分?jǐn)?shù)據(jù)的初始話,其中比較重要的就是Glide的初始話,我們可以看一下Glide的初始話方法
public static Glide get(Context context) {
if (glide == null) {
synchronized (Glide.class) {
if (glide == null) {
Context applicationContext = context.getApplicationContext();
List<GlideModule> modules = new ManifestParser(applicationContext).parse();
GlideBuilder builder = new GlideBuilder(applicationContext);
for (GlideModule module : modules) {
module.applyOptions(applicationContext, builder);
}
glide = builder.createGlide();
for (GlideModule module : modules) {
module.registerComponents(applicationContext, glide);
}
}
}
}
return glide;
}
Glide createGlide() {
if (sourceService == null) {
final int cores = Math.max(1, Runtime.getRuntime().availableProcessors());
sourceService = new FifoPriorityThreadPoolExecutor(cores);
}
if (diskCacheService == null) {
diskCacheService = new FifoPriorityThreadPoolExecutor(1);
}
MemorySizeCalculator calculator = new MemorySizeCalculator(context);
if (bitmapPool == null) {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.HONEYCOMB) {
int size = calculator.getBitmapPoolSize();
bitmapPool = new LruBitmapPool(size);
} else {
bitmapPool = new BitmapPoolAdapter();
}
}
if (memoryCache == null) {
memoryCache = new LruResourceCache(calculator.getMemoryCacheSize());
}
if (diskCacheFactory == null) {
diskCacheFactory = new InternalCacheDiskCacheFactory(context);
}
if (engine == null) {
engine = new Engine(memoryCache, diskCacheFactory, diskCacheService, sourceService);
}
if (decodeFormat == null) {
decodeFormat = DecodeFormat.DEFAULT;
}
return new Glide(engine, memoryCache, bitmapPool, context, decodeFormat);
}
Glide(Engine engine, MemoryCache memoryCache, BitmapPool bitmapPool, Context context, DecodeFormat decodeFormat) {
this.engine = engine;
this.bitmapPool = bitmapPool;
this.memoryCache = memoryCache;
this.decodeFormat = decodeFormat;
loaderFactory = new GenericLoaderFactory(context);
mainHandler = new Handler(Looper.getMainLooper());
bitmapPreFiller = new BitmapPreFiller(memoryCache, bitmapPool, decodeFormat);
dataLoadProviderRegistry = new DataLoadProviderRegistry();
StreamBitmapDataLoadProvider streamBitmapLoadProvider =
new StreamBitmapDataLoadProvider(bitmapPool, decodeFormat);
dataLoadProviderRegistry.register(InputStream.class, Bitmap.class, streamBitmapLoadProvider);
FileDescriptorBitmapDataLoadProvider fileDescriptorLoadProvider =
new FileDescriptorBitmapDataLoadProvider(bitmapPool, decodeFormat);
dataLoadProviderRegistry.register(ParcelFileDescriptor.class, Bitmap.class, fileDescriptorLoadProvider);
ImageVideoDataLoadProvider imageVideoDataLoadProvider =
new ImageVideoDataLoadProvider(streamBitmapLoadProvider, fileDescriptorLoadProvider);
dataLoadProviderRegistry.register(ImageVideoWrapper.class, Bitmap.class, imageVideoDataLoadProvider);
GifDrawableLoadProvider gifDrawableLoadProvider =
new GifDrawableLoadProvider(context, bitmapPool);
dataLoadProviderRegistry.register(InputStream.class, GifDrawable.class, gifDrawableLoadProvider);
dataLoadProviderRegistry.register(ImageVideoWrapper.class, GifBitmapWrapper.class,
new ImageVideoGifDrawableLoadProvider(imageVideoDataLoadProvider, gifDrawableLoadProvider, bitmapPool));
dataLoadProviderRegistry.register(InputStream.class, File.class, new StreamFileDataLoadProvider());
register(File.class, ParcelFileDescriptor.class, new FileDescriptorFileLoader.Factory());
register(File.class, InputStream.class, new StreamFileLoader.Factory());
register(int.class, ParcelFileDescriptor.class, new FileDescriptorResourceLoader.Factory());
register(int.class, InputStream.class, new StreamResourceLoader.Factory());
register(Integer.class, ParcelFileDescriptor.class, new FileDescriptorResourceLoader.Factory());
register(Integer.class, InputStream.class, new StreamResourceLoader.Factory());
register(String.class, ParcelFileDescriptor.class, new FileDescriptorStringLoader.Factory());
register(String.class, InputStream.class, new StreamStringLoader.Factory());
register(Uri.class, ParcelFileDescriptor.class, new FileDescriptorUriLoader.Factory());
register(Uri.class, InputStream.class, new StreamUriLoader.Factory());
register(URL.class, InputStream.class, new StreamUrlLoader.Factory());
register(GlideUrl.class, InputStream.class, new HttpUrlGlideUrlLoader.Factory());
register(byte[].class, InputStream.class, new StreamByteArrayLoader.Factory());
transcoderRegistry.register(Bitmap.class, GlideBitmapDrawable.class,
new GlideBitmapDrawableTranscoder(context.getResources(), bitmapPool));
transcoderRegistry.register(GifBitmapWrapper.class, GlideDrawable.class,
new GifBitmapWrapperDrawableTranscoder(
new GlideBitmapDrawableTranscoder(context.getResources(), bitmapPool)));
bitmapCenterCrop = new CenterCrop(bitmapPool);
drawableCenterCrop = new GifBitmapWrapperTransformation(bitmapPool, bitmapCenterCrop);
bitmapFitCenter = new FitCenter(bitmapPool);
drawableFitCenter = new GifBitmapWrapperTransformation(bitmapPool, bitmapFitCenter);
}
這里面做了很多東西的初始話,包括圖片三級(jí)緩存中的disk緩存和內(nèi)存緩存,還有注冊(cè)了一部分的方法,這里先不展開,我們只需要了解這些東西即可。
到這里基本上,第一個(gè)with方法就講完了,總結(jié)一下with干的內(nèi)容:
1.獲取了傳入Activity的fragmentManager,并且創(chuàng)建了一個(gè)空白的fragment用于監(jiān)聽Activity的生命周期,并最終封裝了一個(gè)requestManager
2.初始話了大量的參數(shù),其中包括了Glide本身,disk緩存和內(nèi)存緩存等。
load
先看一下load的用法
load("https://ss0.baidu.com/6ONWsjip0QIZ8tyhnq/it/u=1066881363,1963636720&fm=173&app=25&f=JPEG?w=639&h=426&s=BF104C810E535FD624B4D89F0300C080")
傳入的類型是String,看一下這個(gè)代碼的具體實(shí)現(xiàn)
public DrawableTypeRequest<File> load(File file) {
return (DrawableTypeRequest<File>) fromFile().load(file);
}
public DrawableTypeRequest<Uri> loadFromMediaStore(Uri uri) {
return (DrawableTypeRequest<Uri>) fromMediaStore().load(uri);
}
public DrawableTypeRequest<Integer> load(Integer resourceId) {
return (DrawableTypeRequest<Integer>) fromResource().load(resourceId);
}
public DrawableTypeRequest<URL> load(URL url) {
return (DrawableTypeRequest<URL>) fromUrl().load(url);
}
public DrawableTypeRequest<String> load(String string) {
return (DrawableTypeRequest<String>) fromString().load(string);
}
這個(gè)方法有多個(gè)重載,對(duì)于傳入String的方法的具體實(shí)現(xiàn),主要關(guān)注fromString()這個(gè)方法
public DrawableTypeRequest<String> fromString() {
return loadGeneric(String.class);
}
private <T> DrawableTypeRequest<T> loadGeneric(Class<T> modelClass) {
//獲取到相應(yīng)的加載器
ModelLoader<T, InputStream> streamModelLoader = Glide.buildStreamModelLoader(modelClass, context);
ModelLoader<T, ParcelFileDescriptor> fileDescriptorModelLoader =
Glide.buildFileDescriptorModelLoader(modelClass, context);
if (modelClass != null && streamModelLoader == null && fileDescriptorModelLoader == null) {
throw new IllegalArgumentException("Unknown type " + modelClass + ". You must provide a Model of a type for"
+ " which there is a registered ModelLoader, if you are using a custom model, you must first call"
+ " Glide#register with a ModelLoaderFactory for your custom model class");
}
return optionsApplier.apply(
new DrawableTypeRequest<T>(modelClass, streamModelLoader, fileDescriptorModelLoader, context,
glide, requestTracker, lifecycle, optionsApplier));
}
這里最后return的值我們就把他看成new DrawableTypeRequest即可,這里完成大量的數(shù)據(jù)構(gòu)建,創(chuàng)建出來的兩個(gè)ModelLoader這里先不講,具體話會(huì)跟前一步的Glide的構(gòu)造器里面的register方法有關(guān),具體返回的值是HttpUrlGlideUrlLoader。接下來看一下DrawableTypeRequest的構(gòu)造方法
DrawableTypeRequest(Class<ModelType> modelClass, ModelLoader<ModelType, InputStream> streamModelLoader,
ModelLoader<ModelType, ParcelFileDescriptor> fileDescriptorModelLoader, Context context, Glide glide,
RequestTracker requestTracker, Lifecycle lifecycle, RequestManager.OptionsApplier optionsApplier) {
super(context, modelClass,
buildProvider(glide, streamModelLoader, fileDescriptorModelLoader, GifBitmapWrapper.class,
GlideDrawable.class, null),
glide, requestTracker, lifecycle);
this.streamModelLoader = streamModelLoader;
this.fileDescriptorModelLoader = fileDescriptorModelLoader;
this.optionsApplier = optionsApplier;
}
關(guān)注一下buildProvider方法
private static <A, Z, R> FixedLoadProvider<A, ImageVideoWrapper, Z, R> buildProvider(Glide glide,
ModelLoader<A, InputStream> streamModelLoader,
ModelLoader<A, ParcelFileDescriptor> fileDescriptorModelLoader, Class<Z> resourceClass,
Class<R> transcodedClass,
ResourceTranscoder<Z, R> transcoder) {
if (streamModelLoader == null && fileDescriptorModelLoader == null) {
return null;
}
if (transcoder == null) {
transcoder = glide.buildTranscoder(resourceClass, transcodedClass);
}
DataLoadProvider<ImageVideoWrapper, Z> dataLoadProvider = glide.buildDataProvider(ImageVideoWrapper.class,
resourceClass);
ImageVideoModelLoader<A> modelLoader = new ImageVideoModelLoader<A>(streamModelLoader,
fileDescriptorModelLoader);
return new FixedLoadProvider<A, ImageVideoWrapper, Z, R>(modelLoader, transcoder, dataLoadProvider);
}
返回了一個(gè)FixedLoadProvider對(duì)象,這個(gè)對(duì)象在后面會(huì)用到記錄一下。
由于篇幅,暫時(shí)先講到這里,總結(jié)一下,with和load主要就是對(duì)Glide的初始化參數(shù)的,另外with會(huì)對(duì)當(dāng)前頁面創(chuàng)建一個(gè)FragmentManager,再用這個(gè)fm創(chuàng)建一個(gè)空的fragment來進(jìn)行對(duì)于這個(gè)頁面的更新,另外with方法還對(duì)Glide進(jìn)行初始化,并注冊(cè)了相應(yīng)的moderLoader。而load主要根據(jù)傳入的參數(shù)決定了對(duì)應(yīng)的moderLoader。