深入剖析Glide源码-4.15版本(一)

@[toc]

Glide作为android中最主流的几个图片加载框架之一,是面试中问到的必不可少的一种框架。它看似简单的外表下,实则隐藏着一个庞然大物,今天我们就把块硬骨头啃上一啃~。

glide在4.15版本生命周期管理与注册机管理进行了改进,我们从4.11版本开始看,流程读懂了再研究4.15版本是如何演化的。

一行代码进行图片加载

使用glide,一行代码就可以进行图片加载,我们从主干流程出发,抽丝剥茧,揭开他的真面目吧~

val ivImage = findViewById<ImageView>(R.id.ivImage)
// 
Glide.with(activity).load("").into(ivImage)
// 
Glide.with(fragment).load("").into(ivImage)
// 
Glide.with(view).load("").into(ivImage)

从调用看,可以把它分为3大主要流程

  • with
  • load
  • into

一、生命周期管理

下面来看第一大流程:with,我们以传入activity为例,正如题所示,这个方法是进行生命周期管理的

// Glide.java
public static RequestManager with(@NonNull Activity activity) {
  return getRetriever(activity).get(activity);
}

Glide初始化

可以看到,其最终返回了一个RequestManager对象,那么它是如何构造的呢?继续往下看

// Glide.java

private final RequestManagerRetriever requestManagerRetriever;


@NonNull
private static RequestManagerRetriever getRetriever(@Nullable Context context) {
  return Glide.get(context).getRequestManagerRetriever();
}


public static Glide get(@NonNull Context context) {
    if (glide == null) {
      GeneratedAppGlideModule annotationGeneratedModule =
          getAnnotationGeneratedGlideModules(context.getApplicationContext());
      synchronized (Glide.class) {
        if (glide == null) {
          checkAndInitializeGlide(context, annotationGeneratedModule);
        }
      }
    }

    return glide;
  }


public RequestManagerRetriever getRequestManagerRetriever() {
    return requestManagerRetriever;
}

可以分析如下几点:

  • RequestManager是从RequestManagerRetriever拿到的。

  • Glide.get(context)方法是一个单例,最终返回Glide对象,后又调用了getRequestManagerRetriever方法,直接返回了requestManagerRetriever变量。

  • 看这个变量是一个final类型的,那么,它必然是在构造方法中初始化的。知道了这个原理,那么来看一看Glide对象是如何new出来的。

上面代码中可以看到调用了checkAndInitializeGlide方法

// Glide.java

@GuardedBy("Glide.class")
private static void checkAndInitializeGlide(
      @NonNull Context context, @Nullable GeneratedAppGlideModule generatedAppGlideModule) {
    if (isInitializing) {
      throw new IllegalStateException(
          "You cannot call Glide.get() in registerComponents(),"
              + " use the provided Glide instance instead");
    }
    isInitializing = true;
    // 调用initializeGlide方法
    initializeGlide(context, generatedAppGlideModule);
    isInitializing = false;
}
// Glide.java

@GuardedBy("Glide.class")
private static void initializeGlide(
      @NonNull Context context, @Nullable GeneratedAppGlideModule generatedAppGlideModule) {
    initializeGlide(context, new GlideBuilder(), generatedAppGlideModule);
}

注意这里传入了一个GlideBuilder对象

// Glide.java

private static void initializeGlide(
      @NonNull Context context,
      @NonNull GlideBuilder builder,
      @Nullable GeneratedAppGlideModule annotationGeneratedModule) {
    
    Context applicationContext = context.getApplicationContext();
    
    // 省略了一大段代码。。。
    Glide glide = builder.build(applicationContext);
    // 省略了一大段代码。。。
    Glide.glide = glide;
  }

为了看清主干流程,这里省略了扰乱我们视线的一些代码,可以看到,最终调用了GlideBuilder#build()

