You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

基于API 33的Kotlin WebView应用编译错误求助

求助:WebView集成编译错误及签名打包问题

我翻遍了网络教程、YouTube视频,没找到可行方案——要么教程有错要么已经过时,只能来社区求最新解决办法,问题解决后会更新主帖贴正确代码。
我参考了一个较新的视频教程,模拟器上能跑,但生成不了签名应用包;连Android Studio官方文档的方案都出现未解析引用错误。

参考来源:

  • 某YouTube视频
  • Android Studio官方WebView文档

我的代码

MainActivity.kt

package com.sloth.hub

import android.R
import android.graphics.Bitmap
import android.os.Bundle
import android.view.View
import android.webkit.WebView
import android.webkit.WebViewClient
import androidx.activity.ComponentActivity
import androidx.activity.compose.setContent
import androidx.compose.foundation.layout.fillMaxSize
import androidx.compose.material3.MaterialTheme
import androidx.compose.material3.Surface
import androidx.compose.material3.Text
import androidx.compose.runtime.Composable
import androidx.compose.ui.Modifier
import androidx.compose.ui.tooling.preview.Preview
import com.sloth.hub.ui.theme.SlothHubTheme


class MainActivity : ComponentActivity() {

    private var myWebView: WebView? = findViewById<View>(R.id.webView) as WebView

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContent {
            SlothHubTheme {
                // A surface container using the 'background' color from the theme
                Surface(modifier = Modifier.fillMaxSize(), color = MaterialTheme.colorScheme.background) {
                    Greeting("Android")
                }
            }
        }
        myWebView.setWebViewClient(WebViewClient())
        myWebView.loadUrl("https://app.sloths.one")
        val webSettings = myWebView.getSettings()
        webSettings.javaScriptEnabled = true
    }

    class myWebClient : WebViewClient() {
        override fun onPageStarted(view: WebView, url: String, favicon: Bitmap) {
            super.onPageStarted(view, url, favicon)
        }

        override fun shouldOverrideUrlLoading(view: WebView, url: String): Boolean {
            view.loadUrl(url)
            return true
        }
    }

    override fun onBackPressed() {
        if (myWebView!!.canGoBack()) {
            myWebView!!.goBack()
        } else {
            super.onBackPressed()
        }
    }
}

@Composable
fun Greeting(name: String, modifier: Modifier = Modifier) {
    Text(
            text = "Hello $name!",
            modifier = modifier
    )
}

@Preview(showBackground = true)
@Composable
fun GreetingPreview() {
    SlothHubTheme {
        Greeting("Android")
    }
}

activity_main.xml

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent">

    <WebView
        android:id="@+id/webView"
        android:layout_width="match_parent"
        android:layout_height="match_parent" />
</RelativeLayout>

编译错误信息

e: /home/dgriffin/AndroidStudioProjects/SlothHub/app/src/main/java/com/sloth/hub/MainActivity.kt: (23, 63): 未解析引用: webview
e: /home/dgriffin/AndroidStudioProjects/SlothHub/app/src/main/java/com/sloth/hub/MainActivity.kt: (28, 18): 仅允许对WebView?类型的可空接收者使用安全调用(?.)或非空断言(!!.)
e: /home/dgriffin/AndroidStudioProjects/SlothHub/app/src/main/java/com/sloth/hub/MainActivity.kt: (29, 18): 仅允许对WebView?类型的可空接收者使用安全调用(?.)或非空断言(!!.)
e: /home/dgriffin/AndroidStudioProjects/SlothHub/app/src/main/java/com/sloth/hub/MainActivity.kt: (30, 36): 仅允许对WebView?类型的可空接收者使用安全调用(?.)或非空断言(!!.)
---
org.gradle.api.GradleException: 编译错误。详见日志获取更多详情
Caused by: org.gradle.api.GradleException: 编译错误。详见日志获取更多详情

请求帮助解决这些编译问题,使应用能够正常编译并生成签名应用包。


