瀏覽代碼

[공통][Bug] MVP Lifecycle 수정
- M/P 는 V (Fragment) 의 생명 주기와 동기화된다.

hyodong.min 7 年之前
父節點
當前提交
7c29c74684

+ 16 - 4
app/src/main/java/kr/co/zumo/app/lifeplus/model/ModelProvider.java

@@ -39,13 +39,25 @@ public class ModelProvider {
    * @return new MainModel()
    */
   public <T extends Model> T getModel(FragmentActivity activity, Class<T> modelClass) {
-    /**
-     * 항상 같은 key 등록하면 다른 model.class 요청했을 때 이전 model 을 clear 시켜준다.
-     */
-    String key = this.getClass().getCanonicalName();
+    String key = modelClass.getCanonicalName();
     Log.e("APP#  ModelProvider | getModel", "|" + key);
 
     return ViewModelProviders.of(activity).get(key, modelClass);
   }
 
+  /**
+   * 모델을 clear 한다.
+   * - 직접 clear 하는 방법은 없다.
+   * - 동일한 key 로 빈 모델(BlankModel)을 get() 하면 이전 모델은 onCleared() 가 호출된다.
+   *
+   * @param activity   FragmentActivity
+   * @param modelClass MainModel.class
+   */
+  public void clearModel(FragmentActivity activity, Class modelClass) {
+    String key = modelClass.getCanonicalName();
+    Log.e("APP#  ModelProvider | clearModel", "|" + key);
+
+    ViewModelProviders.of(activity).get(key, BlankModel.class);
+  }
+
 }

+ 30 - 19
app/src/main/java/kr/co/zumo/app/lifeplus/view/fragment/FragmentBase.java

@@ -5,6 +5,7 @@ package kr.co.zumo.app.lifeplus.view.fragment;
 
 import android.content.Context;
 import android.os.Bundle;
+import android.support.annotation.CallSuper;
 import android.support.annotation.NonNull;
 import android.support.annotation.Nullable;
 import android.support.v4.app.Fragment;
@@ -44,11 +45,17 @@ public abstract class FragmentBase<P extends Presenter> extends Fragment impleme
   public void onAttach(Context context) {
     Log.e("APP# FragmentBase | onAttach", "| >>>>>>>>>>>> " + this.getClass().getSimpleName());
     super.onAttach(context);
+
+    /**
+     * Presenter/Model 은 onCreateView() 에서 생성하여 popStack() 때에도 사용되도록 한다.
+     * - onDestroy() 까지 남아있다.
+     */
+    presenter = definePresenter();
   }
 
   @Override
   public void onCreate(@Nullable Bundle savedInstanceState) {
-    Log.e("APP# FragmentBase | onCreate", "| >>>>>>>>>>>> " + this.getClass().getSimpleName());
+//    Log.e("APP# FragmentBase | onCreate", "| >>>>>>>>>>>> " + this.getClass().getSimpleName());
     super.onCreate(savedInstanceState);
   }
 