// GlideBuilder.java
@NonNull
Glide build(@NonNull Context context) {
    
    // 1. 初始化一些线程池和缓存池, 这些对象可以先记住
    //    后续会明白他们都是干什么用的
    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);
    }
    
    // 这里对象进行图片读取和加载,我们知道初始化了Engine对象即可,不需要知道它是做什么的
    if (engine == null) {
      engine =
          new Engine(
              memoryCache,
              diskCacheFactory,
              diskCacheExecutor,
              sourceExecutor,
              GlideExecutor.newUnlimitedSourceExecutor(),
              animationExecutor,
              isActiveResourceRetentionAllowed);
    }

    if (defaultRequestListeners == null) {
      defaultRequestListeners = Collections.emptyList();
    } else {
      defaultRequestListeners = Collections.unmodifiableList(defaultRequestListeners);
    }

    GlideExperiments experiments = glideExperimentsBuilder.build();
    RequestManagerRetriever requestManagerRetriever =
        new RequestManagerRetriever(requestManagerFactory, experiments);

    return new Glide(
        context,
        engine,
        memoryCache,
        bitmapPool,
        arrayPool,
        requestManagerRetriever,
        connectivityMonitorFactory,
        logLevel,
        defaultRequestOptionsFactory,
        defaultTransitionOptions,
        defaultRequestListeners,
        experiments);
}

现在知道了Glide是在这new出来的,并传入了一个RequestManagerRetriever对象,这里便形成了一个小闭环,那么我们回到主线,with方法是调用了RequestManagerRetriever#get()从而获取到一个RequestManager对象

@NonNull
public RequestManager get(@NonNull Context context) {
  if (context == null) {
    throw new IllegalArgumentException("You cannot start a load on a null Context");
  // 主线程并且context不是application时
  } else if (Util.isOnMainThread() && !(context instanceof Application)) {
    if (context instanceof FragmentActivity) {
      return get((FragmentActivity) context);
    } else if (context instanceof Activity) {
      return get((Activity) context);
    } else if (context instanceof ContextWrapper&& ((ContextWrapper)        context).getBaseContext().getApplicationContext() != null) {
      return get(((ContextWrapper) context).getBaseContext());
    }
  }
   // 子线程或context为application时
  return getApplicationManager(context);
}

RequestManager对象的构建分为了两种情况

  • 主线程,并且context不是application时:调用get()方法
  • 子线程或context为application时:调用getApplicationManager(context)

为什么要这样判断呢,下面重点来了,生命周期管理正是在这两个方法中进行的。如果context是application时,它的生命周期跟随app的灭亡而销毁,否则我们可以根据activity的生命周期来进行管理

RequestManager构建

1. 传入activity时

@NonNull
public RequestManager get(@NonNull FragmentActivity activity) {
  if (Util.isOnBackgroundThread()) {
    return get(activity.getApplicationContext());
  } else {
    assertNotDestroyed(activity);
    frameWaiter.registerSelf(activity);
    FragmentManager fm = activity.getSupportFragmentManager();
    return supportFragmentGet(activity, fm, /*parentHint=*/ null, isActivityVisible(activity));
  }
}

1)调用supportFragmentGet方法

@NonNull
private RequestManager supportFragmentGet(
    @NonNull Context context,
    @NonNull FragmentManager fm,
    @Nullable Fragment parentHint,
    boolean isParentVisible) {
  SupportRequestManagerFragment current = getSupportRequestManagerFragment(fm, parentHint);
  RequestManager requestManager = current.getRequestManager();
  if (requestManager == null) {
    Glide glide = Glide.get(context);
    // 创建requestManager并传入current.getGlideLifecycle()
    requestManager =
        factory.build(
            glide, current.getGlideLifecycle(), current.getRequestManagerTreeNode(), context);
    if (isParentVisible) {
      requestManager.onStart();
    }
    current.setRequestManager(requestManager);
  }
  return requestManager;
}

2)factory是什么?我们可以看到,RequestManager对象是通过factory.build()创建的

// RequestManagerRetriever.java

private final RequestManagerFactory factory;

public RequestManagerRetriever(
    @Nullable RequestManagerFactory factory, GlideExperiments experiments) {
  // 如果不传入,那么将使用DEFAULT_FACTORY
  this.factory = factory != null ? factory : DEFAULT_FACTORY;
}

