ThinkChat🤖让你学习和工作更高效,注册即送10W Token,即刻开启你的AI之旅 广告
本节将以应用程序Activity 的MainActivity组件的启动过程为例,来说明Android应用程序的根Activity组件的启动过程,即Android应用程序的启动过程。由于**根Activity组件代表了一个Android应用程序,因此,它一般是在一个新的进程中启动起来的。** 在**Android系统中, 所有的Activity组件都保存在一个堆栈中**, 其中,后面启动的Activity组件位于前面启动的Activity组件的上面。用户在执行一个操作时,通常需要与一系列相关的Activity组件进行交互,这些相关的Activity组件在系统的Activity堆校中用一个任务(Task )来描述。 ### Activity和Acitivity调用栈 #### 任务栈 #### 参考链接 * [Android群英传读书笔记-第八章Activity与Activity调用栈分析](https://www.kancloud.cn/alex_wsc/heros/156875) * [Google官网文章任务和返回栈](https://developer.android.com/guide/components/tasks-and-back-stack.htm) * [对应译文翻译](https://www.kancloud.cn/alex_wsc/android/433658) - [关于Android中任务栈的总结](https://www.kancloud.cn/alex_wsc/android/433740) 以7.1 Activity组件的应用实例为例,由于ManActivity组件的android:process属性被设置为“ `shy.luo.activity.mainprocess`”,因此,Activity管理服务ActivityManagerService在启动MainActivity组件时,就会发现系统中并不存在一个名称为“`shy.luo.activity.mainprocess`”的应用程序进程,这时候它就会先创建这个应用程序进程,然后再在里面将MainActivity组件启动起来。MainActivity组件是由Launcher组件来启动的,而Launcher组件又是通过Activity 管理服务ActivityManagerService来启动MainActivity组件的。**由于MainActivity组件、Launcher组件和Activity ManagerService是分别运行在不同的进程中的,因此, MainActivity组件的启动过程就涉及到了三个进程**。这三个进程是**通过Binder进程间通信机制来完成MainActivity组件的启动过程的**。 >[info] **注意**: ActivityManagerService是一个系统关键服务, 它运行在系统进程System 中, 负责启动和调度应用程序组件 **Launcher组件启动MainActivity组件的过程如下所示**。 * ( 1 ) Launcher组件向ActivityManagerService发送一个启动MainActivity组件的进程间通信请求。 * ( 2) ActivityManagerService首先将要启动的MainActivity组件的信息保存下来,然后再向Launcher组件发送一个进入中止状态的进程间通信请求。 * ( 3 ) Launcher组件进入到中止状态之后,就会向ActivityManagerService发送一个已进入中止状态的进程间通信请求,以便ActivityManagerService可以继续执行启动MainActivity组件的操作。 * ( 4) ActivityManagerService发现用来运行MainActivity组件的应用程序进程不存在,因此,它就会先启动一个新的应用程序进程。 * ( 5)新的应用程序进程启动完成之后,就会向ActivityManagerService发送一个启动完成的进程间通信请求,以便ActivityManagerService可以继续执行启动MainActivity组件的操作。 * ( 6) ActivityManagerService将第2步保存下来的MainActivity组件的信息发送给第4步创建的应用程序进程,以便它可以将MainActivity组件启动起来。 这个过程一共分为35个步骤 **Step 1: Launcher.startActivitySafely()** ~~~ 1 void startActivitySafely(Intent intent, Object tag) { 2 intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 3 try { 4 startActivity(intent); 5 } catch (ActivityNotFoundException e) { 6 Toast.makeText(this, R.string.activity_not_found, Toast.LENGTH_SHORT).show(); 7 Log.e(TAG, "Unable to launch. tag=" + tag + " intent=" + intent, e); 8 } catch (SecurityException e) { 9 Toast.makeText(this, R.string.activity_not_found, Toast.LENGTH_SHORT).show(); 10 Log.e(TAG, "Launcher does not have the permission to launch " + intent + 11 ". Make sure to create a MAIN intent-filter for the corresponding activity " + 12 "or use the exported attribute for this activity. " 13 + "tag="+ tag + " intent=" + intent, e); 14 } 15 } ~~~