private RequestManager getApplicationManager(Context context) { // Either an application context or we're on a background thread. if (applicationManager == null) { synchronized (this) { if (applicationManager == null) { // Normally pause/resume is taken care of by the fragment we add to the fragment or activity. // However, in this case since the manager attached to the application will not receive lifecycle // events, we must force the manager to start resumed using ApplicationLifecycle. applicationManager = new RequestManager(context.getApplicationContext(), new ApplicationLifecycle(), new EmptyRequestManagerTreeNode()); } } }
ConnectivityMonitor connectivityMonitor = factory.build(context, new RequestManagerConnectivityListener(requestTracker));
// If we're the application level request manager, we may be created on a background thread. In that case we // cannot risk synchronously pausing or resuming requests, so we hack around the issue by delaying adding // ourselves as a lifecycle listener by posting to the main thread. This should be entirely safe. 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); }
//单例模式创建Gilde对象 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); }
//GlideBuilder中的createGlide方法 if (sourceService == null) { final int cores = Math.max(1, Runtime.getRuntime().availableProcessors()); sourceService = new FifoPriorityThreadPoolExecutor(cores); } //下面的方法都是在FifoPriorityThreadPoolExecutor类中,且该类继承ThreadPoolExecutor public FifoPriorityThreadPoolExecutor(int poolSize) { this(poolSize, UncaughtThrowableStrategy.LOG); }
public FifoPriorityThreadPoolExecutor(int poolSize, UncaughtThrowableStrategy uncaughtThrowableStrategy) { this(poolSize, poolSize, 0, TimeUnit.MILLISECONDS, new DefaultThreadFactory(), uncaughtThrowableStrategy); }
public FifoPriorityThreadPoolExecutor(int corePoolSize, int maximumPoolSize, long keepAlive, TimeUnit timeUnit, ThreadFactory threadFactory, UncaughtThrowableStrategy uncaughtThrowableStrategy) { super(corePoolSize, maximumPoolSize, keepAlive, timeUnit, new PriorityBlockingQueue<Runnable>(), threadFactory); this.uncaughtThrowableStrategy = uncaughtThrowableStrategy; }
@Deprecated public DrawableTypeRequest<URL> load(URL url) { return (DrawableTypeRequest<URL>) fromUrl().load(url); }
@Deprecated public DrawableTypeRequest<URL> fromUrl() { return loadGeneric(URL.class); }
private <T> DrawableTypeRequest<T> loadGeneric(Class<T> modelClass) { 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"); }
public class DrawableTypeRequest<ModelType> extends DrawableRequestBuilder<ModelType> implements DownloadOptions { private final ModelLoader<ModelType, InputStream> streamModelLoader; private final ModelLoader<ModelType, ParcelFileDescriptor> fileDescriptorModelLoader; private final RequestManager.OptionsApplier optionsApplier;
/** * Attempts to always load the resource as a {@link android.graphics.Bitmap}, even if it could actually be animated. * * @return A new request builder for loading a {@link android.graphics.Bitmap} */ public BitmapTypeRequest<ModelType> asBitmap() { return optionsApplier.apply(new BitmapTypeRequest<ModelType>(this, streamModelLoader, fileDescriptorModelLoader, optionsApplier)); }
/** * Attempts to always load the resource as a {@link com.bumptech.glide.load.resource.gif.GifDrawable}. * <p> * If the underlying data is not a GIF, this will fail. As a result, this should only be used if the model * represents an animated GIF and the caller wants to interact with the GIfDrawable directly. Normally using * just an {@link com.bumptech.glide.DrawableTypeRequest} is sufficient because it will determine whether or * not the given data represents an animated GIF and return the appropriate animated or not animated * {@link android.graphics.drawable.Drawable} automatically. * </p> * * @return A new request builder for loading a {@link com.bumptech.glide.load.resource.gif.GifDrawable}. */ public GifTypeRequest<ModelType> asGif() { return optionsApplier.apply(new GifTypeRequest<ModelType>(this, streamModelLoader, optionsApplier)); }
/** * {@inheritDoc} */ public <Y extends Target<File>> Y downloadOnly(Y target) { return getDownloadOnlyRequest().downloadOnly(target); }
/** * {@inheritDoc} */ public FutureTarget<File> downloadOnly(int width, int height) { return getDownloadOnlyRequest().downloadOnly(width, height); }
/** * {@inheritDoc} * * <p> * Note - If no transformation is set for this load, a default transformation will be applied based on the * value returned from {@link android.widget.ImageView#getScaleType()}. To avoid this default transformation, * use {@link #dontTransform()}. * </p> * * @param view {@inheritDoc} * @return {@inheritDoc} */ @Override public Target<GlideDrawable> into(ImageView view) { return super.into(view); }
public Target<TranscodeType> into(ImageView view) { Util.assertMainThread();//判断是否在主线程 if (view == null) { throw new IllegalArgumentException("You must pass in a non null View"); }
if (!isTransformationSet && view.getScaleType() != null) { switch (view.getScaleType()) { case CENTER_CROP: applyCenterCrop(); break; case FIT_CENTER: case FIT_START: case FIT_END: applyFitCenter(); break; //$CASES-OMITTED$ default: // Do nothing. } }