公司要做个图形锁屏和解锁的酷效果,暂时还不知道该怎么入手,看到LZ下面这篇文章先收藏了
转自http://blog.csdn.net/stevenhu_223/article/details/8490522
Android源码模块锁屏大体分为两种:
1.LockScreen: 系统默认的锁屏,就是我们所常见的系统原生波纹解锁(涉及MultiWaveView视图类)。如下图:
2.UnlockScreen: 进入手机的设置----->安全----->屏幕锁定。在列表中将看到的可选择项:图案,PIN,密码等锁屏都归为UnlockScreen。(可选择任意一项切换锁屏)
锁屏相关源码所在路径:
1.锁屏模块的框架源码所在路径为:frameworks\base\policy\src\com\android\internal\policy\impl(本文所涉及的代码都在这个目录里)
2.相关的锁屏自定义View类及与其关联类的源码所在路径为:frameworks\base\core\java\com\android\internal\widget
开机绘制锁屏流程代码分析:
手机开机时,在SystemServer类的init2()方法中会启动线程类ServerThread的run方法如下:
- class ServerThread extends Thread
- {
- @Override
- public void run()
- {
- WindowManagerService wm = null;
- ...
- try
- {
- wm.systemReady();
- } catch (Throwable e)
- {
- reportWtf("making Window Manager Service ready", e);
- }
- ...
- }
- }
- <span style="font-size:14px;"> </span>
------>上述代码中的wm为WindowManagerService的引用,所以,wm.systemReady()为调用WindowManagerService的systemReady()方法,如下代码:
- public class WindowManagerService extends IWindowManager.Stub implements Watchdog.Monitor, WindowManagerPolicy.WindowManagerFuncs
- {
- final WindowManagerPolicy mPolicy = PolicyManager.makeNewWindowManager();
- ...
- public void systemReady() {
- mPolicy.systemReady();
- }
- ...
- }
------>WindowManagerPolicy的实现类为PhoneWindowManager,所以,接着调用到PhoneWindowManager的systemReady,如下:
- public class PhoneWindowManager implements WindowManagerPolicy
- {
- KeyguardViewMediator mKeyguardMediator;
- ...
- //手机开机后执行
- public void systemReady() {
- // tell the keyguard
- mKeyguardMediator.onSystemReady(); //进行待机锁屏及解锁逻辑
- android.os.SystemProperties.set("dev.bootcomplete", "1");
- synchronized (mLock) {
- updateOrientationListenerLp();
- mSystemReady = true;
- mHandler.post(new Runnable() {
- public void run() {
- updateSettings();
- }
- });
- }
- }
- ...
- }
------>接着,调用到KeyguardViewMediator类的onSystemReady()方法如下:
- public class KeyguardViewMediator implements KeyguardViewCallback,
- KeyguardUpdateMonitor.InfoCallback, KeyguardUpdateMonitor.SimStateCallback
- {
- ...
- /**
- * Let us know that the system is ready after startup.
- */
- //开机显示锁屏入口
- public void onSystemReady() {
- synchronized (this) {
- if (DEBUG) Log.d(TAG, "onSystemReady");
- mSystemReady = true;
- doKeyguardLocked();
- }
- }
- ...
- }
------>调用KeyguardViewMediator.doKeyguardLocked方法,在该方法中,先执行一些条件判断,若满足直接返回。若不直接返回,则紧接着调用KeyguardViewMediator. showLocked方法,代码如下:
- ...
- /**
- * Send message to keyguard telling it to show itself
- * @see #handleShow()
- */
- private void showLocked() {
- if (DEBUG) Log.d(TAG, "showLocked");
- // ensure we stay awake until we are finished displaying the keyguard
- mShowKeyguardWakeLock.acquire(); //确保屏幕处于唤醒状态
- Message msg = mHandler.obtainMessage(SHOW);
- mHandler.sendMessage(msg);
- }
- ...
----->通过handler发送消息SHOW到handleMessage处理,如下:
- ...
- *
- * This handler will be associated with the policy thread, which will also
- * be the UI thread of the keyguard. Since the apis of the policy, and therefore
- * this class, can be called by other threads, any action that directly
- * interacts with the keyguard ui should be posted to this handler, rather
- * than called directly.
- */
- //Handler对象 , 异步处理
- private Handler mHandler = new Handler() {
- @Override
- public void handleMessage(Message msg) { //异步处理
- switch (msg.what) {
- case TIMEOUT:
- handleTimeout(msg.arg1);
- return ;
- case SHOW:
- handleShow();
- return ;
- case HIDE:
- handleHide();
- return ;
- case RESET:
- handleReset();
- return ;
- case VERIFY_UNLOCK:
- handleVerifyUnlock();
- return;
- case NOTIFY_SCREEN_OFF:
- handleNotifyScreenOff();
- return;
- case NOTIFY_SCREEN_ON:
- handleNotifyScreenOn((KeyguardViewManager.ShowListener)msg.obj);
- return;
- case WAKE_WHEN_READY:
- handleWakeWhenReady(msg.arg1);
- return;
- case KEYGUARD_DONE:
- handleKeyguardDone(msg.arg1 != 0);
- return;
- case KEYGUARD_DONE_DRAWING:
- handleKeyguardDoneDrawing();
- return;
- case KEYGUARD_DONE_AUTHENTICATING:
- keyguardDone(true);
- return;
- case SET_HIDDEN:
- handleSetHidden(msg.arg1 != 0);
- break;
- case KEYGUARD_TIMEOUT:
- synchronized (KeyguardViewMediator.this) {
- doKeyguardLocked();
- }
- break;
- }
- }
- };
- ...
------>当case SHOW:时,调用 handleShow方法,如下:
- private KeyguardViewManager mKeyguardViewManager;
- ...
- /**
- * Handle message sent by {@link #showLocked}.
- * @see #SHOW
- */
- //显示锁屏界面
- private void handleShow() {
- synchronized (KeyguardViewMediator.this) {
- if (DEBUG) Log.d(TAG, "handleShow");
- if (!mSystemReady) return;
- mKeyguardViewManager.show();
- mShowing = true;
- adjustUserActivityLocked();
- adjustStatusBarLocked();
- try {
- ActivityManagerNative.getDefault().closeSystemDialogs("lock");
- } catch (RemoteException e) {
- }
- // Do this at the end to not slow down display of the keyguard.
- playSounds(true);
- mShowKeyguardWakeLock.release();
- }
- }
- ...
----->接着调用KeyguardViewManager的show方法。KeyguardViewManager.show()中,会对KeyguardViewHost(mKeyguardHost)和LockPatternKeyguardView(mKeyguardView)是否为空进行判断:
1).若KeyguardViewHost为空,则创建KeyguardViewHost,同时设置更新其相关的布局参数。然后将KeyguardViewHost对象添加到WindowManagerImpl中。
2). 若LockPatternKeyguardView为空,创建LockPatternKeyguardView对象,通过调用LockPatternKeyguardViewProperties.createKeyguardView()创建。同时为它设置回调。然后将创建得到的对象添加到KeyguardViewHost。
代码如下:
- public class KeyguardViewManager implements KeyguardWindowController {
- ...
- private FrameLayout mKeyguardHost; //该ViewGroup作为顶层View,作为WindowManager添加至窗口
- private KeyguardViewBase mKeyguardView; //具体窗口内容。
- //以上两种的关系相当于DecorView和我们Activity内设置的资源文件一样
- private final KeyguardViewProperties mKeyguardViewProperties;
- ...
- /**
- * Show the keyguard. Will handle creating and attaching to the view manager
- * lazily.
- */
- //显示锁屏界面
- public synchronized void show() {
- if (DEBUG) Log.d(TAG, "show(); mKeyguardView==" + mKeyguardView);
- Resources res = mContext.getResources();
- boolean enableScreenRotation =
- SystemProperties.getBoolean("lockscreen.rot_override",false)
- || res.getBoolean(R.bool.config_enableLockScreenRotation);
- if (mKeyguardHost == null) {
- if (DEBUG) Log.d(TAG, "keyguard host is null, creating it...");
- //创建KeyguardViewHost(FrameLayout)
- mKeyguardHost = new KeyguardViewHost(mContext, mCallback);
- final int stretch = ViewGroup.LayoutParams.MATCH_PARENT;
- int flags = WindowManager.LayoutParams.FLAG_FORCE_NOT_FULLSCREEN
- | WindowManager.LayoutParams.FLAG_SHOW_WALLPAPER
- | WindowManager.LayoutParams.FLAG_KEEP_SURFACE_WHILE_ANIMATING
- /*| WindowManager.LayoutParams.FLAG_LAYOUT_IN_SCREEN
- | WindowManager.LayoutParams.FLAG_LAYOUT_INSET_DECOR*/ ;
- if (!mNeedsInput) {
- flags |= WindowManager.LayoutParams.FLAG_ALT_FOCUSABLE_IM;
- }
- if (ActivityManager.isHighEndGfx(((WindowManager)mContext.getSystemService(
- Context.WINDOW_SERVICE)).getDefaultDisplay())) {
- flags |= WindowManager.LayoutParams.FLAG_HARDWARE_ACCELERATED;
- }
- WindowManager.LayoutParams lp = new WindowManager.LayoutParams(
- stretch, stretch, WindowManager.LayoutParams.TYPE_KEYGUARD,
- flags, PixelFormat.TRANSLUCENT);
- lp.softInputMode = WindowManager.LayoutParams.SOFT_INPUT_ADJUST_RESIZE;
- lp.windowAnimations = com.android.internal.R.style.Animation_LockScreen;
- if (ActivityManager.isHighEndGfx(((WindowManager)mContext.getSystemService(
- Context.WINDOW_SERVICE)).getDefaultDisplay())) {
- lp.flags |= WindowManager.LayoutParams.FLAG_HARDWARE_ACCELERATED;
- lp.privateFlags |=
- WindowManager.LayoutParams.PRIVATE_FLAG_FORCE_HARDWARE_ACCELERATED;
- }
- lp.setTitle("Keyguard");
- mWindowLayoutParams = lp;
- //添加KeyguardViewHost
- mViewManager.addView(mKeyguardHost, lp);
- }
- if (enableScreenRotation) {
- if (DEBUG) Log.d(TAG, "Rotation sensor for lock screen On!");
- mWindowLayoutParams.screenOrientation = ActivityInfo.SCREEN_ORIENTATION_SENSOR;
- } else {
- if (DEBUG) Log.d(TAG, "Rotation sensor for lock screen Off!");
- mWindowLayoutParams.screenOrientation = ActivityInfo.SCREEN_ORIENTATION_NOSENSOR;
- }
- //刷新布局
- mViewManager.updateViewLayout(mKeyguardHost, mWindowLayoutParams);
- if (mKeyguardView == null) {
- if (DEBUG) Log.d(TAG, "keyguard view is null, creating it...");
- /*创建锁屏视图,即创建一个LockPatternKeyguardView对象(FrameLayout)。在创建LockPatternKeyguardView
- * 对象的同时,其构造方法中会调用getInitialMode()得到初始化的状态Mode(Lock or unLock)
- */
- mKeyguardView = mKeyguardViewProperties.createKeyguardView(mContext, mUpdateMonitor, this);
- mKeyguardView.setId(R.id.lock_screen);
- //设置回调
- mKeyguardView.setCallback(mCallback);
- final ViewGroup.LayoutParams lp = new FrameLayout.LayoutParams(
- ViewGroup.LayoutParams.MATCH_PARENT,
- ViewGroup.LayoutParams.MATCH_PARENT);
- //将视图加入根布局mKeyguardHost(FrameLayout)
- mKeyguardHost.addView(mKeyguardView, lp);
- if (mScreenOn) {
- //调用LockPatternKeyguardView的show
- mKeyguardView.show();
- }
- }
- // Disable aspects of the system/status/navigation bars that are not appropriate or
- // useful for the lockscreen but can be re-shown by dialogs or SHOW_WHEN_LOCKED activities.
- // Other disabled bits are handled by the KeyguardViewMediator talking directly to the
- // status bar service.
- int visFlags =
- ( View.STATUS_BAR_DISABLE_BACK
- | View.STATUS_BAR_DISABLE_HOME
- );
- mKeyguardHost.setSystemUiVisibility(visFlags);
- mViewManager.updateViewLayout(mKeyguardHost, mWindowLayoutParams);
- mKeyguardHost.setVisibility(View.VISIBLE);
- mKeyguardView.requestFocus();
- }
- ...
- }
------>在上面的代码中,当KeyguardViewHost为空时,首先会调用KeyguardViewProperties的实现类LockPatternKeyguardViewProperties的createKeyguardView方法,来构造一个LockPatternKeyguardView对象,如下:
- <span style="font-size:14px;">public class LockPatternKeyguardViewProperties implements KeyguardViewProperties {
- ...
- //创建一个LockPatternKeyguardView对象
- public KeyguardViewBase createKeyguardView(Context context,
- KeyguardUpdateMonitor updateMonitor,
- KeyguardWindowController controller) {
- return new LockPatternKeyguardView(context, updateMonitor,
- mLockPatternUtils, controller);
- }
- ...
- }</span>
------->而在LockPatternKeyguardView的构造函数中,有如下调用(以下的流程代码实现均在LockPatternKeyguardView中处理):
- /**
- * @param context Used to inflate, and create views.
- * @param updateMonitor Knows the state of the world, and passed along to each
- * screen so they can use the knowledge, and also register for callbacks
- * on dynamic information.
- * @param lockPatternUtils Used to look up state of lock pattern.
- */
- public LockPatternKeyguardView(
- Context context,
- KeyguardUpdateMonitor updateMonitor,
- LockPatternUtils lockPatternUtils,
- KeyguardWindowController controller) {
- ...
- updateScreen(getInitialMode(), false);
- ...
- }
----->getInitialMode()得到当前锁屏模式(lock or unlock),代码如下:
- ...
- *
- * Given the current state of things, what should be the initial mode of
- * the lock screen (lock or unlock).
- */
- //得到初始化的状态Mode (lock or unlock).
- private Mode getInitialMode() {
- final IccCard.State simState = mUpdateMonitor.getSimState();
- if (stuckOnLockScreenBecauseSimMissing() ||
- (simState == IccCard.State.PUK_REQUIRED &&
- !mLockPatternUtils.isPukUnlockScreenEnable())) {
- return Mode.LockScreen;
- } else {
- if (!isSecure() || mShowLockBeforeUnlock) {
- return Mode.LockScreen;
- } else {
- return Mode.UnlockScreen;
- }
- }
- }
- ...
----->再回到updateScreen(getInitialMode(), false),该函数的实现如下:
- ...
- /根据参数(Lock/unLock),判断显示为LockScreen或者UnlockScreen界面
- private void updateScreen(Mode mode, boolean force) {
- if (DEBUG_CONFIGURATION) Log.v(TAG, "**** UPDATE SCREEN: mode=" + mode
- + " last mode=" + mMode + ", force = " + force, new RuntimeException());
- mMode = mode;
- // Re-create the lock screen if necessary
- if (mode == Mode.LockScreen || mShowLockBeforeUnlock) {
- if (force || mLockScreen == null) {
- //重构LockScreen
- recreateLockScreen();
- }
- }
- // Re-create the unlock screen if necessary. This is primarily required to properly handle
- // SIM state changes. This typically happens when this method is called by reset()
- if (mode == Mode.UnlockScreen) {
- //获取UnlockScreen的具体解锁项,如密码锁(Password)或pin锁;枚举类UnlockMode定义了几种不同的Unlock解锁;
- final UnlockMode unlockMode = getUnlockMode();
- if (force || mUnlockScreen == null || unlockMode != mUnlockScreenMode) {
- //重构unLock解锁
- recreateUnlockScreen(unlockMode);
- }
- }
- // visibleScreen should never be null
- final View goneScreen = (mode == Mode.LockScreen) ? mUnlockScreen : mLockScreen;
- final View visibleScreen = (mode == Mode.LockScreen) ? mLockScreen : mUnlockScreen;
- // do this before changing visibility so focus isn't requested before the input
- // flag is set
- mWindowController.setNeedsInput(((KeyguardScreen)visibleScreen).needsInput());
- if (DEBUG_CONFIGURATION) {
- Log.v(TAG, "Gone=" + goneScreen);
- Log.v(TAG, "Visible=" + visibleScreen);
- }
- if (mScreenOn) {
- if (goneScreen != null && goneScreen.getVisibility() == View.VISIBLE) {
- ((KeyguardScreen) goneScreen).onPause(); //隐藏被切换掉的锁(Lock or unLock)
- }
- if (visibleScreen.getVisibility() != View.VISIBLE) {
- ((KeyguardScreen) visibleScreen).onResume();//显示切换得到的锁(Lock or unLock)
- }
- }
- if (goneScreen != null) {
- goneScreen.setVisibility(View.GONE);
- }
- visibleScreen.setVisibility(View.VISIBLE);
- requestLayout();
- if (!visibleScreen.requestFocus()) {
- throw new IllegalStateException("keyguard screen must be able to take "
- + "focus when shown " + visibleScreen.getClass().getCanonicalName());
- }
- }
- ...
------>在updateScreen(getInitialMode(), false)中,对传进来的参数Mode进行对等判断:
1). 若为LockScreen模式锁屏,则如下:
- <span style="font-family:Comic Sans MS;font-size:18px;">// Re-create the lock screen if necessary
- if (mode == Mode.LockScreen || mShowLockBeforeUnlock) {
- if (force || mLockScreen == null) {
- //重构LockScreen
- recreateLockScreen();
- }
- }</span>
----->然后调用到LockPatternKeyguardView.recreateLockScreen(),在该函数中,首先会对LockScreen进行判断,若之前已存在该对象,则进行移除。然后接着再重新调用createLockScreen()构建LockScreen对象。然后将该对象添加到LockPatternKeyguardView中。createLockScreen()的代码如下:
- ...
- 创建lockScreen
- View createLockScreen() {
- View lockView = new LockScreen(
- mContext,
- mConfiguration,
- mLockPatternUtils,
- mUpdateMonitor,
- mKeyguardScreenCallback);
- initializeTransportControlView(lockView);
- return lockView;
- }
- ...
2).若为UnlockScreen模式锁屏,则如下:
- // Re-create the unlock screen if necessary. This is primarily required to properly handle
- // SIM state changes. This typically happens when this method is called by reset()
- if (mode == Mode.UnlockScreen) {
- //获取UnlockScreen的具体解锁项,如密码锁(Password)或pin锁;枚举类UnlockMode定义了几种不同的Unlock解锁;
- final UnlockMode unlockMode = getUnlockMode();
- if (force || mUnlockScreen == null || unlockMode != mUnlockScreenMode) {
- //重构unLock解锁
- recreateUnlockScreen(unlockMode);
- }
- }
----->然后调用到LockPatternKeyguardView.recreateUnlockScreen(unlockMode),在该函数中,进行的处理和recreateLockScreen函数中的处理原则基本上一致。则调用createUnlockScreen(unlockMode)时,会根据unlockMode的不同创建相应的UnlockScreen具体解锁项。
recreateUnlockScreen如下代码:
- ...
- 重新构建UnlockScreen
- private void recreateUnlockScreen(UnlockMode unlockMode) {
- if (mUnlockScreen != null) {
- ((KeyguardScreen) mUnlockScreen).onPause();
- ((KeyguardScreen) mUnlockScreen).cleanUp();
- //mUnlockScreen不为空,则移除UnlockScreen
- removeView(mUnlockScreen);
- }
- mUnlockScreen = createUnlockScreenFor(unlockMode);
- mUnlockScreen.setVisibility(View.INVISIBLE);
- //将UnlockScreen添进LockPatternKeyguardView
- addView(mUnlockScreen);
- }
- ...
----->接着调用createUnlockScreenFor方法,在该方法中会根据传进来的参数UnlockMode(定义UnlockScreen可选项的枚举类)判断,来决定创建启用对应的UnlockScreen,代码实现如下:
- ...
- 根据不同的Unlock Mode , 创建不同的UnlockScreen
- View createUnlockScreenFor(UnlockMode unlockMode) {
- View unlockView = null;
- if (DEBUG) Log.d(TAG,
- "createUnlockScreenFor(" + unlockMode + "): mEnableFallback=" + mEnableFallback);
- if (unlockMode == UnlockMode.Pattern) {
- //启动图案解锁(手机设置中可见切换)
- PatternUnlockScreen view = new PatternUnlockScreen(
- mContext,
- mConfiguration,
- mLockPatternUtils,
- mUpdateMonitor,
- mKeyguardScreenCallback,
- mUpdateMonitor.getFailedAttempts());
- view.setEnableFallback(mEnableFallback);
- unlockView = view;
- } else if (unlockMode == UnlockMode.SimPuk) {
- unlockView = new SimPukUnlockScreen(
- mContext,
- mConfiguration,
- mUpdateMonitor,
- mKeyguardScreenCallback,
- mLockPatternUtils);
- } else if (unlockMode == UnlockMode.SimPin) {
- //启动PIN解锁(手机设置中可见切换)
- unlockView = new SimUnlockScreen(
- mContext,
- mConfiguration,
- mUpdateMonitor,
- mKeyguardScreenCallback,
- mLockPatternUtils);
- } else if (unlockMode == UnlockMode.Account) {
- try {
- unlockView = new AccountUnlockScreen(
- mContext,
- mConfiguration,
- mUpdateMonitor,
- mKeyguardScreenCallback,
- mLockPatternUtils);
- } catch (IllegalStateException e) {
- Log.i(TAG, "Couldn't instantiate AccountUnlockScreen"
- + " (IAccountsService isn't available)");
- // TODO: Need a more general way to provide a
- // platform-specific fallback UI here.
- // For now, if we can't display the account login
- // unlock UI, just bring back the regular "Pattern" unlock mode.
- // (We do this by simply returning a regular UnlockScreen
- // here. This means that the user will still see the
- // regular pattern unlock UI, regardless of the value of
- // mUnlockScreenMode or whether or not we're in the
- // "permanently locked" state.)
- return createUnlockScreenFor(UnlockMode.Pattern);
- }
- } else if (unlockMode == UnlockMode.Password) {
- //启动密码解锁(手机设置中可见切换)
- unlockView = new PasswordUnlockScreen(
- mContext,
- mConfiguration,
- mLockPatternUtils,
- mUpdateMonitor,
- mKeyguardScreenCallback);
- } else {
- throw new IllegalArgumentException("unknown unlock mode " + unlockMode);
- }
- initializeTransportControlView(unlockView);
- initializeFaceLockAreaView(unlockView); // Only shows view if FaceLock is enabled
- mUnlockScreenMode = unlockMode;
- return unlockView;
- }
- ...
在此,LockScreen或者UnlockScreen就创建出来了,当然,只是创建了相应对象,还得再显示。
------>再次回到KeyguardViewManager类的show方法,在执行完该方法中的的mKeyguardView = mKeyguardViewProperties.createKeyguardView(mContext, mUpdateMonitor, this)代码流程后,接着执行mKeyguardView.show(),即调用KeyguardViewBase的实现类LockPatternKeyguardView的show方法,如下:
- //该类作为LockScreen和UnLockScreen界面的载体,控制显示哪个界面
- public class LockPatternKeyguardView extends KeyguardViewBase implements Handler.Callback,
- KeyguardUpdateMonitor.InfoCallback {
- ...
- @Override
- public void show() {
- /*判断锁屏模式(当然,调用该方法之前已经创建LockPatternKeyguardView对象,
- * 即已调用getInitialMode()获得了Mode),根据结果显示锁屏。
- */
- if (mMode == Mode.LockScreen) {
- //调用onResume显示锁屏
- ((KeyguardScreen) mLockScreen).onResume();
- } else {
- ((KeyguardScreen) mUnlockScreen).onResume();
- }
- if (mLockPatternUtils.usingBiometricWeak() &&
- mLockPatternUtils.isBiometricWeakInstalled() && !mHasOverlay) {
- // Note that show() gets called before the screen turns off to set it up for next time
- // it is turned on. We don't want to set a timeout on the FaceLock area here because it
- // may be gone by the time the screen is turned on again. We set the timout when the
- // screen turns on instead.
- showFaceLockArea(); //显示人脸解锁区域
- } else {
- hideFaceLockArea(); //隐藏人脸解锁区域
- }
- }
- ...
- }
这样,LockScreen或者UnlockScreen就显示出来了,我们再来看看LockScreen的onResume()方法的实现,代码如下:
- //手机默认的解锁实现类
- class LockScreen extends LinearLayout implements KeyguardScreen {
- ...
- //处理LockScreen的显示
- public void onResume() {
- mStatusViewManager.onResume();
- postDelayed(mOnResumePing, ON_RESUME_PING_DELAY);
- }
- ...
- }
对于LockScreen或者UnlockScreen的界面布局和View等可视化UI界面时如何画出来的,具体可参考LockScreen类的实现,UnlockScreen可参考的类:PatternUnlockScreen、SimPukUnlockScreen、SimUnlockScreen、AccountUnlockScreen、PasswordUnlockScreen。有兴趣的读者可自行去研究。
小结:
这篇文章只是讲解手机开机启动时,绘制锁屏的流程,至于通过power键点亮,点暗锁屏,解锁,锁屏,LockScreen或者UnlockScreen的UI界面可视化的实现等等的分析,有时间再去深究。
但,万变不离其宗,锁屏的核心类在于KeyguardViewMediator,该类提供了一些接口,由PhoneWindowManager去访问控制Keyguard,而它的初始化是在PhoneWindowManager的init()函数中创建的。也就是在我们上面分析的代码中,在执行mPolicy.systemReady()时(由PhoneWindowManage调用r),已经创建了KeyguardViewMediator。所以,分析好该类是很重要的。