错误修复方案

1. 解决「未解析引用: webview」问题

  • 删掉import android.R,改成导入自己项目的R文件:import com.sloth.hub.R(Android Studio通常会自动导入,手动补也行)
  • 不能在类初始化阶段调用findViewById——此时Activity还没加载布局,获取到的WebView必然是空的,要把WebView初始化移到onCreate方法里,且必须在加载布局之后执行。

2. 解决可空类型调用错误

myWebView被声明为可空类型WebView?,调用它的方法时必须用安全调用?.或者非空断言!!.,推荐用安全调用+let来避免空指针风险。

3. 修复布局冲突问题

你现在同时用了Compose的setContent和XML布局,两者不能共存,二选一:

方案一:保留XML布局

修改MainActivity,先加载XML布局再初始化WebView:

package com.sloth.hub

import android.graphics.Bitmap
import android.os.Bundle
import android.webkit.WebView
import android.webkit.WebViewClient
import androidx.activity.ComponentActivity
import com.sloth.hub.R

class MainActivity : ComponentActivity() {

    private var myWebView: WebView? = null

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_main) // 先加载XML布局
        myWebView = findViewById(R.id.webView)

        // 用安全调用+let处理可空对象
        myWebView?.let { webView ->
            webView.webViewClient = myWebClient() // 使用自定义的WebViewClient
            webView.loadUrl("https://app.sloths.one")
            val webSettings = webView.settings
            webSettings.javaScriptEnabled = true
        }
    }

    // 改成inner class才能访问Activity上下文
    inner class myWebClient : WebViewClient() {
        override fun onPageStarted(view: WebView, url: String, favicon: Bitmap?) {
            super.onPageStarted(view, url, favicon)
        }

        override fun shouldOverrideUrlLoading(view: WebView, url: String): Boolean {
            view.loadUrl(url)
            return true
        }
    }

    override fun onBackPressed() {
        myWebView?.let {
            if (it.canGoBack()) {
                it.goBack()
            } else {
                super.onBackPressed()
            }
        } ?: super.onBackPressed()
    }
}

方案二:改用Compose实现WebView

如果想继续用Compose,移除XML布局,用AndroidView包裹WebView:

package com.sloth.hub

import android.graphics.Bitmap
import android.webkit.WebView
import android.webkit.WebViewClient
import androidx.activity.ComponentActivity
import androidx.activity.compose.setContent
import androidx.compose.foundation.layout.fillMaxSize
import androidx.compose.material3.MaterialTheme
import androidx.compose.material3.Surface
import androidx.compose.runtime.Composable
import androidx.compose.ui.Modifier
import androidx.compose.ui.viewinterop.AndroidView
import com.sloth.hub.ui.theme.SlothHubTheme

class MainActivity : ComponentActivity() {
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContent {
            SlothHubTheme {
                Surface(modifier = Modifier.fillMaxSize(), color = MaterialTheme.colorScheme.background) {
                    WebViewScreen()
                }
            }
        }
    }
}

@Composable
fun WebViewScreen() {
    AndroidView(modifier = Modifier.fillMaxSize(), factory = { context ->
        WebView(context).apply {
            webViewClient = object : WebViewClient() {
                override fun onPageStarted(view: WebView, url: String, favicon: Bitmap?) {
                    super.onPageStarted(view, url, favicon)
                }

                override fun shouldOverrideUrlLoading(view: WebView, url: String): Boolean {
                    view.loadUrl(url)
                    return true
                }
            }
            loadUrl("https://app.sloths.one")
            settings.javaScriptEnabled = true
        }
    })
}

4. 生成签名应用包

编译错误修复后,按正常流程生成即可:

  1. 点击Android Studio菜单栏Build > Generate Signed Bundle / APK
  2. 选择App Bundle(推荐)或APK,跟着向导完成密钥库配置即可。

内容的提问来源于stack exchange,提问作者David Griffin

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.21 22:05:15