// 默认的构造器
  private static final RequestManagerFactory DEFAULT_FACTORY =
      new RequestManagerFactory() {
        @NonNull
        @Override
        public RequestManager build(
            @NonNull Glide glide,
            @NonNull Lifecycle lifecycle,
            @NonNull RequestManagerTreeNode requestManagerTreeNode,
            @NonNull Context context) {
          return new RequestManager(glide, lifecycle, requestManagerTreeNode, context);
        }
      };

3)RequestManager对象就创建出来了,但是创建之前,还有一个fragment(SupportRequestManagerFragment),那么这是个什么东西呢?看看它怎么获取的

@NonNull
private SupportRequestManagerFragment getSupportRequestManagerFragment(
    @NonNull final FragmentManager fm, @Nullable Fragment parentHint) {
  // 1. 根据tag获取fragment
  SupportRequestManagerFragment current =
      (SupportRequestManagerFragment) fm.findFragmentByTag(FRAGMENT_TAG);
  if (current == null) {
    // 2. tag获取不到,从pendingSupportRequestManagerFragments中获取
    current = pendingSupportRequestManagerFragments.get(fm);
    if (current == null) {
      // 3. 缓存中没有就直接new即可
      current = new SupportRequestManagerFragment();
      current.setParentFragmentHint(parentHint);
      // 4. 将fragment缓存
      pendingSupportRequestManagerFragments.put(fm, current);
      // 5. commitAllowingStateLoss调用这个方法提交
      fm.beginTransaction().add(current, FRAGMENT_TAG).commitAllowingStateLoss();
      // 6.发送消息,讲fragmnet从缓存中移除
      handler.obtainMessage(ID_REMOVE_SUPPORT_FRAGMENT_MANAGER, fm).sendToTarget();
    }
  }
  return current;
}

以上代码明显是创建了一个fragment,所以生命周期管理就是靠这个fragment来进行了。我们来看看这个fragment的构造方法

public class SupportRequestManagerFragment extends Fragment {
    
    private final ActivityFragmentLifecycle lifecycle;
    
    public SupportRequestManagerFragment() {
        this(new ActivityFragmentLifecycle());
    }

    
    public SupportRequestManagerFragment(ActivityFragmentLifecycle lifecycle) {
        this.lifecycle = lifecycle;
    }
    
    
    
    /**
     * 以下是生命周期方法
     */
    @Override
    public void onStart() {
        super.onStart();
        lifecycle.onStart();
    }

    @Override
    public void onStop() {
        super.onStop();
        lifecycle.onStop();
    }

    @Override
    public void onDestroy() {
        super.onDestroy();
        lifecycle.onDestroy();
        unregisterFragmentWithRoot();
    }
}

这里创建了一个ActivityFragmentLifecycle对象,生命周期执行时分别调用了lifecycle中的三个方法

class ActivityFragmentLifecycle implements Lifecycle {
    
  // 这个集合用于保存所有的listener
  private final Set<LifecycleListener> lifecycleListeners =
      Collections.newSetFromMap(new WeakHashMap<LifecycleListener, Boolean>());
  private boolean isStarted;
  private boolean isDestroyed;

  // 添加一个listener
  @Override
  public void addListener(@NonNull LifecycleListener listener) {
    lifecycleListeners.add(listener);

    if (isDestroyed) {
      listener.onDestroy();
    } else if (isStarted) {
      listener.onStart();
    } else {
      listener.onStop();
    }
  }
  
  // 移除一个listener
  @Override
  public void removeListener(@NonNull LifecycleListener listener) {
    lifecycleListeners.remove(listener);
  }
  
  // start生命周期执行时
  void onStart() {
    isStarted = true;
    for (LifecycleListener lifecycleListener : Util.getSnapshot(lifecycleListeners)) {
      lifecycleListener.onStart();
    }
  }
    
  // stop生命周期执行时
  void onStop() {
    isStarted = false;
    for (LifecycleListener lifecycleListener : Util.getSnapshot(lifecycleListeners)) {
      lifecycleListener.onStop();
    }
  }
  
  // destory生命周期执行时
  void onDestroy() {
    isDestroyed = true;
    for (LifecycleListener lifecycleListener : Util.getSnapshot(lifecycleListeners)) {
      lifecycleListener.onDestroy();
    }
  }
}

