当前位置: 首页 > 工具软件 > eC-lang > 使用案例 >

java.lang.IllegalArgumentException: View=DecorView not attached to window manager(Android Dialog崩溃)

华哲茂
2023-12-01

监控报警,Dialog偶现Crash。日志如下:

java.lang.IllegalArgumentException: View=DecorView@9d9a86 not attached to window manager
        at android.view.WindowManagerGlobal.findViewLocked(WindowManagerGlobal.java:619)
        at android.view.WindowManagerGlobal.removeView(WindowManagerGlobal.java:511)
        at android.view.WindowManagerImpl.removeViewImmediate(WindowManagerImpl.java:200)
        at android.app.Dialog.dismissDialog(Dialog.java:766)
        at android.app.Dialog.dismiss(Dialog.java:746)       

对应代码如下:

private void doNetWork() {
    showLoading();
    //网络请求...
    hideLoading();
}

private void showLoading() {
    if (loadingDialog == null) {
        loadingDialog = new LoadingDialog(this);
    }
    loadingDialog.show();
}

private void hideLoading() {
    if (loadingDialog != null) {
        loadingDialog.dismiss();
    }
}

初步分析:dialog在diss时发现无可依附window,原因可能为异步网络请求返回时此Activity已经finish。

初步方案是:isShowLoading里有判断window所依赖的View是否为null,加上试试。

/**
 * @return Whether the dialog is currently showing.
 */
public boolean isShowing() {
    return mDecor == null ? false : mDecor.getVisibility() == View.VISIBLE;
}
private void doNetWork() {
    showLoading();
    //网络请求ing
    hideLoading();
}

//....
private void hideLoading() {
    if (loadingDialog != null && loadingDialog.isShowing()) {
        loadingDialog.dismiss();
    }
}

为了mock还原场景,执行了如下代码,发现依然有“not attached to window manager”的日志报错。

private void doNetWork() {
    showLoading();
    finish();
    //网络请求ing
    hideLoading();
}

需要判断当前依附Activity是否存在,最终优化代码如下:

private void hideLoading() {
    if (loadingDialog != null && loadingDialog.isShowing() && isValidActivity()) {
        loadingDialog.dismiss();
    }
}

private boolean isValidActivity() {
    if (!isDestroyed() && !isFinishing()) {
        return true;
    }
    return false;
}

 类似资料: