1

我的应用程序按照以下(从这里)销毁 webviews。

 parentConstraintLayout.removeView(webView)
 webView.apply{
     clearHistory()
     clearCache(true)
     loadUrl("about:blank")
     onPause()
     removeAllViews()
 }

这一直运行良好,直到将 Kotlin 版本从 1.4.32 升级到 1.5.0 使用 Kotlin 1.5.0,webView 变量在 parentConstraintLayout.removeView(webView)执行后变为 null。clearHistory()引发 NPE 并且应用程序崩溃。webView并且parentConstraintLayout都在 XML 中声明。

我已经验证其他一切都相同,Kotlin 1.5.0 / 1.5.20 会出现问题,但 1.4.32 不会出现问题。为什么升级 Kotlin 会发生这种情况,我能做些什么来解决它?

这是webView

<WebView
     android:id="@+id/webView"
     android:layout_width="0dp"
     android:layout_height="0dp"
     app:layout_constraintTop_toBottomOf="@id/webViewToolbarContainer"
     app:layout_constraintLeft_toLeftOf="parent"
     app:layout_constraintRight_toRightOf="parent"
     app:layout_constraintBottom_toBottomOf="parent"
/>

并且parentConstraintLayout- 它是直接父母

<androidx.constraintlayout.widget.ConstraintLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    android:id="@+id/parentConstraintLayout"
>

这是崩溃日志

Fatal Exception: java.lang.NullPointerException: Attempt to invoke virtual method 'void android.webkit.WebView.clearHistory()' on a null object reference
       at com.myapp.android.screens.sweepstakes.ui.DetailActivity.destroyWebView(DetailActivity.java:25)
       at com.myapp.android.screens.ui.DetailActivity.close(DetailActivity.java:21)
       at com.myapp.android.screens.impl.DetailParentPresenter.onTerminationDialogOptionSubmitClicked(DetailParentPresenter.java:69)
       at com.myapp.android.screens.ui.DetailActivity$showSubsequentTerminationDialog$1.invoke(DetailActivity.java:26)
       at com.myapp.android.screens.ui.DetailActivity$showSubsequentTerminationDialog$1.invoke(DetailActivity.java:2)
       at com.afollestad.materialdialogs.callbacks.DialogCallbackExtKt.invokeAll(DialogCallbackExtKt.java:26)
       at com.afollestad.materialdialogs.MaterialDialog.onActionButtonClicked$core(MaterialDialog.java:34)
       at com.afollestad.materialdialogs.internal.button.DialogActionButtonLayout$onFinishInflate$1.onClick(DialogActionButtonLayout.java:8)
       at android.view.View.performClick(View.java:7448)
       at android.view.View.performClickInternal(View.java:7425)
       at android.view.View.access$3600(View.java:810)
       at android.view.View$PerformClick.run(View.java:28305)
       at android.os.Handler.handleCallback(Handler.java:938)
       at android.os.Handler.dispatchMessage(Handler.java:99)
       at android.os.Looper.loop(Looper.java:223)
       at android.app.ActivityThread.main(ActivityThread.java:7664)
       at java.lang.reflect.Method.invoke(Method.java)
       at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:592)
       at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:947)
4

2 回答 2

0

您可以覆盖 loadWebView。在加载 Web 视图之前,您可以清除数据和 cookie

    override fun loadWebView(userAccessToken: Token) {
    mWebView.clearCache(true)
    mWebView.clearFormData()
    mWebView.clearHistory()
    CookieManager.getInstance().removeAllCookies(null)
    CookieManager.getInstance().flush()
    mWebView.webViewClient = object : BaseWebViewClient() {
        override fun shouldOverrideUrlLoading(view: WebView?, url: String?): Boolean {
           // TODO url validator return true/false

        }
    }
    mWebView.loadUrl(uri.toString())
}
于 2021-07-07T02:56:08.817 回答
0

每次引用时,1.5.0 上的 Kotlin 合成都会调用 findViewById(),而不是在 1.4.x 上使用缓存的。由于您将其从视图中删除,因此 findViewById() 返回 null。

您可以改用它:

 webView.apply{
     parentConstraintLayout.removeView(this)
     clearHistory()
     clearCache(true)
     loadUrl("about:blank")
     onPause()
     removeAllViews()
 }
于 2021-10-12T18:12:26.793 回答