安卓11之adb命令清除锁屏密码
需求說明
客戶設(shè)置密碼后容易遺忘,反復(fù)刷機(jī)不符合需求,需要預(yù)留一個(gè)adb命令去直接清除掉鎖屏密碼。
為什么不直接刪除對(duì)應(yīng)文件
安卓11找不到對(duì)應(yīng)的.key文件了,根據(jù)老的版本,大概8.0之前是有.key文件去管理鎖屏密碼的,但是現(xiàn)在沒有了
修改
原理
制造假數(shù)據(jù)(空的數(shù)據(jù))去覆蓋掉,然后在通過方法去清除掉空數(shù)據(jù)
設(shè)置假數(shù)據(jù)去覆蓋掉舊的密碼
路徑:
frameworks\base\core\java\com\android\internal\widget\LockPatternUtils.java代碼:
/*** Save a new lockscreen credential.** <p> This method will fail (returning {@code false}) if the previously saved credential* provided is incorrect, or if the lockscreen verification is still being throttled.** @param newCredential The new credential to save* @param savedCredential The current credential* @param userHandle the user whose lockscreen credential is to be changed** @return whether this method saved the new password successfully or not. This flow will fail* and return false if the given credential is wrong.* @throws RuntimeException if password change encountered an unrecoverable error.* @throws UnsupportedOperationException secure lockscreen is not supported on this device.* @throws IllegalArgumentException if new credential is too short.*/public boolean setLockCredential(@NonNull LockscreenCredential newCredential,@NonNull LockscreenCredential savedCredential, int userHandle) {if (!hasSecureLockScreen()) {throw new UnsupportedOperationException("This operation requires the lock screen feature.");}newCredential.checkLength();try {if (!getLockSettings().setLockCredential(newCredential, savedCredential, userHandle)) {return false;}} catch (RemoteException e) {throw new RuntimeException("Unable to save lock password", e);}onPostPasswordChanged(newCredential, userHandle);return true;}這個(gè)類怎么用吶?
直接百度翻譯注釋:
這個(gè)方法是用來保存新的鎖屏憑證
這個(gè)方法有三個(gè)參數(shù),分別代表:
新的鎖屏憑證,舊的鎖屏憑證,要修改憑證的用戶
這里提到了LockscreenCredential這個(gè)類,前面兩個(gè)參數(shù)是基于這個(gè)修改的
路徑:
frameworks\base\core\java\com\android\internal\widget\LockscreenCredential.java新的鎖屏憑證:
這里我們需要的是一個(gè)空的密碼憑證,對(duì)應(yīng)方法為:
/*** Creates a LockscreenCredential object representing empty password.*/public static LockscreenCredential createNone() {return new LockscreenCredential(CREDENTIAL_TYPE_NONE, new byte[0]);}很好,這里調(diào)用了自身的構(gòu)造方法,返回一個(gè)基于自己的對(duì)象,這個(gè)構(gòu)造方法怎么說
百度翻譯注釋結(jié)果:
創(chuàng)建表示給定模式的LockscreenCredential對(duì)象
第一個(gè)參數(shù)是一個(gè)類似標(biāo)識(shí)符的東西,在這個(gè)類中通過對(duì)應(yīng)標(biāo)識(shí)去做不同的事情
看代碼得知后面的參數(shù)是指這個(gè)的存放的長(zhǎng)度,就相當(dāng)于預(yù)留多少內(nèi)存空間去存放,這里createNone給的是new byte[0],走if上面,不細(xì)究,喜歡看的自己去細(xì)看源碼。
這樣我們就大概可以知道直接LockscreenCredential.createNone()就可以拿到一個(gè)新的空的鎖屏憑證了,(這里注一個(gè)小知識(shí):被static修飾的方法可以直接調(diào)用,不需要new對(duì)象,且只能被繼承,不能被重寫)。
舊的鎖屏憑證
舊的鎖屏憑證這個(gè)就比較麻煩了,主要是有三種(除了無和滑動(dòng)),這三種分別代表圖案,PIN碼和密碼。
回到LockscreenCredential這個(gè)類,先說密碼的鎖屏憑證
首先是空的憑證和非空憑證的判斷,接下來找非空的判斷走法
/*** Creates a LockscreenCredential object representing the given alphabetic password.*/public static LockscreenCredential createPassword(@NonNull CharSequence password) {return new LockscreenCredential(CREDENTIAL_TYPE_PASSWORD,charSequenceToByteArray(password));}傳個(gè)密碼就好了。嗯,當(dāng)然,這就要知道安卓系統(tǒng)一般保存這種數(shù)據(jù)都是通過數(shù)據(jù)庫(kù)的,既然可以寫入,自然就可以拿到了,當(dāng)然,如果沒有怎么辦,我們就自己做一個(gè)。
先拿密碼和PIN碼為例
路徑:
沒有這個(gè)路徑怎么辦,老辦法找對(duì)應(yīng)類就好了
Settings.System.putString(getContext().getContentResolver(), "lock_password", passwordText.toString());這句代碼加在handleNext();方法里面,
為什么??
看調(diào)用:
這里干了啥,點(diǎn)擊按鍵的監(jiān)聽,什么按鍵?
很顯然,FooterButton,這里是通過導(dǎo)包拿的,應(yīng)該是自定義的一個(gè)控件,主要說明,為什么在這里面調(diào)用,這個(gè)就是輸入密碼的時(shí)候的下一步按鈕的事件監(jiān)聽;
好了,這里我們還需要導(dǎo)包
這里我們已經(jīng)加上了在輸入密碼和PIN碼的,接下來就是圖案密碼了
byte[] pBytes = LockPatternUtils.patternToByteArray(pattern);String res = new String(pBytes);Settings.System.putString(getContext().getContentResolver(), "lock_password", res.toString());加在onPatternDetected(List<LockPatternView.Cell> pattern);方法里面,這里也需要導(dǎo)包
和上面的密碼和PIN碼導(dǎo)的包一樣
由于這兩個(gè)類都是Activity,這樣我們需要考慮到這個(gè)值是否會(huì)受到生命周期的影響,比如說在切換橫豎屏的時(shí)候,由于這個(gè)值不是固定的xml文件中的存在,且沒有對(duì)應(yīng)id去控制,所以,我們需要在onSaveInstanceState()中去保存
這樣我們就創(chuàng)建好了一個(gè)舊的密碼的存儲(chǔ)方式,且保存了舊的憑證的臨時(shí)數(shù)據(jù)。
我們可以通過下面的方式拿到密碼,且知道圖案密碼的保存值也是被轉(zhuǎn)化的password
這樣就可以拿到舊的鎖屏憑證之密碼憑證了。
PIN碼的拿法和這個(gè)一致,只是方法里面的參數(shù)換成了CharSequence pin
我們拿到密碼是針對(duì)鎖屏所有的,所以傳入的參數(shù)還是password,只是方法換成了
接下來就是圖案密碼了
/*** Creates a LockscreenCredential object representing the given pattern.*/public static LockscreenCredential createPattern(@NonNull List<LockPatternView.Cell> pattern) {return new LockscreenCredential(CREDENTIAL_TYPE_PATTERN,LockPatternUtils.patternToByteArray(pattern));}這里用同樣的方法去將password轉(zhuǎn)化成需要的參數(shù)。
這里需要借助LockPatternUtils的byteArrayToPattern()方法,先將password轉(zhuǎn)化成byte數(shù)組,以byte數(shù)組轉(zhuǎn)化成pattern,最后通過createPattern()方法拿到舊的鎖屏憑證之圖案。
要修改憑證的用戶
int userId = UserHandle.USER_SYSTEM;這里直接拿系統(tǒng)用戶就可以了
這個(gè)是UserHandle的類,由于文章篇幅過長(zhǎng),不做闡述,自己去看詳細(xì)代碼
http://t.csdn.cn/2KVw0
現(xiàn)在就已經(jīng)完成了新的空密碼替換舊的密碼了,我們還需要讓鎖屏界面不顯示,也就是切換成無的狀態(tài)
這里用的是LockPatternUtils的setLockScreenDisabled(boolean disable, int userId);方法
以下就是清除鎖屏密碼的全部代碼
//清除鎖屏密碼public void clearLockscreen(){String password = Settings.System.getString(mContext.getContentResolver(), "lock_password");int userId = UserHandle.USER_SYSTEM;int type = mLockPatternUtils.getCredentialTypeForUser(userId);if(type == LockPatternUtils.CREDENTIAL_TYPE_PASSWORD){mLockPatternUtils.setLockCredential(LockscreenCredential.createNone(),LockscreenCredential.createPasswordOrNone(password), userId);mLockPatternUtils.setLockScreenDisabled(true, userId);ShutdownThread.reboot(mContext,"userrequested",false);}else if(type == LockPatternUtils.CREDENTIAL_TYPE_PIN){mLockPatternUtils.setLockCredential(LockscreenCredential.createNone(),LockscreenCredential.createPinOrNone(password), userId);mLockPatternUtils.setLockScreenDisabled(true, userId);ShutdownThread.reboot(mContext,"userrequested",false);}else if(type == LockPatternUtils.CREDENTIAL_TYPE_PATTERN){byte[] pBytes = password.getBytes();mLockPatternUtils.setLockCredential(LockscreenCredential.createNone(),LockscreenCredential.createPattern(LockPatternUtils.byteArrayToPattern(pBytes)), userId);mLockPatternUtils.setLockScreenDisabled(true, userId);ShutdownThread.reboot(mContext,"userrequested",false);}}這里用了ShutdownThread的reboot方法,這個(gè)方法是為了請(qǐng)求干凈關(guān)機(jī),等待子系統(tǒng)清理其
*狀態(tài)等,必須從其UI所在的循環(huán)器線程調(diào)用。如果不使用這個(gè)方法會(huì)無效。
而type是為了篩選3種不同的密碼實(shí)現(xiàn)方式。
方法已經(jīng)給了,則adb命令可以通過廣播去實(shí)現(xiàn),這里不做具體闡述,注意在導(dǎo)包的時(shí)候可能由于不處在一個(gè)項(xiàng)目里面而失敗,建議在PhoneWindowManager.java中實(shí)現(xiàn)。
總結(jié)
以上是生活随笔為你收集整理的安卓11之adb命令清除锁屏密码的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: html弹性盒子垂直排列,css3弹性盒
- 下一篇: RTCP Interarrival j