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

Android悬浮WebView加载Home Assistant深色模式启动页异常

解决Android悬浮WebView(API28)中Home Assistant启动页深色模式异常问题

问题核心

全屏WebView加载Home Assistant时启动页正常显示深色,但通过WindowManager实现的悬浮WebView启动页为浅色,最终页面可正常显示深色。HA官方说明启动页的深浅由浏览器设置决定,因此需为悬浮WebView配置深色环境。

原因分析

全屏WebView继承了Activity的主题配置,默认适配深色模式;而悬浮WebView是通过WindowManager添加的独立视图,未继承Activity的深色主题,WebView默认使用浅色环境,导致HA启动页加载浅色样式。

解决方案(适配API28)

由于API28不支持WebView的setForceDark等深色模式专属API,需通过视图层级配置+JS注入的方式模拟深色浏览器环境:

1. 为悬浮视图容器设置深色背景

在添加父容器到WindowManager前,设置黑色背景,避免WebView加载前显示空白白色:

mParentView = FrameLayout(this)
mParentView.setBackgroundColor(Color.BLACK) // 添加这一行
windowManager.addView(mParentView, floatWindowLayoutParam)

2. 让WebView继承容器主题上下文

Inflate布局时传入父容器,确保WebView获取到正确的主题环境:

// 替换原inflate代码,传入mParentView作为父容器
floatView = inflater.inflate(R.layout.widget_web, mParentView, false) as ViewGroup

3. 配置WebView背景并注入JS强制深色模式

设置WebView自身背景为黑色,并在页面启动时注入JS,让HA识别到深色环境:

myWebView = floatView.findViewById(R.id.web_view) as WebView
myWebView.setBackgroundColor(Color.BLACK) // 设置WebView深色背景

// 配置WebViewClient,在页面启动时注入JS
myWebView.webViewClient = object : WebViewClient() {
    override fun onPageStarted(view: WebView?, url: String?, favicon: Bitmap?) {
        super.onPageStarted(view, url, favicon)
        view?.evaluateJavascript(
            "(function() { " +
                "document.documentElement.style.setProperty('color-scheme', 'dark only'); " +
                "if (window.matchMedia) { " +
                "window.matchMedia('(prefers-color-scheme: dark)').matches = true; " +
                "} " +
                "})()", null
        )
    }
}

修改后的完整悬浮WebView代码

lateinit var windowManager: WindowManager
lateinit var floatView: ViewGroup
lateinit var mParentView: ViewGroup
lateinit var floatWindowLayoutParam: WindowManager.LayoutParams

setContentView(R.layout.widget_web)
floatWindowLayoutParam = WindowManager.LayoutParams(
    1000,1000,
    WindowManager.LayoutParams.TYPE_APPLICATION_OVERLAY,
    WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE,
    PixelFormat.TRANSLUCENT
)

windowManager = getSystemService(WINDOW_SERVICE) as WindowManager
val inflater: LayoutInflater = baseContext.getSystemService(LAYOUT_INFLATER_SERVICE) as LayoutInflater

mParentView = FrameLayout(this)
mParentView.setBackgroundColor(Color.BLACK)
windowManager.addView(mParentView, floatWindowLayoutParam)

floatView = inflater.inflate(R.layout.widget_web, mParentView, false) as ViewGroup
floatView.visibility = View.GONE
mParentView.addView(floatView)

myWebView = floatView.findViewById(R.id.web_view) as WebView
myWebView.setBackgroundColor(Color.BLACK)
myWebView.settings.javaScriptEnabled = true
myWebView.settings.domStorageEnabled = true
myWebView.setInitialScale(100)
myWebView.addJavascriptInterface(WebViewJavascriptInterface(applicationContext), "externalApp")

myWebView.webViewClient = object : WebViewClient() {
    override fun onPageStarted(view: WebView?, url: String?, favicon: Bitmap?) {
        super.onPageStarted(view, url, favicon)
        view?.evaluateJavascript(
            "(function() { " +
                "document.documentElement.style.setProperty('color-scheme', 'dark only'); " +
                "if (window.matchMedia) { " +
                "window.matchMedia('(prefers-color-scheme: dark)').matches = true; " +
                "} " +
                "})()", null
        )
    }
}

myWebView.loadUrl("http://192.168.1.73:8123/dashboard-studyonly?external_auth=1")
myWebView.requestFocus()
myWebView.visibility = View.VISIBLE
finish()

注意事项

  • 测试前需清除WebView缓存,避免旧的偏好设置干扰结果
  • 确保Home Assistant后台已开启全局深色模式
  • API28及以下版本无法使用WebView原生深色模式API,上述方案是兼容该版本的最优解

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.27 18:20:17