From 224760abf61c0bbc9850b75b5bf3fa21f48a2d8f Mon Sep 17 00:00:00 2001 From: seven332 Date: Tue, 12 May 2015 13:33:21 +0800 Subject: [PATCH] Create new scene after Activity recreate --- .../ehviewer/ui/scene/GalleryListScene.java | 21 ++++++--- .../hippo/ehviewer/widget/ContentLayout.java | 21 ++++++--- .../main/java/com/hippo/scene/Curtain.java | 8 ++-- app/src/main/java/com/hippo/scene/Scene.java | 25 ++++++++-- .../java/com/hippo/scene/SceneManager.java | 47 +++++++++++++------ .../java/com/hippo/scene/SimpleDialog.java | 26 ++++++---- 6 files changed, 104 insertions(+), 44 deletions(-) diff --git a/app/src/main/java/com/hippo/ehviewer/ui/scene/GalleryListScene.java b/app/src/main/java/com/hippo/ehviewer/ui/scene/GalleryListScene.java index 44d7d2ae5..d73758e1e 100644 --- a/app/src/main/java/com/hippo/ehviewer/ui/scene/GalleryListScene.java +++ b/app/src/main/java/com/hippo/ehviewer/ui/scene/GalleryListScene.java @@ -179,9 +179,18 @@ public class GalleryListScene extends Scene implements SearchBar.Helper, } }; + @Override + protected void onReplace(@NonNull Scene oldScene) { + super.onReplace(oldScene); + + GalleryListScene oldGalleryListScene = (GalleryListScene) oldScene; + mGalleryListHelper = oldGalleryListScene.mGalleryListHelper + .newInstance(getStageActivity()); + } + @SuppressWarnings("deprecation") @Override - public void onCreate(@Nullable Bundle savedInstanceState) { + protected void onCreate(@Nullable Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.scene_gallery_list); @@ -223,9 +232,7 @@ public class GalleryListScene extends Scene implements SearchBar.Helper, mSearchLayout.setHelper(this); // Content Layout - if (mGalleryListHelper != null) { - mGalleryListHelper = mGalleryListHelper.newInstance(mActivity); - } else { + if (mGalleryListHelper == null) { mGalleryListHelper = new GalleryListHelper(mActivity); } @@ -633,13 +640,13 @@ public class GalleryListScene extends Scene implements SearchBar.Helper, init(); } - private GalleryListHelper(Context context, List data) { - super(context, data); + private GalleryListHelper(Context context, GalleryListHelper oldContentHelper) { + super(context, oldContentHelper); init(); } public GalleryListHelper newInstance(Context context) { - return new GalleryListHelper(context, getData()); + return new GalleryListHelper(context, this); } private void init() { diff --git a/app/src/main/java/com/hippo/ehviewer/widget/ContentLayout.java b/app/src/main/java/com/hippo/ehviewer/widget/ContentLayout.java index 643d75033..222cb759d 100644 --- a/app/src/main/java/com/hippo/ehviewer/widget/ContentLayout.java +++ b/app/src/main/java/com/hippo/ehviewer/widget/ContentLayout.java @@ -185,7 +185,6 @@ public class ContentLayout extends FrameLayout { private int mCurrentPage; private int mPageVolume; - // TODO save mCurrentTaskId mCurrentTaskType mCurrentTaskPage private int mCurrentTaskId; private int mCurrentTaskType; private int mCurrentTaskPage; @@ -228,9 +227,21 @@ public class ContentLayout extends FrameLayout { mIdGenerator = IntIdGenerator.create(); } - protected ContentHelper(Context context, List data) { + @SuppressWarnings("unchecked") + protected ContentHelper(Context context, ContentHelper oldContentHelper) { this(context); - mData.addAll(data); + mData.addAll(oldContentHelper.mData); + + mFirstPage = oldContentHelper.mFirstPage; + mLastPage = oldContentHelper.mLastPage; + mFirstIndex = oldContentHelper.mFirstIndex; + mLastIndex = oldContentHelper.mLastIndex; + mPageSize = oldContentHelper.mPageSize; + mCurrentPage = oldContentHelper.mCurrentPage; + mPageVolume = oldContentHelper.mPageVolume; + mCurrentTaskId = oldContentHelper.mCurrentTaskId; + mCurrentTaskType = oldContentHelper.mCurrentTaskType; + mCurrentTaskPage = oldContentHelper.mCurrentTaskPage; } private void init(ContentLayout contentLayout) { @@ -256,10 +267,6 @@ public class ContentLayout extends FrameLayout { mSnackbar.setAction(mContext.getString(R.string.retry), this); } - protected List getData() { - return mData; - } - protected abstract RecyclerView.LayoutManager generateLayoutManager(); protected abstract void onScrollToPosition(); diff --git a/app/src/main/java/com/hippo/scene/Curtain.java b/app/src/main/java/com/hippo/scene/Curtain.java index 8aa617c10..eb6fcd4fc 100644 --- a/app/src/main/java/com/hippo/scene/Curtain.java +++ b/app/src/main/java/com/hippo/scene/Curtain.java @@ -23,18 +23,18 @@ import com.hippo.util.ViewUtils; public abstract class Curtain { - private int mPreviousSceneCode; + private int mPreviousSceneId; void setPreviousScene(@Nullable Scene pScene) { if (pScene == null) { - mPreviousSceneCode = -1; + mPreviousSceneId = -1; } else { - mPreviousSceneCode = pScene.hashCode(); + mPreviousSceneId = pScene.getId(); } } boolean isPreviousScene(@Nullable Scene scene) { - return scene != null && scene.hashCode() == mPreviousSceneCode; + return scene != null && scene.getId() == mPreviousSceneId; } /** diff --git a/app/src/main/java/com/hippo/scene/Scene.java b/app/src/main/java/com/hippo/scene/Scene.java index 369cd4e6d..5fdfdda6d 100644 --- a/app/src/main/java/com/hippo/scene/Scene.java +++ b/app/src/main/java/com/hippo/scene/Scene.java @@ -60,10 +60,20 @@ public abstract class Scene { protected static SceneManager sSceneManager; + private int mId; + static void setSceneManager(SceneManager sceneManager) { sSceneManager = sceneManager; } + public Scene() { + mId = sSceneManager.nextId(); + } + + int getId() { + return mId; + } + void setCurtain(@Nullable Curtain curtain) { mCurtain = curtain; } @@ -168,6 +178,10 @@ public abstract class Scene { onResume(); } + void replace(@NonNull Scene oldScene) { + onReplace(oldScene); + } + void setFitPaddingBottom(int b) { onGetFitPaddingBottom(b); } @@ -205,8 +219,7 @@ public abstract class Scene { StageActivity sa = getStageActivity(); mSceneView = createSceneView(sa); initBackground(mSceneView); - mSceneView.addView(view, new FrameLayout.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, - ViewGroup.LayoutParams.MATCH_PARENT)); + mSceneView.addView(view, new FrameLayout.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.MATCH_PARENT)); } private void initBackground(@NonNull View bg) { @@ -238,6 +251,12 @@ public abstract class Scene { protected void onResume() { } + protected void onReplace(@NonNull Scene oldScene) { + mId = oldScene.mId; + mAnnouncer = oldScene.mAnnouncer; + mCurtain = oldScene.mCurtain; + } + /** * It will be called if nav bar is transparent. * @param b the nav bar's height @@ -346,7 +365,7 @@ public abstract class Scene { // It is constant private String getStateKey() { - return "scene:" + Integer.toHexString(hashCode()); + return "scene:" + mId; } private String getIsGoneKey() { diff --git a/app/src/main/java/com/hippo/scene/SceneManager.java b/app/src/main/java/com/hippo/scene/SceneManager.java index 19e79328d..3692b1701 100644 --- a/app/src/main/java/com/hippo/scene/SceneManager.java +++ b/app/src/main/java/com/hippo/scene/SceneManager.java @@ -19,6 +19,7 @@ import android.os.Bundle; import android.support.annotation.NonNull; import android.support.annotation.Nullable; +import com.hippo.util.IntIdGenerator; import com.hippo.util.Log; import java.util.Stack; @@ -32,10 +33,16 @@ class SceneManager { private Scene mLegacyScene; + private IntIdGenerator mIdGenerator = IntIdGenerator.create(); + // Should only be called by SceneApplication SceneManager() { } + int nextId() { + return mIdGenerator.nextId(); + } + void setStageActivity(StageActivity stageActivity) { mStageActivity = stageActivity; } @@ -48,17 +55,9 @@ class SceneManager { return mStageActivity != null; } - // TODO check previousState state - void startScene(@NonNull Class sceneClass, @Nullable Announcer announcer, - @Nullable Curtain curtain) { - if (!isStageAlive()) { - Log.w(TAG, "Stage is not alive, but attemp to create " + sceneClass.getSimpleName()); - return; - } - - Scene scene; + Scene createSceneByClass(@NonNull Class sceneClass) { try { - scene = (Scene) sceneClass.newInstance(); + return (Scene) sceneClass.newInstance(); } catch (InstantiationException e) { throw new IllegalStateException("Can't instance " + sceneClass.getName()); } catch (IllegalAccessException e) { @@ -67,6 +66,17 @@ class SceneManager { } catch (ClassCastException e) { throw new IllegalStateException(sceneClass.getName() + " can not cast to scene"); } + } + + // TODO check previousState state + void startScene(@NonNull Class sceneClass, @Nullable Announcer announcer, + @Nullable Curtain curtain) { + if (!isStageAlive()) { + Log.w(TAG, "Stage is not alive, but attemp to create " + sceneClass.getSimpleName()); + return; + } + + Scene scene = createSceneByClass(sceneClass); scene.setAnnouncer(announcer); scene.setCurtain(curtain); @@ -219,10 +229,19 @@ class SceneManager { } protected void onRestoreInstanceState(@NonNull Bundle savedInstanceState) { - for (Scene scene : mSceneStack) { - // Recreate - scene.create(savedInstanceState); - scene.restoreInstanceState(savedInstanceState); + Stack tempStack = new Stack<>(); + tempStack.addAll(mSceneStack); + mSceneStack.clear(); + + for (Scene oldScene : tempStack) { + Scene newScene = createSceneByClass(oldScene.getClass()); + newScene.replace(oldScene); + oldScene.destroy(); + oldScene.setState(Scene.SCENE_STATE_DESTROY); + newScene.create(savedInstanceState); + newScene.setState(Scene.SCENE_STATE_RUN); + newScene.restoreInstanceState(savedInstanceState); + mSceneStack.push(newScene); } } } diff --git a/app/src/main/java/com/hippo/scene/SimpleDialog.java b/app/src/main/java/com/hippo/scene/SimpleDialog.java index 7c5bd26cc..646962f86 100644 --- a/app/src/main/java/com/hippo/scene/SimpleDialog.java +++ b/app/src/main/java/com/hippo/scene/SimpleDialog.java @@ -42,8 +42,6 @@ public class SimpleDialog extends SceneDialog implements View.OnClickListener, private Builder mBuilder; - private StageActivity mActivity; - private SceneDialogView mSceneDialogView; private SimpleDialogFrame mFrame; private View mBody; @@ -59,7 +57,7 @@ public class SimpleDialog extends SceneDialog implements View.OnClickListener, private int mFitPaddingBottom; - private SimpleDialog(@NonNull Builder builder) { + private void setBuilder(@NonNull Builder builder) { mBuilder = builder; } @@ -70,12 +68,10 @@ public class SimpleDialog extends SceneDialog implements View.OnClickListener, // TODO setBackgroundColor(BACKGROUND_COLOR); - mActivity = getStageActivity(); - setContentView(R.layout.simple_dialog_frame); mFrame = (SimpleDialogFrame) findViewById(R.id.simple_dialog_frame); - mActivity.getLayoutInflater().inflate(R.layout.simple_dialog, mFrame); + getStageActivity().getLayoutInflater().inflate(R.layout.simple_dialog, mFrame); mSceneDialogView = (SceneDialogView) getSceneView(); mBody = findViewById(R.id.body); @@ -92,6 +88,16 @@ public class SimpleDialog extends SceneDialog implements View.OnClickListener, bindDialog(); } + @Override + protected void onReplace(@NonNull Scene oldScene) { + super.onReplace(oldScene); + + SimpleDialog oldDialog = (SimpleDialog) oldScene; + mBuilder = oldDialog.mBuilder; + // Avoid memory leak + mBuilder.mContext = getStageActivity(); + } + private void bindDialog() { if (mBuilder.mTitle == null && mBuilder.mMessage == null && mBuilder.mCustomViewResId == 0) { ViewUtils.setVisibility(mBody, View.GONE); @@ -305,8 +311,10 @@ public class SimpleDialog extends SceneDialog implements View.OnClickListener, return this; } - public @NonNull SceneDialog build() { - return new SimpleDialog(this); + public @NonNull SimpleDialog build() { + SimpleDialog dialog = new SimpleDialog(); + dialog.setBuilder(this); + return dialog; } public void show() { @@ -317,7 +325,7 @@ public class SimpleDialog extends SceneDialog implements View.OnClickListener, if (curtain == null) { curtain = new SimpleDialogCurtain(mStartX, mStartY); } - new SimpleDialog(this).show(curtain); + build().show(curtain); } }