关于Android Context------你应该心里稍微有个数

到底是群居好,还是自己一个人独立好,不分情况,考虑所有的情况

什么是Context

大家在开发App时,肯定很多时候都用到了这个东西,获取资源啊,启动activity啊,等等,但是这到底是什么?

Context

看源码:

/**
 * Interface to global information about an application environment.  This is
 * an abstract class whose implementation is provided by
 * the Android system.  It
 * allows access to application-specific resources and classes, as well as
 * up-calls for application-level operations such as launching activities,
 * broadcasting and receiving intents, etc.
 */
public abstract class Context {
     ...  
     //获得系统级服务  
     public abstract Object getSystemService(String name); 
     //通过一个Intent启动Activity 
     public abstract void startActivity(Intent intent); 
     //启动Service    
     public abstract ComponentName startService(Intent service);   
     //根据文件名得到SharedPreferences对象  
     public abstract SharedPreferences getSharedPreferences(String name,int mode);  
     ...  
}

翻译一下上面的注释:
应用程序环境的全局信息的接口。 它是一个抽象类,它的执行被Android系统所提供。它允许获取以应用为特征的资源和类型,是一个统领一些资源(应用程序环境变量等)的上下文。

其他不看,总结Context

应用程序环境的全局信息,就像单词翻译过来的—–上下文

是个抽象类,不管,会有实现的

通过它我们可以获取应用程序的资源和类(包括应用级别操作,如启动Activity,发广播,接受Intent等)

一个应用的Context个数

APP Context总数 = Application数(1) + Activity数(Customer) + Service数(Customer);

为什么是这样?继承不一样,下面讲。

开始分析:

这里写图片描述

ContextImpl

实现了Context类的所有API。

/**
 * Common implementation of Context API, which provides the base
 * context object for Activity and other application components.
 */
class ContextImpl extends Context {

    //所有Application程序公用一个mPackageInfo对象  
    /*package*/ 
    ActivityThread.PackageInfo mPackageInfo;  

    private Context mOuterContext;

    ......
}

ContextWrapper

ContextImpl的代理,该类的构造函数包含了一个真正的Context(ContextImpl对象)引用,ContextImpl的装饰者模式

/**
 * Proxying implementation of Context that simply delegates all of its calls to
 * another Context.  Can be subclassed to modify behavior without changing
 * the original Context.
 */
public class ContextWrapper extends Context {

    //该属性指向一个ContextIml实例,一般在创建Application、Service、Activity时赋值
    Context mBase;

    public ContextWrapper(Context base) {
        mBase = base;
    }

    /**
     * Set the base context for this ContextWrapper.  All calls will then be
     * delegated to the base context.  Throws
     * IllegalStateException if a base context has already been set.
     * 
     * @param base The new base context for this wrapper.
     * 创建Application、Service、Activity,会调用该方法给mBase属性赋值
     */
    protected void attachBaseContext(Context base) {
        if (mBase != null) {
            throw new IllegalStateException("Base context already set");
        }
        mBase = base;
    }
    ......
}

ContextThemeWrapper

该类内部包含了主题Theme相关的接口,即android:theme属性指定的。

/**
 * A ContextWrapper that allows you to modify the theme from what is in the 
 * wrapped context. 
 */
public class ContextThemeWrapper extends ContextWrapper {
   //该属性指向一个ContextIml实例,一般在创建Application、Service、Activity时赋值  

     private Context mBase;  
    //mBase赋值方式同样有一下两种  
     public ContextThemeWrapper(Context base, int themeres) {  
            super(base);  
            mBase = base;  
            mThemeResource = themeres;  
     }  

     @Override  
     protected void attachBaseContext(Context newBase) {  
            super.attachBaseContext(newBase);  
            mBase = newBase;  
     }  
}

再来看看Activity、Service、Application类的继承关系源码:

public class Activity extends ContextThemeWrapper
        implements LayoutInflater.Factory2,
        Window.Callback, KeyEvent.Callback,
        OnCreateContextMenuListener, ComponentCallbacks2,
        Window.OnWindowDismissedCallback {
    ......
}
public abstract class Service extends ContextWrapper implements ComponentCallbacks2 {
    ......
}
public class Application extends ContextWrapper implements ComponentCallbacks2 {
    ......
}

枯燥的来了

Activity中ContextImpl实例化

这里写图片描述

归纳一下:

通过startActivity启动一个新的Activity—>回调ActivityThread的handleLaunchActivity()方法—>内部会调用performLaunchActivity()方法

performLaunchActivity()方法—>调用createBaseContextForActivity(xx,xx)方法

createBaseContextForActivity(xx,xx )中创建了ContextImpl对象,并且调用了contextImpl的setOuterContext(activity),将当前的Activity对象赋值给了内部成员变量mOuterContext,所以到了这一步,ContextImpl类关联了Activity

最后通过调用Activity.attach( xx,xx,·····)方法,将createBaseContextForActivity返回的ContextImpl对象传入到ContextWrapper类的mBase变量,这样,ContextWrapper类的成员mBase就被实例化l

Service中ContextImpl实例化

图不贴了,和Activity差不多

通过startService启动一个新的Activity—>回调ActivityThread的handleCreateService()方法创建了ContextImpl对象,并赋值mOuterContext,产生关联。

调用Service.attach方法,将ContextImpl对象传入到ContextWrapper类的mBase变量

Application中ContextImpl实例化

一个APP以后每次重新启动时都会首先创建Application对象(每个APP都有一个唯一的全局Application对象,与整个APP的生命周期相同)

创建Application—>回调ActivityThread的handleBindApplication()方法

调用该方法中的LoadedApk类的makeApplication方法创建ContextImpl对象,,并赋值mOuterContext,产生关联。

中间还有一系列的attach传递

最后调用Application类的attach方法,ContextImpl对象传入到ContextWrapper类的mBase变量

真复杂,再精简

不管创建Activity,还是Service,还是Application

在ActivityThread线程回调中创建ContextImpl对象,并把自身赋值给内部的mOuterContext对象,产生关联

最后经过里面一系列的方法传递,调用相应的attach,将ContextImpl对象传入到ContextWrapper类的mBase变量。

参考:
http://blog.csdn.net/yanbober/article/details/45967639

http://blog.csdn.net/qinjuning/article/details/7310620

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值