前面讲了那么多xml,我们缓一下,现在讲从代码角度来看fragment的创建。
我们通常会在FragmentActivity中通过如下方法:
getSupportFragmentManager().beginTransaction().replace(R.id.content, fragment, tag).commit(); getSupportFragmentManager().beginTransaction().add(R.id.content, fragment, tag).commit();
来调用新建或者取代一个fragment。那你知道这中间发生了什么事情吗,别急,让我们慢慢看代码。
FragmentActivity.java中有个方法:getSupportFragmentManager
public FragmentManager getSupportFragmentManager() { return mFragments; }
这个方法用于获取一个FragmentManager,那么这个mFragments是哪里来的呢,我们搜一下这个类,不难发现他的初始化是这个样子的:
final FragmentManagerImpl mFragments = new FragmentManagerImpl();
从中我们就可以知道FragmentManager以及FragmentManagerImpl是父子类关系。
final class FragmentManagerImpl extends FragmentManager
而且不用说也可以看出来,FragmentManagerImpl是FragmentManager的具体实现,然后自然而然的我们能找到代码:
public FragmentTransaction beginTransaction() { return new BackStackRecord(this); }
自然而然的我们要去找到BackStackRecord.java这个类了,代码如下:
public BackStackRecord(FragmentManagerImpl manager) { mManager = manager; }
接下来,我们看如何添加一个Fragment到Activity,无非是addFragment方法了,我们到FragmentTransaction中看一下(前面说过的Impl类是具体实现):
public void addFragment(Fragment paramFragment, boolean paramBoolean) { if (this.mAdded == null) this.mAdded = new ArrayList(); if (DEBUG) Log.v("FragmentManager", "add: " + paramFragment); makeActive(paramFragment); if (!paramFragment.mDetached) { this.mAdded.add(paramFragment); paramFragment.mAdded = true; paramFragment.mRemoving = false; if ((paramFragment.mHasMenu) && (paramFragment.mMenuVisible)) this.mNeedMenuInvalidate = true; if (paramBoolean) moveToState(paramFragment); } }
这里果然是有一个数组ArrayList在管理,ArrayList是啥?是动态数组,这就意味着他是可以动态添加的,不是栈,所以里面的Fragments可以随便获取以及插入。
其中最重要的那句话就是moveToState,其实现代码还是比较多的,我们贴一下看看:
void moveToState(Fragment paramFragment, int paramInt1, int paramInt2, int paramInt3) { if ((!paramFragment.mAdded) && (paramInt1 > 1)) paramInt1 = 1; if ((paramFragment.mRemoving) && (paramInt1 > paramFragment.mState)) paramInt1 = paramFragment.mState; if (paramFragment.mState < paramInt1) { if ((paramFragment.mFromLayout) && (!paramFragment.mInLayout)) return; if (paramFragment.mAnimatingAway != null) { paramFragment.mAnimatingAway = null; moveToState(paramFragment, paramFragment.mStateAfterAnimating, 0, 0); } switch (paramFragment.mState) { default: case 0: case 1: case 2: case 3: case 4: } } while (true) { paramFragment.mState = paramInt1; break; if (DEBUG) Log.v("FragmentManager", "moveto CREATED: " + paramFragment); if (paramFragment.mSavedFragmentState != null) { paramFragment.mSavedViewState = paramFragment.mSavedFragmentState.getSparseParcelableArray("android:view_state"); paramFragment.mTarget = getFragment(paramFragment.mSavedFragmentState, "android:target_state"); if (paramFragment.mTarget != null) paramFragment.mTargetRequestCode = paramFragment.mSavedFragmentState.getInt("android:target_req_state", 0); } paramFragment.mActivity = this.mActivity; paramFragment.mFragmentManager = this.mActivity.mFragments; paramFragment.mCalled = false; paramFragment.onAttach(this.mActivity); if (!paramFragment.mCalled) throw new SuperNotCalledException("Fragment " + paramFragment + " did not call through to super.onAttach()"); //第一步:attach this.mActivity.onAttachFragment(paramFragment); if (!paramFragment.mRetaining) { paramFragment.mCalled = false; //第二步:onCreate paramFragment.onCreate(paramFragment.mSavedFragmentState); if (!paramFragment.mCalled) throw new SuperNotCalledException("Fragment " + paramFragment + " did not call through to super.onCreate()"); } paramFragment.mRetaining = false; if (paramFragment.mFromLayout) { //第三步:onCreateView paramFragment.mView = paramFragment.onCreateView(paramFragment.getLayoutInflater(paramFragment.mSavedFragmentState), null, paramFragment.mSavedFragmentState); if (paramFragment.mView == null) break label570; paramFragment.mInnerView = paramFragment.mView; paramFragment.mView = NoSaveStateFrameLayout.wrap(paramFragment.mView); if (paramFragment.mHidden) paramFragment.mView.setVisibility(8); paramFragment.onViewCreated(paramFragment.mView, paramFragment.mSavedFragmentState); } while (true) { if (paramInt1 <= 1) break label777; if (DEBUG) Log.v("FragmentManager", "moveto ACTIVITY_CREATED: " + paramFragment); if (paramFragment.mFromLayout) break; ViewGroup localViewGroup = null; if (paramFragment.mContainerId != 0) { localViewGroup = (ViewGroup)this.mActivity.findViewById(paramFragment.mContainerId); if ((localViewGroup == null) && (!paramFragment.mRestored)) { throw new IllegalArgumentException("No view found for id 0x" + Integer.toHexString(paramFragment.mContainerId) + " for fragment " + paramFragment); label570: paramFragment.mInnerView = null; continue; } } paramFragment.mContainer = localViewGroup; paramFragment.mView = paramFragment.onCreateView(paramFragment.getLayoutInflater(paramFragment.mSavedFragmentState), localViewGroup, paramFragment.mSavedFragmentState); if (paramFragment.mView == null) break label753; paramFragment.mInnerView = paramFragment.mView; paramFragment.mView = NoSaveStateFrameLayout.wrap(paramFragment.mView); if (localViewGroup != null) { Animation localAnimation2 = loadAnimation(paramFragment, paramInt2, true, paramInt3); if (localAnimation2 != null) paramFragment.mView.startAnimation(localAnimation2); localViewGroup.addView(paramFragment.mView); } if (paramFragment.mHidden) paramFragment.mView.setVisibility(8); paramFragment.onViewCreated(paramFragment.mView, paramFragment.mSavedFragmentState); } while (true) { paramFragment.mCalled = false; //第四步:onActivityCreated paramFragment.onActivityCreated(paramFragment.mSavedFragmentState); if (paramFragment.mCalled) break; throw new SuperNotCalledException("Fragment " + paramFragment + " did not call through to super.onActivityCreated()"); label753: paramFragment.mInnerView = null; } if (paramFragment.mView != null) paramFragment.restoreViewState(); paramFragment.mSavedFragmentState = null; label777: if (paramInt1 > 3) { if (DEBUG) Log.v("FragmentManager", "moveto STARTED: " + paramFragment); paramFragment.mCalled = false; paramFragment.performStart(); if (!paramFragment.mCalled) throw new SuperNotCalledException("Fragment " + paramFragment + " did not call through to super.onStart()"); } if (paramInt1 <= 4) continue; if (DEBUG) Log.v("FragmentManager", "moveto RESUMED: " + paramFragment); paramFragment.mCalled = false; paramFragment.mResumed = true; //第五步:onResume paramFragment.onResume(); if (!paramFragment.mCalled) throw new SuperNotCalledException("Fragment " + paramFragment + " did not call through to super.onResume()"); paramFragment.mSavedFragmentState = null; paramFragment.mSavedViewState = null; continue; if (paramFragment.mState <= paramInt1) continue; switch (paramFragment.mState) { default: break; case 1: case 5: case 4: case 3: case 2: while (paramInt1 < 1) { if ((this.mDestroyed) && (paramFragment.mAnimatingAway != null)) { View localView = paramFragment.mAnimatingAway; paramFragment.mAnimatingAway = null; localView.clearAnimation(); } if (paramFragment.mAnimatingAway == null) break label1519; paramFragment.mStateAfterAnimating = paramInt1; paramInt1 = 1; break; if (paramInt1 < 5) { if (DEBUG) Log.v("FragmentManager", "movefrom RESUMED: " + paramFragment); paramFragment.mCalled = false; //第六步:onPause paramFragment.onPause(); if (!paramFragment.mCalled) throw new SuperNotCalledException("Fragment " + paramFragment + " did not call through to super.onPause()"); paramFragment.mResumed = false; } if (paramInt1 < 4) { if (DEBUG) Log.v("FragmentManager", "movefrom STARTED: " + paramFragment); paramFragment.mCalled = false; paramFragment.performStop(); if (!paramFragment.mCalled) throw new SuperNotCalledException("Fragment " + paramFragment + " did not call through to super.onStop()"); } if (paramInt1 < 3) { if (DEBUG) Log.v("FragmentManager", "movefrom STOPPED: " + paramFragment); paramFragment.performReallyStop(); } if (paramInt1 >= 2) continue; if (DEBUG) Log.v("FragmentManager", "movefrom ACTIVITY_CREATED: " + paramFragment); if ((paramFragment.mView != null) && (!this.mActivity.isFinishing()) && (paramFragment.mSavedViewState == null)) saveFragmentViewState(paramFragment); paramFragment.mCalled = false; paramFragment.performDestroyView(); if (!paramFragment.mCalled) throw new SuperNotCalledException("Fragment " + paramFragment + " did not call through to super.onDestroyView()"); if ((paramFragment.mView != null) && (paramFragment.mContainer != null)) { Animation localAnimation1 = null; if ((this.mCurState > 0) && (!this.mDestroyed)) localAnimation1 = loadAnimation(paramFragment, paramInt2, false, paramInt3); if (localAnimation1 != null) { paramFragment.mAnimatingAway = paramFragment.mView; paramFragment.mStateAfterAnimating = paramInt1; localAnimation1.setAnimationListener(new Animation.AnimationListener(paramFragment) { public void onAnimationEnd(Animation paramAnimation) { if (this.val$fragment.mAnimatingAway != null) { this.val$fragment.mAnimatingAway = null; FragmentManagerImpl.this.moveToState(this.val$fragment, this.val$fragment.mStateAfterAnimating, 0, 0); } } public void onAnimationRepeat(Animation paramAnimation) { } public void onAnimationStart(Animation paramAnimation) { } }); paramFragment.mView.startAnimation(localAnimation1); } paramFragment.mContainer.removeView(paramFragment.mView); } paramFragment.mContainer = null; paramFragment.mView = null; paramFragment.mInnerView = null; } label1519: if (DEBUG) Log.v("FragmentManager", "movefrom CREATED: " + paramFragment); if (!paramFragment.mRetaining) { paramFragment.mCalled = false; //第八步:onDestroy paramFragment.onDestroy(); if (!paramFragment.mCalled) throw new SuperNotCalledException("Fragment " + paramFragment + " did not call through to super.onDestroy()"); } paramFragment.mCalled = false; //第九步:onDetach paramFragment.onDetach(); if (!paramFragment.mCalled) throw new SuperNotCalledException("Fragment " + paramFragment + " did not call through to super.onDetach()"); if (!paramFragment.mRetaining) { makeInactive(paramFragment); continue; } paramFragment.mActivity = null; paramFragment.mFragmentManager = null; } } }
本来不想贴这部分的代码的,但确实这个比较重要,还是看一下吧。
最后一步肯定是commit了,这个方法是由FragmentTransaction.java类调用的,其实包括前面的addFragment等都是在这个类调用的,可是他是个抽象类,具体的实现还是在Impl类中。我们还是稍微浏览一下这个类吧(只截取了部分):
public abstract class FragmentTransaction { public abstract FragmentTransaction add(int containerViewId, Fragment fragment); public abstract FragmentTransaction add(int containerViewId, Fragment fragment, String tag); public abstract FragmentTransaction replace(int containerViewId, Fragment fragment); public abstract FragmentTransaction replace(int containerViewId, Fragment fragment, String tag); public abstract FragmentTransaction remove(Fragment fragment); public abstract FragmentTransaction hide(Fragment fragment); public abstract FragmentTransaction show(Fragment fragment); public abstract FragmentTransaction detach(Fragment fragment); public abstract FragmentTransaction attach(Fragment fragment); public abstract int commit(); }
最后看commit的实现,本人目前还没找到,求告诉!
详解fragment(一):从源代码看fragment的生命周期