From 62bea2f1710be0d1a42c07109fd4307ded660d3b Mon Sep 17 00:00:00 2001 From: Dianne Hackborn Date: Tue, 4 Sep 2012 18:48:15 -0700 Subject: Nested fragments. Change-Id: I79acc19b391352c16b06afee2ca543223c38e364 --- core/java/android/app/FragmentManager.java | 147 +++++++++++++---------------- 1 file changed, 68 insertions(+), 79 deletions(-) (limited to 'core/java/android/app/FragmentManager.java') diff --git a/core/java/android/app/FragmentManager.java b/core/java/android/app/FragmentManager.java index 52a6557..eaaf0d7 100644 --- a/core/java/android/app/FragmentManager.java +++ b/core/java/android/app/FragmentManager.java @@ -20,7 +20,6 @@ import android.animation.Animator; import android.animation.AnimatorInflater; import android.animation.AnimatorListenerAdapter; import android.content.res.Configuration; -import android.content.res.Resources; import android.content.res.TypedArray; import android.os.Bundle; import android.os.Handler; @@ -30,7 +29,6 @@ import android.os.Parcelable; import android.util.DebugUtils; import android.util.Log; import android.util.LogWriter; -import android.util.Slog; import android.util.SparseArray; import android.view.Menu; import android.view.MenuInflater; @@ -381,6 +379,13 @@ final class FragmentManagerState implements Parcelable { } /** + * Callbacks from FragmentManagerImpl to its container. + */ +interface FragmentContainer { + public View findViewById(int id); +} + +/** * Container for fragments associated with an activity. */ final class FragmentManagerImpl extends FragmentManager { @@ -410,6 +415,8 @@ final class FragmentManagerImpl extends FragmentManager { int mCurState = Fragment.INITIALIZING; Activity mActivity; + FragmentContainer mContainer; + Fragment mParent; boolean mNeedMenuInvalidate; boolean mStateSaved; @@ -585,7 +592,11 @@ final class FragmentManagerImpl extends FragmentManager { sb.append("FragmentManager{"); sb.append(Integer.toHexString(System.identityHashCode(this))); sb.append(" in "); - DebugUtils.buildShortClassTag(mActivity, sb); + if (mParent != null) { + DebugUtils.buildShortClassTag(mParent, sb); + } else { + DebugUtils.buildShortClassTag(mActivity, sb); + } sb.append("}}"); return sb.toString(); } @@ -681,6 +692,11 @@ final class FragmentManagerImpl extends FragmentManager { } writer.print(prefix); writer.println("FragmentManager misc state:"); + writer.print(prefix); writer.print(" mActivity="); writer.println(mActivity); + writer.print(prefix); writer.print(" mContainer="); writer.println(mContainer); + if (mParent != null) { + writer.print(prefix); writer.print(" mParent="); writer.println(mParent); + } writer.print(prefix); writer.print(" mCurState="); writer.print(mCurState); writer.print(" mStateSaved="); writer.print(mStateSaved); writer.print(" mDestroyed="); writer.println(mDestroyed); @@ -809,7 +825,9 @@ final class FragmentManagerImpl extends FragmentManager { } } f.mActivity = mActivity; - f.mFragmentManager = mActivity.mFragments; + f.mParentFragment = mParent; + f.mFragmentManager = mParent != null + ? mParent.mChildFragmentManager : mActivity.mFragments; f.mCalled = false; f.onAttach(mActivity); if (!f.mCalled) { @@ -817,14 +835,9 @@ final class FragmentManagerImpl extends FragmentManager { + " did not call through to super.onAttach()"); } mActivity.onAttachFragment(f); - + if (!f.mRetaining) { - f.mCalled = false; - f.onCreate(f.mSavedFragmentState); - if (!f.mCalled) { - throw new SuperNotCalledException("Fragment " + f - + " did not call through to super.onCreate()"); - } + f.performCreate(f.mSavedFragmentState); } f.mRetaining = false; if (f.mFromLayout) { @@ -845,7 +858,7 @@ final class FragmentManagerImpl extends FragmentManager { if (!f.mFromLayout) { ViewGroup container = null; if (f.mContainerId != 0) { - container = (ViewGroup)mActivity.findViewById(f.mContainerId); + container = (ViewGroup)mContainer.findViewById(f.mContainerId); if (container == null && !f.mRestored) { throwException(new IllegalArgumentException( "No view found for id 0x" @@ -873,14 +886,9 @@ final class FragmentManagerImpl extends FragmentManager { } } - f.mCalled = false; - f.onActivityCreated(f.mSavedFragmentState); - if (!f.mCalled) { - throw new SuperNotCalledException("Fragment " + f - + " did not call through to super.onActivityCreated()"); - } + f.performActivityCreated(f.mSavedFragmentState); if (f.mView != null) { - f.restoreViewState(); + f.restoreViewState(f.mSavedFragmentState); } f.mSavedFragmentState = null; } @@ -888,23 +896,13 @@ final class FragmentManagerImpl extends FragmentManager { case Fragment.STOPPED: if (newState > Fragment.STOPPED) { if (DEBUG) Log.v(TAG, "moveto STARTED: " + f); - f.mCalled = false; f.performStart(); - if (!f.mCalled) { - throw new SuperNotCalledException("Fragment " + f - + " did not call through to super.onStart()"); - } } case Fragment.STARTED: if (newState > Fragment.STARTED) { if (DEBUG) Log.v(TAG, "moveto RESUMED: " + f); - f.mCalled = false; f.mResumed = true; - f.onResume(); - if (!f.mCalled) { - throw new SuperNotCalledException("Fragment " + f - + " did not call through to super.onResume()"); - } + f.performResume(); // Get rid of this in case we saved it and never needed it. f.mSavedFragmentState = null; f.mSavedViewState = null; @@ -915,23 +913,13 @@ final class FragmentManagerImpl extends FragmentManager { case Fragment.RESUMED: if (newState < Fragment.RESUMED) { if (DEBUG) Log.v(TAG, "movefrom RESUMED: " + f); - f.mCalled = false; - f.onPause(); - if (!f.mCalled) { - throw new SuperNotCalledException("Fragment " + f - + " did not call through to super.onPause()"); - } + f.performPause(); f.mResumed = false; } case Fragment.STARTED: if (newState < Fragment.STARTED) { if (DEBUG) Log.v(TAG, "movefrom STARTED: " + f); - f.mCalled = false; f.performStop(); - if (!f.mCalled) { - throw new SuperNotCalledException("Fragment " + f - + " did not call through to super.onStop()"); - } } case Fragment.STOPPED: case Fragment.ACTIVITY_CREATED: @@ -944,12 +932,7 @@ final class FragmentManagerImpl extends FragmentManager { saveFragmentViewState(f); } } - f.mCalled = false; f.performDestroyView(); - if (!f.mCalled) { - throw new SuperNotCalledException("Fragment " + f - + " did not call through to super.onDestroyView()"); - } if (f.mView != null && f.mContainer != null) { Animator anim = null; if (mCurState > Fragment.INITIALIZING && !mDestroyed) { @@ -1008,12 +991,7 @@ final class FragmentManagerImpl extends FragmentManager { } else { if (DEBUG) Log.v(TAG, "movefrom CREATED: " + f); if (!f.mRetaining) { - f.mCalled = false; - f.onDestroy(); - if (!f.mCalled) { - throw new SuperNotCalledException("Fragment " + f - + " did not call through to super.onDestroy()"); - } + f.performDestroy(); } f.mCalled = false; @@ -1027,6 +1005,7 @@ final class FragmentManagerImpl extends FragmentManager { makeInactive(f); } else { f.mActivity = null; + f.mParentFragment = null; f.mFragmentManager = null; } } @@ -1050,11 +1029,11 @@ final class FragmentManagerImpl extends FragmentManager { if (mActivity == null && newState != Fragment.INITIALIZING) { throw new IllegalStateException("No activity"); } - + if (!always && mCurState == newState) { return; } - + mCurState = newState; if (mActive != null) { boolean loadersRunning = false; @@ -1099,11 +1078,11 @@ final class FragmentManagerImpl extends FragmentManager { if (mActive == null) { mActive = new ArrayList(); } - f.setIndex(mActive.size()); + f.setIndex(mActive.size(), mParent); mActive.add(f); } else { - f.setIndex(mAvailIndices.remove(mAvailIndices.size()-1)); + f.setIndex(mAvailIndices.remove(mAvailIndices.size()-1), mParent); mActive.set(f.mIndex, f); } if (DEBUG) Log.v(TAG, "Allocated fragment index " + f); @@ -1120,7 +1099,7 @@ final class FragmentManagerImpl extends FragmentManager { mAvailIndices = new ArrayList(); } mAvailIndices.add(f.mIndex); - mActivity.invalidateFragmentIndex(f.mIndex); + mActivity.invalidateFragment(f.mWho); f.initState(); } @@ -1296,7 +1275,7 @@ final class FragmentManagerImpl extends FragmentManager { if (mActive != null && who != null) { for (int i=mActive.size()-1; i>=0; i--) { Fragment f = mActive.get(i); - if (f != null && who.equals(f.mWho)) { + if (f != null && (f=f.findFragmentByWho(who)) != null) { return f; } } @@ -1566,7 +1545,7 @@ final class FragmentManagerImpl extends FragmentManager { if (mStateBundle == null) { mStateBundle = new Bundle(); } - f.onSaveInstanceState(mStateBundle); + f.performSaveInstanceState(mStateBundle); if (!mStateBundle.isEmpty()) { result = mStateBundle; mStateBundle = null; @@ -1735,7 +1714,7 @@ final class FragmentManagerImpl extends FragmentManager { for (int i=0; i(); + if (f != null) { + if (f.performCreateOptionsMenu(menu, inflater)) { + show = true; + if (newMenus == null) { + newMenus = new ArrayList(); + } + newMenus.add(f); } - newMenus.add(f); } } } @@ -1916,9 +1904,10 @@ final class FragmentManagerImpl extends FragmentManager { if (mAdded != null) { for (int i=0; i