这样生命周期管理就完成了,如果一个对象需要进行生命周期管理时,只需要实现LifecycleListener接口,并调用ActivityFragmentLifecycle#addListener()方法,就可以自动进行生命周期管理了。

好,我们回到第1)步骤,创建requestManager时,传入了current.getGlideLifecycle(),这个就是fragment中的ActivityFragmentLifecycle对象了

requestManager =
        factory.build(
            glide, current.getGlideLifecycle(), current.getRequestManagerTreeNode(), context);


// current.getGlideLifecycle()就是下面这个方法
// SupportRequestManagerFragment.java
// 
ActivityFragmentLifecycle getGlideLifecycle() {
    return lifecycle;
}

通过DEFAULT_FACTORY构建requestManager时,lifecycle作为了一个构造参数:

public RequestManager(
    @NonNull Glide glide,
    @NonNull Lifecycle lifecycle,
    @NonNull RequestManagerTreeNode treeNode,
    @NonNull Context context) {
  this(
      glide,
      lifecycle,
      treeNode,
      new RequestTracker(),
      glide.getConnectivityMonitorFactory(),
      context);
}
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()) {
    Util.postOnUiThread(addSelfToLifecycle);
  } else {
    // RequestManager实现了LifecycleListener, 所以它可以自己进行生命周期绑定
    lifecycle.addListener(this);
  }
  // 将网络连接监听器与生命周期绑定
  lifecycle.addListener(connectivityMonitor);

  defaultRequestListeners =
      new CopyOnWriteArrayList<>(glide.getGlideContext().getDefaultRequestListeners());
  setRequestOptions(glide.getGlideContext().getDefaultRequestOptions());

  glide.registerRequestManager(this);
}

这样,当fragment执行生命周期onStart()时,就会调用lifecycle.onStart(),在通过lifecycle回调到RequestManager中的onStart()。生命周期管理就这样简单的完成了,同时也意味着,所有的逻辑都是从RequestManager出发的。

RequestManager生命周期

我们来看看RequestManager的生命周期方法

@Override
public synchronized void onStart() {
  resumeRequests();
  targetTracker.onStart();
}

@Override
public synchronized void onStop() {
  pauseRequests();
  targetTracker.onStop();
}

@Override
public synchronized void onDestroy() {
  targetTracker.onDestroy();
  for (Target<?> target : targetTracker.getAll()) {
    clear(target);
  }
  targetTracker.clear();
  requestTracker.clearRequests();
  lifecycle.removeListener(this);
  lifecycle.removeListener(connectivityMonitor);
  Util.removeCallbacksOnUiThread(addSelfToLifecycle);
  glide.unregisterRequestManager(this);
}

onStartonStop中分别调用了resumeRequestspauseRequests

public synchronized void resumeRequests() {
    requestTracker.resumeRequests();
}

// RequestTracker.java
public void resumeRequests() {
  isPaused = false;
  for (Request request : Util.getSnapshot(requests)) {
    if (!request.isComplete() && !request.isRunning()) {
      request.begin();
    }
  }
  pendingRequests.clear();
}
public synchronized void pauseRequests() {
  requestTracker.pauseRequests();
}

// RequestTracker.java
public void pauseRequests() {
    isPaused = true;
    for (Request request : Util.getSnapshot(requests)) {
      if (request.isRunning()) {
        request.pause();
        pendingRequests.add(request);
      }
    }
  }

可以看到:

onStart时,将所有的请求进行启动,并清空等待队列;

onStop时,将所有的请求暂停,并加入到等待队列中;

target生命周期

我们知道,当RequestManager进入生命周期时,进行了图片加载的启动与暂停,除此之外,还有一行代码,targetTracker.onStart()targetTracker.onStop()

private final TargetTracker targetTracker = new TargetTracker();


synchronized void track(@NonNull Target<?> target, @NonNull Request request) {
    targetTracker.track(target);
    requestTracker.runRequest(request);
}

请记住这个方法!!!Target对象也实现了LifecycleListener ,当其它类调用RequestManagertrack方法时,相当于也把自己加入到了生命周期管理里面。这个地方将会真正的开始第一次网络请求,请记住requestTracker.runRequest(request);方法,我们在第三大步骤中重点讲到。

