Android去除煩人的默認(rèn)閃退Dialog
安卓應(yīng)用閃退后總會(huì)出現(xiàn)一個(gè)“抱歉,App已經(jīng)停止運(yùn)行”的彈窗,這樣的用戶體驗(yàn)并不好。很多大廠的App都去除了這個(gè)彈窗,因此本文主要介紹如何去除默認(rèn)閃退彈窗,以及在閃退時(shí)做一些必要的善后工作。
UnCaughtExceptionHandler
UnCaughtExceptionHandler能夠在Thread遇到未catch住的Exception而終止前做一些善后工作。但是它無(wú)法阻止線程停止運(yùn)行,線程最后還是要退出。
Thread.setDefaultUncaughtExceptionHandler(new Thread.UncaughtExceptionHandler() {
@Override
public void uncaughtException(Thread thread, Throwable ex) {
System.exit(1);
}
});
去除Dialog
Android系統(tǒng)默認(rèn)設(shè)置了一個(gè)UnCaughtExceptionHandler,而彈出閃退彈窗的工作就是在這個(gè)handler做的。所以如果要去除彈窗,只要實(shí)現(xiàn)一個(gè)UnCaughtExceptionHandler并替換掉系統(tǒng)默認(rèn)的就可以了,代碼如下。
public class App extends Application {
@Override
public void onCreate() {
super.onCreate();
Thread.setDefaultUncaughtExceptionHandler(new MyUnCaughtExceptionHandler());
}
class MyUnCaughtExceptionHandler implements Thread.UncaughtExceptionHandler{
@Override
public void uncaughtException(Thread thread, Throwable ex) {
ex.printStackTrace();
// do some work here
android.os.Process.killProcess(android.os.Process.myPid());
System.exit(1);
}
}
}
以上的替換UnCaughtExceptionHandler的工作是在Application中統(tǒng)一做的,當(dāng)然你也可以在每一個(gè)Activity中做。對(duì)于單個(gè)Activity還好,當(dāng)Activity很多的時(shí)候就必需實(shí)現(xiàn)一個(gè)BaseActivity,在BaseActivity中替換,其它Activity要集成BaseActivity。
必要的善后工作
為了處理閃退,提升用戶體驗(yàn),有必要做一些善后工作,主要有幾條羅列如下:
異常上報(bào)
可以采用郵件或者通過服務(wù)器接口上傳的方式。兩者各有優(yōu)缺點(diǎn),郵件方式開發(fā)簡(jiǎn)單,但需要用戶額外操作,用戶體驗(yàn)較差。如果用上傳服務(wù)器方式,因?yàn)樵赨nCaughtExceptionHandler中不能打開一個(gè)新的線程,所以只能同步請(qǐng)求,在網(wǎng)絡(luò)情況不好的時(shí)候花費(fèi)時(shí)間會(huì)較長(zhǎng)而阻塞運(yùn)行。也可能因?yàn)榫W(wǎng)絡(luò)原因而上報(bào)失敗。當(dāng)然總體下來還是上傳服務(wù)器好一點(diǎn)。具體實(shí)現(xiàn)留給讀者。
記錄日志
將閃退信息存儲(chǔ)到文件系統(tǒng)中。不能存到SharedPreferences中,因?yàn)榇蜷_SP需要使用一個(gè)新的線程(Android內(nèi)部實(shí)現(xiàn)),而這在UnCaughtExceptionHandler中,這是不被允許的。
閃退三次清除數(shù)據(jù)
很多時(shí)候是由于后臺(tái)返回?cái)?shù)據(jù)錯(cuò)誤導(dǎo)致的閃退。如果這些數(shù)據(jù)被緩存下來,那么用戶即使再次打開還是會(huì)發(fā)生閃退,這時(shí)候就只能通過重裝或者清除數(shù)據(jù)的方式才能解決閃退問題,用戶體驗(yàn)十分不好。所以在多次閃退后自動(dòng)清除緩存數(shù)據(jù)十分必要。具體實(shí)現(xiàn)可以參考我的另一篇博客Android實(shí)現(xiàn)多次閃退清除數(shù)據(jù)。不過該博客中使用的是ACRA,一個(gè)對(duì)UnCaughtExceptionHandler再次封裝的開源項(xiàng)目,讀者可以將ACRA替換為UnCaughtExceptionHandler來實(shí)現(xiàn)。
重新打開App
可以在UnCaughtExceptionHandler中重新打開App或者彈出自定義彈窗。
class MyUnCaughtExceptionHandler implements Thread.UncaughtExceptionHandler{
@Override
public void uncaughtException(Thread thread, Throwable ex) {
ex.printStackTrace();
Intent intent = new Intent(App.this, MainActivity.class);
intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
App.this.startActivity(intent);
android.os.Process.killProcess(android.os.Process.myPid());
System.exit(1);
}
}
注意setFlags這一步是必需的,因?yàn)槭褂玫腃ontext是App的Context,所以必需打開一個(gè)新的任務(wù)隊(duì)列,否則打開Activity無(wú)法生效,如果你替換Handler是在Activity做的,拿到的Context是Activity的Context,則無(wú)需這一步。
注意事項(xiàng)
最主要的注意點(diǎn)我之前已經(jīng)提到,不要在UnCaughtExceptionHandler中新開一個(gè)線程,會(huì)拋出異常。
以上就是本文的全部?jī)?nèi)容,希望對(duì)大家的學(xué)習(xí)有所幫助。
- Android中制作自定義dialog對(duì)話框的實(shí)例分享
- Android中AlertDialog各種對(duì)話框的用法實(shí)例詳解
- 8種android 對(duì)話框(Dialog)使用方法詳解
- Android中使用Toast.cancel()方法優(yōu)化toast內(nèi)容顯示的解決方法
- Android開發(fā)技巧之永不關(guān)閉的Toast信息框(長(zhǎng)時(shí)間顯示而非系統(tǒng)關(guān)閉)
- android之自定義Toast使用方法
- Android重要控件SnackBar使用方法詳解
- Android提醒微技巧你真的了解Dialog、Toast和Snackbar嗎
相關(guān)文章
Android 自定義View實(shí)現(xiàn)任意布局的RadioGroup效果
這篇文章主要介紹了Android 自定義View實(shí)現(xiàn)任意布局的RadioGroup,需要的朋友可以參考下2018-11-11
Android IPC機(jī)制綁定Service實(shí)現(xiàn)本地通信
本文主要介紹Android IPC機(jī)制綁定Service 實(shí)現(xiàn)本地通信,通過圖解,代碼等方式給大家解釋Android IPC機(jī)制,需要參考的同學(xué)可以看一下2016-07-07
Flutter Image實(shí)現(xiàn)圖片加載
這篇文章主要為大家詳細(xì)介紹了Flutter Image實(shí)現(xiàn)圖片加載,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2019-07-07
移動(dòng)端開發(fā)之Jetpack?Hilt技術(shù)實(shí)現(xiàn)解耦
Hilt的出現(xiàn)解決前兩點(diǎn)問題,因?yàn)镠ilt是Dagger針對(duì)Android平臺(tái)的場(chǎng)景化框架,比如Dagger需要我們手動(dòng)聲明注入的地方,而Android聲明的地方不都在onCreate()嗎,所以Hilt就幫我們做了,除此之外還做了很多事情2023-02-02
Android Webview滑進(jìn)出屏幕閃爍的解決方法
這篇文章主要給大家介紹了關(guān)于Android Webview滑進(jìn)出屏幕閃爍的解決方法,文中通過示例代碼介紹的非常詳細(xì),對(duì)各位Android開發(fā)者們具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面來一起學(xué)習(xí)學(xué)習(xí)吧2019-03-03
RecyclerView實(shí)現(xiàn)橫向滾動(dòng)效果
這篇文章主要為大家詳細(xì)介紹了RecyclerView實(shí)現(xiàn)橫向滾動(dòng)效果,文中示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2021-01-01
Kotlin實(shí)現(xiàn)半圓形進(jìn)度條的方法示例
這篇文章主要給大家介紹了關(guān)于Kotlin實(shí)現(xiàn)半圓形進(jìn)度條的相關(guān)資料,文中通過示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面來一起學(xué)習(xí)學(xué)習(xí)吧。2018-03-03
Android ndk獲取手機(jī)內(nèi)部存儲(chǔ)卡的根目錄方法
今天小編就為大家分享一篇Android ndk獲取手機(jī)內(nèi)部存儲(chǔ)卡的根目錄方法,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。一起跟隨小編過來看看吧2018-08-08

