系列笔记4、工厂方法模式 -Activity的onCreate方法

工厂模式比较好理解。uml图如下:










接下来主要要讲的是onCreate方法


一个Activity的onCreate方法相当于一个工厂方法,那么这个onCreate方法是怎么启动的呢?




对于一个应用程序来说,它的真正入口是ActivityThread的main方法。




ActivityThread.java
package android.app;
public final class ActivityThread {
 public static void main(String[] args) {
        SamplingProfilerIntegration.start();




        // CloseGuard defaults to true and can be quite spammy.  We
        // disable it here, but selectively enable it later (via
        // StrictMode) on debug builds, but using DropBox, not logs.
        CloseGuard.setEnabled(false);




        Process.setArgV0("<pre-initialized>");




        Looper.prepareMainLooper();
        if (sMainThreadHandler == null) {
            sMainThreadHandler = new Handler();
        }




        ActivityThread thread = new ActivityThread();
        thread.attach(false);




        if (false) {
            Looper.myLooper().setMessageLogging(new
                    LogPrinter(Log.DEBUG, "ActivityThread"));
        }




        Looper.loop();




        throw new RuntimeException("Main thread loop unexpectedly exited");
    }
}




    private void attach(boolean system) {
        sThreadLocal.set(this);
        mSystemThread = system;
        if (!system) {
            // 非System部分的代码
            ...
            IActivityManager mgr = ActivityManagerNative.getDefault();
            try {
                mgr.attachApplication(mAppThread);
            } catch (RemoteException ex) {
                // Ignore
            }
        } else {
            // System部分的代码
            android.ddm.DdmHandleAppName.setAppName("system_process");
            try {
                mInstrumentation = new Instrumentation();
                ContextImpl context = new ContextImpl();
                context.init(getSystemContext().mPackageInfo, null, this);
                Application app = Instrumentation.newApplication(Application.class, context);
                mAllApplications.add(app);
                mInitialApplication = app;
                app.onCreate();
            } catch (Exception e) {
                throw new RuntimeException(
                        "Unable to instantiate Application():" + e.toString(), e);
            }
        }
        
       ...
    }








最核心的是mgr.attachApplication(mAppThread);这行代码。
这里的非System部分,ActivityManagerNative.getDefault()返回的是一个ActivityMAnagerService(AMS)对象,主要是调用AMS的attachApplication方法,将ApplicationThread绑定至AMS中。看看AMS的attachApplication方法做了什么。








com/android/server/am/ActivityManagerService.java
    public ActivityStack mMainStack;
  public final void attachApplication(IApplicationThread thread) {
        synchronized (this) {
            int callingPid = Binder.getCallingPid();
            final long origId = Binder.clearCallingIdentity();
            //调用此方法进行的绑定
            attachApplicationLocked(thread, callingPid);
            
            Binder.restoreCallingIdentity(origId);
        }
    }




thread.bindApplication方法是将ApplicationThread对象绑定到ActivityManagerService.
然后真正启动Acticity的方法是mMainStack.realStartActivityLocked(hr, app, true, true)




ActivityManagerService.java
private final boolean attachApplicationLocked(IApplicationThread thread,
            int pid) {
              try {
   thread.bindApplication(processName, appInfo, providers,
                    app.instrumentationClass, profileFile, profileFd, profileAutoStop,
                    app.instrumentationArguments, app.instrumentationWatcher, testMode, 
                    isRestrictedBackupMode || !normalMode, app.persistent,
                    new Configuration(mConfiguration), app.compat, getCommonServicesLocked(),
                    mCoreSettingsObserver.getCoreSettingsLocked());
                         } catch (Exception e) {
       return false;
        }
ActivityRecord hr = mMainStack.topRunningActivityLocked(null);
        if (hr != null && normalMode) {
            if (hr.app == null && app.info.uid == hr.info.applicationInfo.uid
                    && processName.equals(hr.processName)) {
                try {
                    if (mMainStack.realStartActivityLocked(hr, app, true, true)) {
                        didSomething = true;
                    }
                } catch (Exception e) {
                    Slog.w(TAG, "Exception in new application when starting activity "
                          + hr.intent.getComponent().flattenToShortString(), e);
                    badApp = true;
                }
            } else {
                mMainStack.ensureActivitiesVisibleLocked(hr, null, processName, 0);
            }
        }




       }




thread.bindApplication有什么作用?留以后再看。
我们来看ActivityStack具体的realStartActivityLocked方法。




