I have an Application
class in which i override getApplicationContext()
.
I've looked in the Android Source code and I'm unable to find from where it's called?
The inheritance hierarchy is:
Application -> ContextWrapper -> Context
public abstract Context getApplicationContext();
getApplicationContext()
is an abstract method in Context
class which is overridden in ContextWrapper
class.
@Override
public Context getApplicationContext() {
return mBase.getApplicationContext();
}
mBase
is reference to an object of type Context
which is initialized in ContextWrapper's constructor but as per the code Application's class constructor passes null to the constructor of super()
i.e. constructor of ContextWrapper
.
public Application() {
super(null);
}
Now the only possible way to pass context is via :
protected void attachBaseContext(Context base) {
if (mBase != null) {
throw new IllegalStateException("Base context already set");
}
mBase = base;
}
but there is no call to this method either. Please help me in finding that from where is getApplicationContext()
called then?
NOTE : Please don't post any links to such questions as I've gone through each one of them but still no concrete answer.
This method is generally used for the application level and can be used to refer to all the activities. For example, if we want to access a variable throughout the android app, one has to use it via getApplicationContext().
You only use getApplicationContext() when you know you need a Context for something that may live longer than any other likely Context you have at your disposal. Scenarios include: Use getApplicationContext() if you need something tied to a Context that itself will have global scope.
getApplicationContext() : Returns the context for the entire application (the process all the Activities are running inside of). Use this instead of the current Activity context if you need a context tied to the lifecycle of the entire application, not just the current Activity.
To get a reference to the ApplicationContext in a Spring application, it can easily be achieved by implementing the ApplicationContextAware interface. Spring will automatically detect this interface and inject a reference to the ApplicationContext: view rawMyBeanImpl. java hosted by GitHub.
I guess the question is rather "where is attachBaseContext()
called for the Application
object?"
See Application.java:
/**
* @hide
*/
/* package */ final void attach(Context context) {
attachBaseContext(context);
mLoadedApk = ContextImpl.getImpl(context).mPackageInfo;
}
If you go a little further up the call chain, you will find Instrumentation.newApplication()
(Instrumentation.java) and finally LoadedApk.makeApplication()
(LoadedApk.java), which are called as the application is being started:
java.lang.ClassLoader cl = getClassLoader();
ContextImpl appContext = new ContextImpl();
appContext.init(this, null, mActivityThread);
app = mActivityThread.mInstrumentation.newApplication(cl, appClass, appContext);
...
mApplication = app;
In short, the base Context supplied to the Application
class is a ContextImpl
instance, created right in this method.
And, if you check ContextImpl.getApplicationContext()
:
@Override
public Context getApplicationContext() {
return (mPackageInfo != null) ? mPackageInfo.getApplication() : mMainThread.getApplication();
}
you'll see that it actually ends up calling LoadedApk.getApplication()
(since mPackageInfo
is the LoadedApk
instance), which is the mApplication
field set by the makeApplication()
method mentioned before.
In short, after all this is set up, Application.getApplicationContext()
ends up returning... the very same Application
instance. :)
Context
is set through setBaseContext
method, when an Activity / Service / Receiver instance is created for the first time. Here is the call stack:
ContextWrapper::attachBaseContext <-- Application::attach <-- Instrumentation::newApplication <-- LoadedApk::makeApplication <-- ActivityThread::performLaunchActivity || ActivityThread::handleReceiver || ActivityThread::handleCreateService || ActivityThread::handleBindApplication
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With