至此,RequestManager返回给with函数,第一个步骤就完成了。

2. 传入application时

让我们的思绪回到RequestManager的构建,当context是一个application时,它将跟随app的生命周期而执行

@NonNull
private RequestManager getApplicationManager(@NonNull Context context) {
  if (applicationManager == null) {
    synchronized (this) {
      if (applicationManager == null) {
        Glide glide = Glide.get(context.getApplicationContext());
        applicationManager =
            factory.build(
                glide,
                new ApplicationLifecycle(),
                new EmptyRequestManagerTreeNode(),
                context.getApplicationContext());
      }
    }
  }

  return applicationManager;
}

可以看到,返回了applicationManager,通过factory构建时,传入了ApplicationLifecycle,而并非fragment中的,因为application不能监听页面的生命周期,所以索性都不创建fragment了。

class ApplicationLifecycle implements Lifecycle {
  @Override
  public void addListener(@NonNull LifecycleListener listener) {
    listener.onStart();
  }

  @Override
  public void removeListener(@NonNull LifecycleListener listener) {
    // Do nothing.
  }
}

可以看到,application很简单,在addListener时,调用onStart即可,remove时不需要进行任何操作。

二、最新版本优化

明白了它的生命周期管理,那么我们看看最新版本有什么改变呢?

了解过androidxLifecycle的同学知道,它“抄袭“了Glide框架中的思想,每个页面也创建了一个空白的fragment,用于管理它们的生命周期。这样我们在用Glide的时候,一个页面就会创建两个空白的fragment,可能是出于这方面的考虑,Glide在最新版本中进行了优化,使用了androidxLifecycle进行生命周期管理。

我们看getRetriever(activity).get(activity);中的get方法

// RequestManagerRetriever.java

private final LifecycleRequestManagerRetriever lifecycleRequestManagerRetriever;

public RequestManagerRetriever(
      @Nullable RequestManagerFactory factory, GlideExperiments experiments) {
    this.factory = factory != null ? factory : DEFAULT_FACTORY;

    lifecycleRequestManagerRetriever = new LifecycleRequestManagerRetriever(this.factory);
}


@NonNull
public RequestManager get(@NonNull FragmentActivity activity) {
  if (Util.isOnBackgroundThread()) {
    return get(activity.getApplicationContext());
  }
  assertNotDestroyed(activity);
  frameWaiter.registerSelf(activity);
  boolean isActivityVisible = isActivityVisible(activity);
  Glide glide = Glide.get(activity.getApplicationContext());
  return lifecycleRequestManagerRetriever.getOrCreate(
      activity,
      glide,
      activity.getLifecycle(),
      activity.getSupportFragmentManager(),
      isActivityVisible);
}

可以看到,最终调用了LifecycleRequestManagerRetriever#getOrCreate()

// LifecycleRequestManagerRetriever.java

RequestManager getOrCreate(
    Context context,
    Glide glide,
    final Lifecycle lifecycle,
    FragmentManager childFragmentManager,
    boolean isParentVisible) {
  Util.assertMainThread();
  // 1. 缓存中通过lifecycle获取requestmanager对象
  RequestManager result = getOnly(lifecycle);
  // 如果缓存中没有
  if (result == null) {
    // 2. 创建androidx的lifecycle监听
    LifecycleLifecycle glideLifecycle = new LifecycleLifecycle(lifecycle);
    // 3. 构建requestmanager
    result =
        factory.build(
            glide,
            glideLifecycle,
            new SupportRequestManagerTreeNode(childFragmentManager),
            context);
    // 4. 将requestmanager对象加入到缓存
    lifecycleToRequestManager.put(lifecycle, result);
    glideLifecycle.addListener(
        new LifecycleListener() {
          @Override
          public void onStart() {}

          @Override
          public void onStop() {}

          @Override
          public void onDestroy() {
            // 6. 页面销毁,移除缓存
            lifecycleToRequestManager.remove(lifecycle);
          }
        });
      
    if (isParentVisible) {
      // 5. 直接调用onstart方法
      result.onStart();
    }
  }
  return result;
}