@@ -57,11 +64,6 @@ public abstract class FragmentBase<P extends Presenter> extends Fragment impleme
   public final View onCreateView(@NonNull LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {
     Log.e("APP# FragmentBase | onCreateView", "| >>>>>>>>>>>> " + this.getClass().getSimpleName());
 
-    /**
-     * Presenter/Model 은 onCreateView() 에서 생성하여 popStack() 때에도 사용되도록 한다.
-     */
-    presenter = definePresenter();
-
     defineActionBar();
     defineActionButton();
 
@@ -70,37 +72,46 @@ public abstract class FragmentBase<P extends Presenter> extends Fragment impleme
 
   @Override
   public final void onViewCreated(@NonNull View view, @Nullable Bundle savedInstanceState) {
-    Log.e("APP# FragmentBase | onViewCreated", "| >>>>>>>>>>>> " + this.getClass().getSimpleName());
+//    Log.e("APP# FragmentBase | onViewCreated", "| >>>>>>>>>>>> " + this.getClass().getSimpleName());
     super.onViewCreated(view, savedInstanceState);
-
-    onAfterActivityCreated(savedInstanceState);
   }
 
+  /**
+   * onActivityCreated() 는 restart 에 실행되지 않는다.
+   * - 레이아웃의 view 들을 변수에 assign 해준다.
+   *
+   * @param savedInstanceState
+   */
   @Override
   public final void onActivityCreated(@Nullable Bundle savedInstanceState) {
     Log.e("APP# FragmentBase | onActivityCreated", "| >>>>>>>>>>>> " + this.getClass().getSimpleName());
     super.onActivityCreated(savedInstanceState);
 
+    onAfterActivityCreated(savedInstanceState);
   }
 
+  @CallSuper
   @Override
   public void onStart() {
     presenter.start();
     super.onStart();
   }
 
+  @CallSuper
   @Override
   public void onResume() {
     presenter.resume();
     super.onResume();
   }
 
+  @CallSuper
   @Override
   public void onPause() {
     presenter.pause();
     super.onPause();
   }
 
+  @CallSuper
   @Override
   public void onStop() {
     presenter.stop();
@@ -108,22 +119,13 @@ public abstract class FragmentBase<P extends Presenter> extends Fragment impleme
   }
 
   @Override
-  public void onDestroyView() {
+  public final void onDestroyView() {
     Log.w("APP# FragmentBase | onDestroyView", "| <<<<<<<<<<<<< " + this.getClass().getSimpleName());
     if (null != disposable) {
       disposable.dispose();
       disposable = null;
     }
 
-    /**
-     * fragment 전환 시 onDestroyView() 까지만 실행된다.
-     */
-
-    if (null != presenter) {
-      presenter.destroy();
-      presenter = null;
-    }
-
     super.onDestroyView();
 
     onAfterDestroyView();
@@ -134,6 +136,15 @@ public abstract class FragmentBase<P extends Presenter> extends Fragment impleme
     Log.w("APP# FragmentBase | onDestroy", "| <<<<<<<<<<<<< " + this.getClass().getSimpleName());
     super.onDestroy();
 
+    /**
+     * Presenter 및 Model 을 destroy 한다.
+     * Fragment 가 destroy 되면 재사용은 불가능해진다.
+     */
+    if (null != presenter) {
+      presenter.destroy();
+      presenter = null;
+    }
+
     onAfterDestroy();
   }
 

+ 1 - 2
app/src/main/java/kr/co/zumo/app/lifeplus/view/fragment/main/MainFragment.java

@@ -174,8 +174,7 @@ public class MainFragment extends FragmentBase<MainPresenter> implements IMainVi
   }
 
   @Override
-  public void onDestroyView() {
-    super.onDestroyView();
+  protected void onAfterDestroyView() {
 
     if (null != adapter) {
       adapter.dispose();

+ 1 - 2
app/src/main/java/kr/co/zumo/app/lifeplus/view/fragment/pin/PinConfirmFragment.java

@@ -99,8 +99,7 @@ public class PinConfirmFragment extends FragmentBase<PinConfirmPresenter> implem
   }
 
   @Override
-  public void onDestroyView() {
-    super.onDestroyView();
+  protected void onAfterDestroyView() {
 
     if (null != pinPresenter) {
       pinPresenter.dispose();

+ 1 - 2
app/src/main/java/kr/co/zumo/app/lifeplus/view/fragment/signup/SignUpMobileAuthFragment.java

@@ -80,8 +80,7 @@ public class SignUpMobileAuthFragment extends FragmentBase<SignUpMobileAuthPrese
   }
 
   @Override
-  public void onDestroyView() {
-    super.onDestroyView();
+  protected void onAfterDestroyView() {
 
     if (null != authView) {
       authView.dispose();

+ 10 - 1
app/src/main/java/kr/co/zumo/app/lifeplus/view/presenter/Presenter.java

@@ -3,6 +3,7 @@
  */
 package kr.co.zumo.app.lifeplus.view.presenter;
 
+import android.support.v4.app.FragmentActivity;
 import android.support.v7.app.ActionBar;
 import android.util.Log;
 
@@ -11,6 +12,7 @@ import com.google.gson.Gson;
 import kr.co.zumo.app.lifeplus.ILifeCycle;
 import kr.co.zumo.app.lifeplus.model.IModelResult;
 import kr.co.zumo.app.lifeplus.model.Model;
+import kr.co.zumo.app.lifeplus.model.ModelProvider;
 import kr.co.zumo.app.lifeplus.network.INetworkReceiverListener;
 import kr.co.zumo.app.lifeplus.supervisor.ScreenID;
 import kr.co.zumo.app.lifeplus.view.Event;
@@ -73,7 +75,14 @@ public abstract class Presenter<M extends Model, V extends IView> implements ILi
    */
   @Override
   public final void destroy() {
-    Log.i("APP# Presenter | destroyInternal", "|" + "<<------------------------- " + this.getClass().getSimpleName());
+    Log.i("APP# Presenter | destroy", "|" + "<<------------------------- " + this.getClass().getSimpleName());
+
+    /**
+     * 모델을 클리어해준다.
+     *
+     * todo 여러 모델들의 데이터를 취합 할 수 있는 방법 필요 (ex> DataHelper) SignUpModel 등
+     */
+    ModelProvider.getInstance().clearModel((FragmentActivity) view.getActivity(), model.getClass());
 
     destroyInternal();
   }