/*
 * Copyright (c) 2015-present, Facebook, Inc.
 *
 * This source code is licensed under the MIT license found in the
 * LICENSE file in the root directory of this source tree.
 */

package com.facebook.common.activitylistener;

import android.app.Activity;
import android.content.Context;
import android.content.ContextWrapper;
import com.facebook.common.internal.Preconditions;
import java.lang.ref.WeakReference;

/**
 * Registers ActivityListener with ActivityListener.
 *
 * <p> A WeakReference is used to wrap an ActivityVisibilityListener. When it is nullified
 * ActivityListener is automatically removed from the listened ListenableActivity.
 */
public class ActivityListenerManager {

  /**
   * If given context is an instance of ListenableActivity then creates new instance of
   * WeakReferenceActivityListenerAdapter and adds it to activity's listeners
   */
  public static void register(
      ActivityListener activityListener,
      Context context) {
    if (!(context instanceof ListenableActivity) && context instanceof ContextWrapper) {
      context = ((ContextWrapper) context).getBaseContext();
    }
    if (context instanceof ListenableActivity) {
      ListenableActivity listenableActivity = (ListenableActivity) context;
      Listener listener = new Listener(activityListener);
      listenableActivity.addActivityListener(listener);
    }
  }

  private static class Listener extends BaseActivityListener {
    private final WeakReference<ActivityListener> mActivityListenerRef;

    public Listener(ActivityListener activityListener) {
      mActivityListenerRef = new WeakReference<ActivityListener>(activityListener);
    }

    @Override
    public void onActivityCreate(Activity activity) {
      ActivityListener activityVisibilityListener = getListenerOrCleanUp(activity);
      if (activityVisibilityListener != null) {
        activityVisibilityListener.onActivityCreate(activity);
      }
    }

    @Override
    public void onDestroy(Activity activity) {
      ActivityListener activityVisibilityListener = getListenerOrCleanUp(activity);
      if (activityVisibilityListener != null) {
        activityVisibilityListener.onDestroy(activity);
      }
    }

    @Override
    public void onStart(Activity activity) {
      ActivityListener activityVisibilityListener = getListenerOrCleanUp(activity);
      if (activityVisibilityListener != null) {
        activityVisibilityListener.onStart(activity);
      }
    }

    @Override
    public void onStop(Activity activity) {
      ActivityListener activityVisibilityListener = getListenerOrCleanUp(activity);
      if (activityVisibilityListener != null) {
        activityVisibilityListener.onStop(activity);
      }
    }

    @Override
    public void onResume(Activity activity) {
      ActivityListener activityVisibilityListener = getListenerOrCleanUp(activity);
      if (activityVisibilityListener != null) {
        activityVisibilityListener.onResume(activity);
      }
    }

    @Override
    public void onPause(Activity activity) {
      ActivityListener activityVisibilityListener = getListenerOrCleanUp(activity);
      if (activityVisibilityListener != null) {
        activityVisibilityListener.onPause(activity);
      }
    }

    private ActivityListener getListenerOrCleanUp(Activity activity) {
      ActivityListener activityVisibilityListener = mActivityListenerRef.get();
      if (activityVisibilityListener == null) {
        Preconditions.checkArgument(activity instanceof ListenableActivity);
        ListenableActivity listenableActivity = (ListenableActivity) activity;
        listenableActivity.removeActivityListener(this);
      }
      return activityVisibilityListener;
    }
  }
}

@@ -409,16 +409,50 @@
 ference;
+%0Aimport javax.annotation.Nullable;
 %0A%0A/**%0A *
@@ -511,17 +511,16 @@
 *%0A * %3Cp%3E
- 
 A WeakRe
@@ -930,23 +930,16 @@
 egister(
-%0A      
 Activity
@@ -939,32 +939,202 @@
 ctivityListener 
+activityListener, Context context) %7B%0A    ListenableActivity activity = getListenableActivity(context);%0A    if (activity != null) %7B%0A      Listener listener = new Listener(
 activityListener
@@ -1137,16 +1137,135 @@
 ener
-,
+);
 %0A      
+activity.addActivityListener(listener);%0A    %7D%0A  %7D%0A%0A  public static @Nullable ListenableActivity getListenableActivity(
 Cont
@@ -1494,197 +1494,67 @@
     
-ListenableActivity listenableActivity = (ListenableActivity) context;%0A      Listener listener = new Listener(activityListener);%0A      listenableActivity.addActivityListener(listener);%0A    %7D
+return (ListenableActivity) context;%0A    %7D%0A    return null;
 %0A  %7D

Break apart register method to allow access to found ListenableActivity