福建网站建建设方案便宜点的网站建设
- 作者: 五速梦信息网
- 时间: 2026年03月21日 11:16
当前位置: 首页 > news >正文
福建网站建建设方案,便宜点的网站建设,建设网站及后期维护费用是多少,网站建设服务器主板1150针FyListen——生命周期监听器#xff08;设计原理之理解生命周期#xff09; FyListen 的核心原理有两个#xff1a; 通过子Fragment对Activity、Fragment进行生命周期监听Java8 接口特性 default
- 什么是上下文Context 这是一个装饰器模式#xff0c; ContextImpl 是 …FyListen——生命周期监听器设计原理之理解生命周期 FyListen 的核心原理有两个 通过子Fragment对Activity、Fragment进行生命周期监听Java8 接口特性 default
- 什么是上下文Context 这是一个装饰器模式 ContextImpl 是 Context 的基础实现类 ContextWrapper 是对 ContextImpl 的包装类。ContextThemeWrapper 是对装饰器的再装饰又增加了一些功能。
1.1 如何获取 Context
获取 Context 的方法有很多getContext(), getBaseContext(), getApplication(), getApplicationContext()。我们来看一下他们的区别
getApplication()和 getApplicationContext() 获取到的就是同一个对象只是使用的范围不一样
getApplication() 只有 Activity 和 Service 才有。想要在其他地方获取 Application 只能通过 getApplicationContext().
getContext(), getBaseContext()和 getApplicationContext() 有什么区别 ActivityService 和 Application 都有 getBaseContext()getApplicationContext() 这两个方法但没有 getContext() 方法。 getContext() 方法只有在 Fragment 中才有获取的是寄主对象也就是 Activity。 所以 Fragment 必须依赖于 Activity 存在
1.2 Application 有什么用 Application 是全局单例可以通过 getApplication() 和 getApplicationContext() 获取。 需要注意的是如果在 application 中调用 context 的方法必须在 attachBaseContext() 之后在此之前 context 是没有赋值的。 - Activity 与 Fragment 生命周期绑定原理 先来看一张Fragment状态转移图图来自稀土掘金 这张图的解读可以看到下面这张表Activity 管理 Fragment 生命周期的方式是在 Activity 的生命周期方法中调用 FragmentManager 的对应方法通过 FragmentManager 将现有的 Fragment 迁移到下一个状态同时触发相应的生命周期函数 Activity生命周期函数FragmentManager触发的方法Fragmet你状态转移Fragment生命周期回调onCreate()dispatchCreateINITIALIZING-CREATEDonAttach()、onCreate()dispatchActivityCreated()CREATED-ACTIVITY_CREATEDonCreateView()、onActivityCreated()、onStart()dispatchStartACTIVITY_CREATED-STARTEDonStart()onResume()dispatchResumeSTARTED-RESUMEDonResume()onPausedispatchPauseRESUMED-STARTEDonPause()onStopdispatchStopSTARTED-STOPPEDonStop()onDestroydispatchDestroySTOPPED-ACTIVITY_CREATED-CREATED-CREATED-INITIALIZINGonDestroyView()、onDestroy()、onDetach() 我们从源码角度来看一下是如何绑定的生命周期首先我们需要知道Activity 生命周期是由 AMSActivityManagerService管理、回调的这部分请大家在 AMS 专题学习。便于理解我们提前看到源码中关于Fragment的状态转移代码处理 需要提醒的Java基础是switch: 一旦switch表达式与某个case分支匹配则从该分支的语句开始执行一致执行下去其后所有case分支的语句也会被执行直到遇到break语句 //[FragmentManager.java] void moveToState(Fragment f, int newState, int transit, int transitionStyle,boolean keepActive) {//newState是Fragment将要被转移到的状态state//f.mState是Fragment现有的状态stateif(f.mState newState){switch(f.mState){case Fragment.INITIALIZING://Fragment当前状态还在INITIALIZINGActivity调用了onCreate()newState是CREATEDFragment进行状态转移if(newState Fragment.INITIALIZING){f.onAttach();dispatchOnFragmentAttached();if(!f.mIsCreated){//如果fragment还没create()f.performCreate();dispatchOnFragmentCreated();}else{//如果fragment过去已经create()过了只不过是detach()了并没有销毁。也就是这个Fragment虽然生命结束了但后来又被加载使用了复用了f.mState Fragment.CREATED;}}case Fragment.CREATED:if(newState Fragment.CREATED){//Fragment当前状态在CREATED但Activity紧接着又将状态调整为ACTIVITY_CREATED,Fragment进行状态转移f.mView f.performCreateView();if(f.mView!null){//如果没有view就不往它的子Fragment进行生命周期回调分发了dispatchOnFragmentViewCreated();}f.performActivityCreated();dispatchOnFragmentActivityCreated();}case Fragment.ACTIVITY_CREATED:if(newState Fragment.ACTIVITY_CREATED){//只进行状态转移f.mState Fragment.STOPPED;}case Fragment.STOPPED:if(newState Fragment.STOPPED){f.performStart();dispatchOnFragmentStarted();}case Fragment.STARTED:if(newState Fragment.STARTED){f.performResume();dispatchOnFragmentResumed();}}}else if(f.mState newState){//反向转移switch(f.mState){case Fragment.RESUMED:if(newState Fragment.RESUMED){f.performPause();dispatchOnFragmentPaused();}case Fragment.STARTED:if(newState Fragment.STARTED){f.performStop();dispatchOnFragmentStopped();}case Fragment.STOPPED:case Fragment.ACTIVITY_CREATED:if(newState Fragment.ACTIVITY_CREATED){f.performDestroyView();dispatchOnFragmentViewDestroyed();}case Fragment.CREATED:if(newState Fragment.CREATED){f.performDestroy();dispatchOnFragmentDestroy();}f.performDetach();dispatchOnFragmentDetached();}if(f.mState ! newState){f.mState newState;}} }我们了解了 Fragment 的生命周期是由于 Activity 生命周期的回调设定了 Fragment 应当到的 newState然后让 Fragment 进行状态转移转移的过程中回调 Fragment 的生命周期。所以我们主要需要看 Activity 是如何设置 newState 的。从 AMS 回调 Activity 的 performXXX() 看起 2.1 AMS-Activity.performCreate() 在 Activity 的 onCreate() 中将 Fragment 的状态转移目标 newState 设置为了 CREATED状态转移期间回调了Fragment的 onAttach() 和 onCreate()performCreate()又将 Fragment 的状态转移目标newState设置为了 ACTIVITY_CREATEDFragment在状态转移期间回调了Fragment的 onCreateView() 和 onActivityCreate() //[Activity.java] final void performCreate(Bundle icicle, PersistableBundle persistentState) {//调用Activity的onCreate()方法其中回调了Fragment的onAttach()和onCreate()方法if (persistentState ! null) {onCreate(icicle, persistentState);} else {onCreate(icicle);}//调用到moveToState,且newState为Fragment.ACTIVITY_CREATED,状态转移过程中回调了Fragment的onCreateView()和onActivityCreate().mFragments.dispatchActivityCreated(); }protected void onCreate(Nullable Bundle savedInstanceState) {//调用到moveToState,且newState为Fragment.CREATED在状态转移期间回调了Fragment的onAttach()和onCreate()方法mFragments.dispatchCreate();//Application的Lifecycle回调dispatchActivityCreated(savedInstanceState); }2.2 AMS-performStart() 调用了 Activity 的 onStart()将Fragment的状态转移目标newState设置为了STARTEDFragment在期间回调了Fragment的 onStart() 方法 //[Activity.java] final void performStart(String reason){//回调了 activity.onStart(),其中进行Application的Lifecycle回调mInstrumentation.callActivityOnStart(this);//调用到moveToState且newState为Fragment.STARTED,其中回调了onStart()方法。虽然在switch中将Fragment的状态停留在了STOPPED但在moveToState()方法的最后又将Fragment的状态设置到了STARTED。mFragments.dispatchStart() }2.3 AMS-performResume() 调用了 Activity 的 onResume()将Fragment的状态转移目标newState设置为了RESUMEDFragment在状态转移期间回调了Fragment的 onResume(); //[Activity.java] final void performResume(boolean followedByPause, String reason){//如果activity之前不是started的会进入此方法确保将activity变为startperformRestart(true,reason);//如果activity之前是start的//回调activity.onResume()里面回调了 Application的LifecyclemInstrumentation.callActivityOnResume(this);//调用到moveToState且newState为Fragment.RESUMED状态转移期间回调了Fragment的onResume()方法mFragments.dispatchResume(); }2.4 AMS-performPause() 【注意】我们发现从这里开始是先从Fragment开始状态转换而且是往回转移newStatef.mState然后才调用Activity的生命周期回调 注意状态转移设为newStateSTARTED开始往回转移Fragment状态转移期间回调了onPause()方法然后才调用Activity的onPause()方法 //[Activity.java] final void performPause(boolean preserveWindow, String reason) {//在此之前状态为RESUMED由于f.mStatenewState,将进行往回状态转移//Fragment状态转移到STARTED期间回调了Fragment的onPause()mFragments.dispatchPause();//调用Activity的onPause(),同时回调Application的LifecycleonPause(); }2.5 AMS-performStop() 【注意】先从Fragment开始状态转换而且是往回转移newStatef.mState然后才调用Activity的生命周期回调 注意状态转移目标设为newState STOPPED往回状态转移Fragment状态转移期间回调了 onStop()方法然后才调用Activity的onStop()方法 //[Activity.java] final void performStop(boolean preserveWindow, String reason) {//Fragment状态转移到STOPPED往回状态转移期间回调了Fragment的onStop()方法mFragments.dispatchStop();//其中回调了Activity的onStop()同时回调Application中的监听LifecyclemInstrumentation.callActivityOnStop(this); }2.6 AMS-performRestart() Activity可能会在onStop()之后又onRestart()需要注意的是这里并没有回调Fragment的生命周期只调用了activity的onRestart()并调用performStart()后续的生命周期回调就和onStart()之后的一致了 //[Activity.java] final void performRestart(boolean start, String reason) {//先判断之前是否为Stop状态if(mStopped){mStopped false;//调用Activity的onRestart()回调mInstrumentation.callActivityOnRestart(this);//里面调用了Activity的onStart()并进行Fragment状态转移与生命周期回调performStart();} }final void performStart(String reason) {//调用Activity.onStart()并回调Application的Lifecycle通知Application这个activity的生命周期现状mInstrumentation.callActivityOnStart(this);//newStateSTARTEDFragment状态从STOPPED到STARTED状态转移期间回调了Fragment的onStart()mFragments.dispatchStart(); }2.7 AMS-performDestroy() 【注意】先从Fragment开始状态转换而且是往回转移newStatef.mState然后才调用Activity的生命周期回调 先进行Fragment状态转移newStateINITIALIZING期间回调了Fragment的onDestroyView,onDestroy,onDetachFragment状态转移完成才进行Activity的onDestroy() //[Activity.java] final void performDestroy(){//先进行Fragment状态转移newStateINITIALIZING期间回调了Fragment的onDestroyView,onDestroy,onDetachmFragments.dispatchDestroy();//Fragment状态转移完成才进行Activity的onDestroy()onDestroy(); }我们回到 moveToState 来看一下是怎么连着回调三个Fragment生命周期的需要注意此时f.mState STOPPEDnewStateINITIALIZING: 需要提醒的Java基础是switch: 一旦switch表达式与某个case分支匹配则从该分支的语句开始执行一致执行下去其后所有case分支的语句也会被执行直到遇到break语句 //[FragmentManager.java] void moveToState(Fragment f, int newState, int transit, int transitionStyle,boolean keepActive) {if(f.mState 《 newState){//…}else if(f.mState newState){switch(f.mState){//…case Fragment.STOPPED://分支判断成功继续执行后续case分支语句直到遇到breakcase Fragment.ACTIVITY_CREATE:if(newState Fragment.ACTIVITY_CREATED){//1. 回调Fragment的onDestroyView()f.performDestroyView();//把该事件也分发给f的子FragmentdispatchOnFragmentViewDestroyed();}case Fragment.CREATED:if(newState Fragment.ACTIVITY_CREATED){//2. 回调Fragment的onDestroy()f.performDestroy();//把该事件也分发给f的子FragmentdispatchOnFragmentDestroyed();//3. 回调Fragment的onDetach()f.performDetach();//把该事件也分发给f的子FragmentdispatchOnFragmentDetached(); }//switch end}}//状态转移完成最终更新f.mState INITIALIZINGif(f.mState ! newState){f.mState newState;} }至此我们分析完了生命周期回调。如果你比较细心会发现这里除了处理fragment的生命周期还有的时候会处理fragment的动画和view的显示。
- 补充Fragment生命周期除了自动由 Activity 来回调也可以由用户操控 FragmentTansaction 进行 Fragment 的调度时候回调生命周期 先来看这张图图源稀土掘金 我们经常使用 FragmentTransaction 中的 add()、remove()、replace()、attach()、detach()、hide()、show() 等方法对 Fragment进行操作这些方法都会使 Fragment 的状态发生变化出发对应的生命周期函数。默认 Activity 处于 Resume 状态 add/remove 操作会引起 Fragment 在 INITIALIZING 和 RESUMED 这两个状态之间迁移attach/detach操作会引起 Fragment 在 CREATED 和 RESUMED 两个状态之间迁移 add() 需要注意的是如果Activity处于 STARTED 状态Fragment 是无法进入 RESUMED 状态的只有当 Activity 进入 RESUME 状态才会通知 Fragment 进入 RESUMED。 hide/show方法内部其实调用了 FragmentTransaction 的add/remove 方法。 3. Fragment 与 子Fragment 生命周期绑定原理 我们观察到 Fragment 中也持有一个 FragmentManagermChildFragmentManage 用于管理子Fragment。所以在生命周期事件分发过程中会呈树形结构向所有子Fragment进行分发 //[Fragment.java] public class Fragment implements ComponentCallbacks2, OnCreateContextMenuListener {//上层管理当前Fragment的FragmentManagerFragmentManagerImpl mFragmentManager;//当前Fragment用于管理子Fragment的fm在生命周期回调中会同时分发给 MChildFragmentManager 中的所有子FragmentFragmentManagerImpl mChildFragmentManager;//所属的父FragmentFragment mParentFragment; } FragmentManager 中管理着 FragmentsmAdds 和 mActive //[FragmentManager.java] final class FragmentManagerImpl extends FragmentManager implements LayoutInflater.Factory2 {//当前活跃的FragmentSparseArrayFragment mActive;//所有已添加的Fragmentfinal ArrayListFragment mAdded new ArrayList();//管理的其他信息ArrayListBackStackRecord mBackStack;ArrayListFragment mCreatedMenus;//…//分发生命周期以dispatchResume()为例public void dispatchResume(){mStateSaved false;//进行Fragment的状态转移dispatchMoveToState(Fragment.RESUMED);}//其中通过moveToState先进行预处理即找到所有当前FragmentManager所管理的Fragment进行逐个事件分发private void dispatchMoveToState(int state) {if (mAllowOldReentrantBehavior) {moveToState(state, false);} else {try {mExecutingActions true;moveToState(state, false);} finally {mExecutingActions false;}}execPendingActions();}//拿到 mAdds 和 mActive 中的Fragment去分发事件逐个让他们去进行状态转移//注意这个是两个参数的 moveToState()真正状态转移的moveToState()方法是四个参数的注意区分void moveToState(int newState,boolean always){if (mActive ! null) {final int numAdded mAdded.size();for (int i 0; i numAdded; i) {Fragment f mAdded.get(i);//逐个fragment进行状态转移moveFragmentToExpectedState(f);}final int numActive mActive.size();for (int i 0; i numActive; i) {Fragment f mActive.valueAt(i);if (f ! null (f.mRemoving || f.mDetached) !f.mIsNewlyAdded) {//逐个fragment进行状态转移moveFragmentToExpectedState(f);}}}}//moveFragmentToExceptedState()通过四个参数的moveToState()让fragment进行状态转移void moveFragmentToExceptedState(final Fragment f){int nextState mCurState;//新状态被标记在成员变量不作为参数传入简化代码//进行状态转移具体的我们之前已经看过了moveToState(f, nextState, f.getNextTransition(), f.getNextTransitionStyle(), false);}}4. Activity与Fragment的树形结构 既然我们已经知道了 Fragment 的生命周期可以由 Activity 或者 Fragment 进行回调那么我们就可以通过这个特性进行 Activity 或者 父Fragment生命周期的监听主流框架 Glide 中生命周期监听的方式也是利用了这个特性。我画了两张图大家先感性地认知一下 Fragment 监听 Activity 生命周期的构造 Activity与Fragment的树形结构 我们可以看到这是一个可以找到父节点的多叉树。 fragment想要与Activity通信可以通过Fragment中的 FragmentHostCallback类型对象mHost里面存了Fragment所依存的Activity实例、主线程Handler。Fragment中启动Activity也是通过这个对象让上层去执行启动Activity的请求。 5. 使用 Java8 接口特性 default 进行外观设计 java8 之前往接口里新加一个方法那么所有的实现类都需要变动都需要同步实现这个方法。 java8 给接口新增了两个关键字default static 使得可以往接口里添加默认方法子类可以无需变动。 同时这也使得接口中的方法并不需要全都实现只需要重写需要的方法即可
- 上一篇: 福建省住房和建设网站网站模板站扩容
- 下一篇: 福建网站建设推广wordpress连接mysql8
相关文章
-
福建省住房和建设网站网站模板站扩容
福建省住房和建设网站网站模板站扩容
- 技术栈
- 2026年03月21日
-
福建省住房城乡和建设厅网站网站下载app免费
福建省住房城乡和建设厅网站网站下载app免费
- 技术栈
- 2026年03月21日
-
福建省漳州市建设厅网站高校思政主题网站建设的意义
福建省漳州市建设厅网站高校思政主题网站建设的意义
- 技术栈
- 2026年03月21日
-
福建网站建设推广wordpress连接mysql8
福建网站建设推广wordpress连接mysql8
- 技术栈
- 2026年03月21日
-
福建网站建设推广前端做网站维护
福建网站建设推广前端做网站维护
- 技术栈
- 2026年03月21日
-
福建网站开发速成班南京seo公司
福建网站开发速成班南京seo公司
- 技术栈
- 2026年03月21日