ActivityStack.java
    final boolean realStartActivityLocked(ActivityRecord r,
            ProcessRecord app, boolean andResume, boolean checkConfig)
            throws RemoteException {
        //冻结尚未启动的其他Activity
        r.startFreezingScreenLocked(app, 0);
        //向WindowManager设置Token,标识当前App位于前台显示,
        mService.mWindowManager.setAppVisibility(r.appToken, true);




        // 搜集启动较慢的App信息
        r.startLaunchTickingLocked();




        // 检查配置信息
        if (checkConfig) {
            Configuration config = mService.mWindowManager.updateOrientationFromAppTokens(
                    mService.mConfiguration,
                    r.mayFreezeScreenLocked(app) ? r.appToken : null);
            mService.updateConfigurationLocked(config, r, false, false);
        }
        //设置参数
        r.app = app;
        app.waitingToKill = null;
        ...
        try {
            //将桌面的Acticity添加到当前Activity栈到底部
            if (r.isHomeActivity) {
                mService.mHomeProcess = app;
            }
            mService.ensurePackageDexOpt(r.intent.getComponent().getPackageName());
            ...




            //所有参数信息到位后准备启动Acticity
            app.thread.scheduleLaunchActivity(new Intent(r.intent), r.appToken,
                    System.identityHashCode(r), r.info,
                    new Configuration(mService.mConfiguration),
                    r.compat, r.icicle, results, newIntents, !andResume,
                    mService.isNextTransitionForward(), profileFile, profileFd,
                    profileAutoStop);
            
         ...
        return true;
    }




   该方法中,首先会设置相关参数信息,然后调用app.thread.scheduleLaunchActivity方法来启动Activity。也就是ActivityThread类的一个内部类ApplicationThread的scheduleLaunchActivity方法来启动Activity。也就是ActivityThread类的一个内部类ApplicationThread方法。


ActivityThread.java
   private class ApplicationThread extends ApplicationThreadNative {
     public final void scheduleLaunchActivity(Intent intent, IBinder token, int ident,
                ActivityInfo info, Configuration curConfig, CompatibilityInfo compatInfo,
                Bundle state, List<ResultInfo> pendingResults,
                List<Intent> pendingNewIntents, boolean notResumed, boolean isForward,
                String profileName, ParcelFileDescriptor profileFd, boolean autoStopProfiler) {
            ActivityClientRecord r = new ActivityClientRecord();




            r.token = token;
            r.ident = ident;
            r.intent = intent;
            r.activityInfo = info;
            r.compatInfo = compatInfo;
            ...
            updatePendingConfiguration(curConfig);




            queueOrSendMessage(H.LAUNCH_ACTIVITY, r);
        }
}




scheduleLaunchActivity构造了一个ActivityClientRecord对象,设置相关参数,最后通过sendMassage方法发送启动消息到消息队列,由ActivityThread的Handler处理启动,即ActivityThread内部的一个继承自Handler的字类H。




ActivityThread.java
public final class ActivityThread {
    private class H extends Handler {
       public static final int LAUNCH_ACTIVITY         = 100;
       public void handleMessage(Message msg) {
            if (DEBUG_MESSAGES) Slog.v(TAG, ">>> handling: " + msg.what);
            switch (msg.what) {
                case LAUNCH_ACTIVITY: {
                    ActivityClientRecord r = (ActivityClientRecord)msg.obj;




                    r.packageInfo = getPackageInfoNoCheck(
                            r.activityInfo.applicationInfo, r.compatInfo);
                    handleLaunchActivity(r, null);
                } break;
                ...
            }




        }    
    }




    private void handleLaunchActivity(ActivityClientRecord r, Intent customIntent) {
        ...
        Activity a = performLaunchActivity(r, customIntent);
        ...
    }




private Activity performLaunchActivity(ActivityClientRecord r, Intent customIntent) {
     
     ActivityInfo aInfo = r.activityInfo;
        if (r.packageInfo == null) {
            r.packageInfo = getPackageInfo(aInfo.applicationInfo, r.compatInfo,
                    Context.CONTEXT_INCLUDE_CODE);
        }




        ComponentName component = r.intent.getComponent();
       
       f (component == null) {
            component = r.intent.resolveActivity(
                mInitialApplication.getPackageManager());
            r.intent.setComponent(component);
        }




        if (r.activityInfo.targetActivity != null) {
            component = new ComponentName(r.activityInfo.packageName,
                    r.activityInfo.targetActivity);
        }




        //构造Activity对象并设置参数
        Activity activity = null;
        try {
            java.lang.ClassLoader cl = r.packageInfo.getClassLoader();
            activity = mInstrumentation.newActivity(
                    cl, component.getClassName(), r.intent);
        
        } catch (Exception e) {
           
        }
      try {
         //获取Application对象
         Application app = r.packageInfo.makeApplication(false, mInstrumentation);
         if (activity != null) {
             ContextImpl appContext = new ContextImpl();
             //将Application对象,Context对象绑定到Activity对象
             activity.attach(appContext, this, getInstrumentation(), r.token,
                        r.ident, app, r.intent, r.activityInfo, title, r.parent,
                        r.embeddedID, r.lastNonConfigurationInstances, config);
             //调用Activity的onCreate方法
             mInstrumentation.callActivityOnCreate(activity, r.state);
              } catch (Exception e) {
              }
          return activity;
    }


Instrumentation类会在应用的任何代码执行前被实列化,用来监控系统与应用的交互。可以看到Activity在这里调用了performCreate方法,并最终在performCreate方法里执行了onCreate方法。


Instrumentation.java
    public class Instrumentation {
    public void callActivityOnCreate(Activity activity, Bundle icicle) {
        ...
        activity.performCreate(icicle);
        ...
    }




    Activity.java
    final void performCreate(Bundle icicle) {
        onCreate(icicle);
        mVisibleFromClient = !mWindow.getWindowStyle().getBoolean(
                com.android.internal.R.styleable.Window_windowNoDisplay, false);
        mFragments.dispatchActivityCreated();
    }
    
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值