前言
在Android开发中,我们经常会使用BroadcastReceiver来接收系统或者其他应用发送的广播消息。然而,BroadcastReceiver的注册过程并不是那么容易理解。本文将深入剖析Android源码中BroadcastReceiver的注册过程,帮助读者更好地理解这一关键的组件。
BroadcastReceiver的注册
BroadcastReceiver的注册分为两种方式,一种是在AndroidManifest.xml文件中静态注册,另一种是在代码中动态注册。
静态注册
静态注册是将BroadcastReceiver的声明放在应用的AndroidManifest.xml文件中,示例如下:
<receiver android:name=".MyReceiver">
<intent-filter>
<action android:name="android.intent.action.BOOT_COMPLETED" />
<category android:name="android.intent.category.DEFAULT" />
</intent-filter>
</receiver>
上述代码将一个名为"MyReceiver"的BroadcastReceiver注册到系统的android.intent.action.BOOT_COMPLETED
广播中。当系统发送该广播时,MyReceiver将被调用。
动态注册
动态注册是通过代码的方式,在应用运行时动态地注册BroadcastReceiver。示例代码如下:
MyReceiver receiver = new MyReceiver();
IntentFilter filter = new IntentFilter();
filter.addAction("android.intent.action.BOOT_COMPLETED");
registerReceiver(receiver, filter);
上述代码中,我们创建了一个名为MyReceiver的BroadcastReceiver实例,并将其注册到系统的android.intent.action.BOOT_COMPLETED
广播中。
BroadcastReceiver的注册过程
接下来,让我们详细解析一下BroadcastReceiver的注册过程。
静态注册
静态注册的关键是通过解析AndroidManifest.xml文件,将其中声明的BroadcastReceiver注册到系统中。
在ActivityThread
类的handleBindApplication()
方法中,会调用LoadedApk
类的makeApplication()
方法来加载应用程序的配置信息,其中会解析AndroidManifest.xml文件。
private void handleBindApplication()
{
// ...
try {
// ...
LoadedApk loadedApk = mResourcesManager.getLoadedApk(appInfo.sourceDir,
mResCompatibilityInfo);
// ...
service = loadedApk.makeApplication(mRestrictedProcesses[0], this);
// ...
} catch (Exception e) {
// ...
}
// ...
}
在LoadedApk
的makeApplication()
方法中,会调用parseComponent()
方法解析AndroidManifest.xml文件中的组件信息,其中包括BroadcastReceiver。
public Application makeApplication(boolean forceDefaultAppClass, Instrumentation instrumentation) {
// ...
Application app = null;
String appClass = null;
try {
// ...
appClass = ai != null ? ai.className : "android.app.Application";
java.lang.ClassLoader cl = getClassLoader();
if (!forceDefaultAppClass && ai != null && ai.appComponentFactory != null) {
app = (Application) cl.loadClass(ai.appComponentFactory).newInstance();
} else {
// ...
app = new Application();
}
// ...
} catch (Exception e) {
// ...
}
// ...
ArrayList<BroadcastReceiver> receivers = mReceivers.get(app);
if (receivers == null) {
receivers = new ArrayList<BroadcastReceiver>();
mReceivers.put(app, receivers);
}
return app;
}
在parseComponent()
方法中,会调用parseComponentFilters()
方法解析BroadcastReceiver的过滤器信息,其中会获取到BroadcastReceiver的IntentFilter
实例。
动态注册
动态注册的过程相对比较简单。在Context
的registerReceiver()
方法中,会将BroadcastReceiver的实例和IntentFilter注册到系统中。
public Intent registerReceiver(BroadcastReceiver receiver, IntentFilter filter)
{
// ...
return registerReceiver(receiver, filter, null, null);
}
在registerReceiver()
方法中,会将BroadcastReceiver和IntentFilter打包成ReceiverDispatcher
实例,并将其添加到系统的ActivityThread
的mRegisteredReceivers
集合中。
Intent registerReceiver(BroadcastReceiver receiver, IntentFilter filter, String broadcastPermission,
Handler scheduler) {
// ...
IIntentReceiver rd = null;
if (receiver != null) {
if (mPackageInfo != null && context != null) {
// ...
rd = mPackageInfo.getReceiverDispatcher(receiver, context, mMainThread.getHandler(),
mInstrumentation, true);
} else {
throw new IllegalArgumentException(
"You must register your BroadcastReceiver with registerReceiver()");
}
}
// ...
intent = mMainThread.getInstrumentation().execStartActivity(
getOuterContext(), mMainThread.getApplicationThread(), null, null,
intent, -1, options);
// ...
return intent;
}
总结
通过以上分析,我们可以看到BroadcastReceiver的注册过程是在系统的ActivityThread
中完成的。静态注册是通过解析AndroidManifest.xml文件,将Receiver信息存储到系统中;而动态注册是通过Context
的registerReceiver()
方法将Receiver和IntentFilter打包注册到系统中。这些过程对于我们理解BroadcastReceiver的本质以及应用程序的广播消息处理流程非常重要。
以上就是Android源码剖析:BroadcastReceiver注册过程详细解析的内容,希望对读者有所帮助。如有错误或不足之处,请指正。
本文来自极简博客,作者:深海探险家,转载请注明原文链接:Android源码剖析:BroadcastReceiver注册过程详细解析