这次在构建RequestManager传入了一个glideLifecycle,也就是LifecycleLifecycle,这个是将androidxLifecycleGlideLifecycle进行了巧妙的融合

final class LifecycleLifecycle implements Lifecycle, LifecycleObserver {
  @NonNull
  private final Set<LifecycleListener> lifecycleListeners = new HashSet<LifecycleListener>();

  @NonNull private final androidx.lifecycle.Lifecycle lifecycle;

  LifecycleLifecycle(androidx.lifecycle.Lifecycle lifecycle) {
    this.lifecycle = lifecycle;
    lifecycle.addObserver(this);
  }

  @OnLifecycleEvent(Event.ON_START)
  public void onStart(@NonNull LifecycleOwner owner) {
    for (LifecycleListener lifecycleListener : Util.getSnapshot(lifecycleListeners)) {
      lifecycleListener.onStart();
    }
  }

  @OnLifecycleEvent(Event.ON_STOP)
  public void onStop(@NonNull LifecycleOwner owner) {
    for (LifecycleListener lifecycleListener : Util.getSnapshot(lifecycleListeners)) {
      lifecycleListener.onStop();
    }
  }

  @OnLifecycleEvent(Event.ON_DESTROY)
  public void onDestroy(@NonNull LifecycleOwner owner) {
    for (LifecycleListener lifecycleListener : Util.getSnapshot(lifecycleListeners)) {
      lifecycleListener.onDestroy();
    }
    owner.getLifecycle().removeObserver(this);
  }

  @Override
  public void addListener(@NonNull LifecycleListener listener) {
    lifecycleListeners.add(listener);

    if (lifecycle.getCurrentState() == State.DESTROYED) {
      listener.onDestroy();
    } else if (lifecycle.getCurrentState().isAtLeast(State.STARTED)) {
      listener.onStart();
    } else {
      listener.onStop();
    }
  }

  @Override
  public void removeListener(@NonNull LifecycleListener listener) {
    lifecycleListeners.remove(listener);
  }
}

我们看到,它创建了一个androidxLifecycle,然后自己实现LifecycleObserver并传入到Lifecycle,以作为一个观察者来监听页面的生命周期变化。

与空白fragment不同的是,这里在addListener的时候判断页面状态,如果是可见状态,那么直接调用listener.onStart(),然后回调到RequestManageronStart()

兼容

众所周知,android中的Lifecycle只有androidx里面有,如果传入Activityandroid.app.fragment,是不能监听生命周期的,这时,还会走进以前的方法,只是被标记为了过时。

// 传入android.app.Fragment 
public static RequestManager with(@NonNull android.app.Fragment fragment) {
  return getRetriever(fragment.getActivity()).get(fragment);
}
public RequestManager get(@NonNull android.app.Fragment fragment) {
  if (fragment.getActivity() == null) {
    throw new IllegalArgumentException(
        "You cannot start a load on a fragment before it is attached");
  }
  if (Util.isOnBackgroundThread() || Build.VERSION.SDK_INT < Build.VERSION_CODES.JELLY_BEAN_MR1) {
    return get(fragment.getActivity().getApplicationContext());
  } else {
    if (fragment.getActivity() != null) {
      frameWaiter.registerSelf(fragment.getActivity());
    }
    android.app.FragmentManager fm = fragment.getChildFragmentManager();
    return fragmentGet(fragment.getActivity(), fm, fragment, fragment.isVisible());
  }
}

这里就一目了然了吧,又调用了fragmentGet方法创建一个空白的fragment,这样兼容也就完成了。

思考

看到这里,面试中常见的两个问题你已经搞懂了,不妨自己试着回答一下

Glide如何进行生命周期管理?

使用Glide为什么有时候会出现内存溢出 or 内存泄漏?

©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 201,681评论 5 474
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 84,710评论 2 377
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 148,623评论 0 334
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 54,202评论 1 272
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 63,232评论 5 363
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,368评论 1 281
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 37,795评论 3 393
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,461评论 0 256
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 40,647评论 1 295
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,476评论 2 317
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,525评论 1 329
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,226评论 3 318
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 38,785评论 3 303
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,857评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,090评论 1 258
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 42,647评论 2 348
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,215评论 2 341

推荐阅读更多精彩内容