ActivityThread是什么
ActivityThread在Android中它就代表了Android的主线程,但是并不是一个Thread类。
严格来说,UI主线程不是ActivityThread。ActivityThread类是Android APP进程的初始类,它的main函数是这个APP进程的入口。APP进程中UI事件的执行代码段都是由ActivityThread提供的。也就是说,Main Thread实例是存在的,只是创建它的代码我们不可见。ActivityThread的main函数就是在这个Main Thread里被执行的。
Java程序初始类中的main()方法,将作为该程序初始线程的起点,任何其他的线程都是由这个初始线程启动的。这个线程就是程序的主线程。
源码如下:
public final class ActivityThread {
//...
private static ActivityThread sCurrentActivityThread;
public static ActivityThread currentActivityThread() {
return sCurrentActivityThread;
}
private void attach(boolean system) {
sCurrentActivityThread = this;
//...
}
public static void main(String[] args) {
//....
//创建Looper和MessageQueue对象,用于处理主线程的消息
Looper.prepareMainLooper();
//创建ActivityThread对象
ActivityThread thread = new ActivityThread();
//建立Binder通道 (创建新线程)
thread.attach(false);
Looper.loop(); //消息循环运行
throw new RuntimeException("Main thread loop unexpectedly exited");
}
}
ApplicationThread是什么,有什么用?
ApplicationThread是ActivityThread的内部类,也是一个Binder对象。在此处它是作为Activitythread和AMS通信的桥梁.
private class ApplicationThread extends IApplicationThread.Stub {
public final void schedulePauseActivity(IBinder token, boolean finished,
boolean userLeaving, int configChanges, boolean dontReport) {
......
}
public final void scheduleStopActivity(IBinder token, boolean showWindow,
int configChanges) {
......
}
public final void scheduleLaunchActivity(Intent intent, IBinder token, int ident,
ActivityInfo info, Configuration curConfig, CompatibilityInfo compatInfo,
String referrer, IVoiceInteractor voiceInteractor, int procState, Bundle state,
PersistableBundle persistentState, List<ResultInfo> pendingResults,
List<ReferrerIntent> pendingNewIntents, boolean notResumed, boolean isForward,
ProfilerInfo profilerInfo) {
......
}
......
}
上述方法是用来启动activity的,除此外还有几种重要的方法,由此看来ApplicationThread的作用除了启动activity 和ams交互之外还用调用activity的生命周期方法,也就是我们看到的 几个activity生命周期方法。那么我们再看一下这些生命周期方法的调用过程。
schedulePauseActivity()
scheduleStopActivity()
scheduleResumeActivity()
scheduleSendResult()
scheduleLaunchActivity()
scheduleNewIntent()
scheduleDestroyActivity()
scheduleReceiver()
scheduleCreateService()
scheduleBindService()
scheduleUnbindService()
scheduleServiceArgs()
scheduleStopService()
bindApplication()
scheduleConfigurationChanged()
scheduleRegisteredReceiver()
scheduleInstallProvider()
ApplicationThread中的所有schedule方法内部都会调用一个sendMessage()而其实际要调用到activtyThread中的H的实例对象mH中,mH中定义了很多消息类型,下图是其handlerMessage方法,这也印章了我上边的所说的ApplicationThread的桥梁作用,ams直接通过binder调用,实际调用到activityThread中的方法 。
private void sendMessage(int what, Object obj, int arg1, int arg2, int seq) {
if (DEBUG_MESSAGES) Slog.v(
TAG, "SCHEDULE " + mH.codeToString(what) + " arg1=" + arg1 + " arg2=" + arg2 +
"seq= " + seq);
Message msg = Message.obtain();
msg.what = what;
SomeArgs args = SomeArgs.obtain();
args.arg1 = obj;
args.argi1 = arg1;
args.argi2 = arg2;
args.argi3 = seq;
msg.obj = args;
mH.sendMessage(msg);
}
private class H extends Handler {
……
public void handleMessage(Message msg) {
if (DEBUG_MESSAGES) Slog.v(TAG, ">>> handling: " + codeToString(msg.what));
switch (msg.what) {
case LAUNCH_ACTIVITY: {
Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "activityStart");
final ActivityClientRecord r = (ActivityClientRecord) msg.obj;
r.packageInfo = getPackageInfoNoCheck(
r.activityInfo.applicationInfo, r.compatInfo);
handleLaunchActivity(r, null, "LAUNCH_ACTIVITY");
Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);
} break;
case RELAUNCH_ACTIVITY: {
Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "activityRestart");
ActivityClientRecord r = (ActivityClientRecord)msg.obj;
handleRelaunchActivity(r);
Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);
} break;
case PAUSE_ACTIVITY: {
Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "activityPause");
SomeArgs args = (SomeArgs) msg.obj;
handlePauseActivity((IBinder) args.arg1, false,
(args.argi1 & USER_LEAVING) != 0, args.argi2,
(args.argi1 & DONT_REPORT) != 0, args.argi3);
Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);
} break;
case PAUSE_ACTIVITY_FINISHING: {
Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "activityPause");
SomeArgs args = (SomeArgs) msg.obj;
handlePauseActivity((IBinder) args.arg1, true, (args.argi1 & USER_LEAVING) != 0,
args.argi2, (args.argi1 & DONT_REPORT) != 0, args.argi3);
Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);
} break;
case STOP_ACTIVITY_SHOW: {
Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "activityStop");
SomeArgs args = (SomeArgs) msg.obj;
handleStopActivity((IBinder) args.arg1, true, args.argi2, args.argi3);
Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);
} break;
case STOP_ACTIVITY_HIDE: {
Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "activityStop");
SomeArgs args = (SomeArgs) msg.obj;
handleStopActivity((IBinder) args.arg1, false, args.argi2, args.argi3);
Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);
} break;
case SHOW_WINDOW:
Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "activityShowWindow");
handleWindowVisibility((IBinder)msg.obj, true);
Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);
break;
case HIDE_WINDOW:
Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "activityHideWindow");
handleWindowVisibility((IBinder)msg.obj, false);
Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);
break;
case RESUME_ACTIVITY:
Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "activityResume");
SomeArgs args = (SomeArgs) msg.obj;
handleResumeActivity((IBinder) args.arg1, true, args.argi1 != 0, true,
args.argi3, "RESUME_ACTIVITY");
Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);
break;
case SEND_RESULT:
Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "activityDeliverResult");
handleSendResult((ResultData)msg.obj);
Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);
break;
case DESTROY_ACTIVITY:
Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "activityDestroy");
handleDestroyActivity((IBinder)msg.obj, msg.arg1 != 0,
msg.arg2, false);
Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);
break;
case BIND_APPLICATION:
Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "bindApplication");
AppBindData data = (AppBindData)msg.obj;
handleBindApplication(data);
Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);
break;
case EXIT_APPLICATION:
if (mInitialApplication != null) {
mInitialApplication.onTerminate();
}
Looper.myLooper().quit();
break;
case NEW_INTENT:
Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "activityNewIntent");
handleNewIntent((NewIntentData)msg.obj);
Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);
break;
case RECEIVER:
Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "broadcastReceiveComp");
handleReceiver((ReceiverData)msg.obj);
Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);
break;
case CREATE_SERVICE:
Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, ("serviceCreate: " + String.valueOf(msg.obj)));
handleCreateService((CreateServiceData)msg.obj);
Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);
break;
case BIND_SERVICE:
Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "serviceBind");
handleBindService((BindServiceData)msg.obj);
Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);
break;
case UNBIND_SERVICE:
Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "serviceUnbind");
handleUnbindService((BindServiceData)msg.obj);
Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);
break;
case SERVICE_ARGS:
Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, ("serviceStart: " + String.valueOf(msg.obj)));
handleServiceArgs((ServiceArgsData)msg.obj);
Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);
break;
case STOP_SERVICE:
Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "serviceStop");
handleStopService((IBinder)msg.obj);
Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);
break;
}
Object obj = msg.obj;
if (obj instanceof SomeArgs) {
((SomeArgs) obj).recycle();
}
if (DEBUG_MESSAGES) Slog.v(TAG, "<<< done: " + codeToString(msg.what));
}
}
private void handleDestroyActivity(IBinder token, boolean finishing,
int configChanges, boolean getNonConfigInstance) {
ActivityClientRecord r = performDestroyActivity(token, finishing,
configChanges, getNonConfigInstance);
if (r != null) {
cleanUpPendingRemoveWindows(r, finishing);
WindowManager wm = r.activity.getWindowManager();
View v = r.activity.mDecor;
if (v != null) {
if (r.activity.mVisibleFromServer) {
mNumVisibleActivities--;
}
IBinder wtoken = v.getWindowToken();
if (r.activity.mWindowAdded) {
if (r.mPreserveWindow) {
// Hold off on removing this until the new activity's
// window is being added.
r.mPendingRemoveWindow = r.window;
r.mPendingRemoveWindowManager = wm;
// We can only keep the part of the view hierarchy that we control,
// everything else must be removed, because it might not be able to
// behave properly when activity is relaunching.
r.window.clearContentView();
} else {
wm.removeViewImmediate(v);
}
}
if (wtoken != null && r.mPendingRemoveWindow == null) {
WindowManagerGlobal.getInstance().closeAll(wtoken,
r.activity.getClass().getName(), "Activity");
} else if (r.mPendingRemoveWindow != null) {
// We're preserving only one window, others should be closed so app views
// will be detached before the final tear down. It should be done now because
// some components (e.g. WebView) rely on detach callbacks to perform receiver
// unregister and other cleanup.
WindowManagerGlobal.getInstance().closeAllExceptView(token, v,
r.activity.getClass().getName(), "Activity");
}
r.activity.mDecor = null;
}
if (r.mPendingRemoveWindow == null) {
// If we are delaying the removal of the activity window, then
// we can't clean up all windows here. Note that we can't do
// so later either, which means any windows that aren't closed
// by the app will leak. Well we try to warning them a lot
// about leaking windows, because that is a bug, so if they are
// using this recreate facility then they get to live with leaks.
WindowManagerGlobal.getInstance().closeAll(token,
r.activity.getClass().getName(), "Activity");
}
// Mocked out contexts won't be participating in the normal
// process lifecycle, but if we're running with a proper
// ApplicationContext we need to have it tear down things
// cleanly.
Context c = r.activity.getBaseContext();
if (c instanceof ContextImpl) {
((ContextImpl) c).scheduleFinalCleanup(
r.activity.getClass().getName(), "Activity");
}
}
if (finishing) {
try {
ActivityManager.getService().activityDestroyed(token);
} catch (RemoteException ex) {
throw ex.rethrowFromSystemServer();
}
}
mSomeActivitiesChanged = true;
}
ActivityClientRecord 上述代码太多我删掉了好多不熟悉的,我们看到了STOP_SERVICE,DESTROY_ACTIVITY,所以继续用我们比较熟悉的DESTROY_ACTIVITY为例进行分析。于是又抛出一个新的概念ActivityClientRecord(感觉我是写不完了。。。)因为上述代码已经拿到了activity window等我们熟知的对象,所以里边的方法就不继续深入讨论,下次有时间继续撸ActivityClientRecord 在activity启动中是如何发挥作用的。
static final class ActivityClientRecord {
IBinder token;
int ident;
Intent intent;
String referrer;
IVoiceInteractor voiceInteractor;
Bundle state;
PersistableBundle persistentState;
Activity activity;
Window window;
Activity parent;
String embeddedID;
Activity.NonConfigurationInstances lastNonConfigurationInstances;
……
ActivityClientRecord nextIdle;
ProfilerInfo profilerInfo;
ActivityInfo activityInfo;
CompatibilityInfo compatInfo;
LoadedApk packageInfo;
Window mPendingRemoveWindow;
WindowManager mPendingRemoveWindowManager;
boolean mPreserveWindow;
// Set for relaunch requests, indicates the order number of the relaunch operation, so it
// can be compared with other lifecycle operations.
int relaunchSeq = 0;
// Can only be accessed from the UI thread. This represents the latest processed message
// that is related to lifecycle events/
int lastProcessedSeq = 0;
ActivityClientRecord() {
parent = null;
embeddedID = null;
paused = false;
stopped = false;
hideForNow = false;
nextIdle = null;
configCallback = (Configuration overrideConfig, int newDisplayId) -> {
if (activity == null) {
throw new IllegalStateException(
"Received config update for non-existing activity");
}
activity.mMainThread.handleActivityConfigurationChanged(
new ActivityConfigChangeData(token, overrideConfig), newDisplayId);
};
}
……
}
网友评论