uni-app无法通过JS控制锁屏/控制中心深色模式,必须在manifest.json各平台节点配置"darkmode":true和"themeLocation":"theme.json",并确保theme.json位于根目录、结构合规,系统据此原生渲染预览界面。

uni-app 本身不提供锁屏界面或控制中心的深色模式控制能力——这是操作系统级功能,无法通过前端代码直接干预。所谓“锁屏控制中心适配深色模式”,实际是指:App 启动时、前台运行时、以及原生容器(如 iOS 控制中心预览、Android 锁屏小部件)展示的 UI 是否能跟随系统主题正确渲染。这依赖的是 manifest.json 和 theme.json 的平台级配置,而非 JS 或 CSS 动态切换。
manifest.json 必须为每个目标平台显式开启 darkmode
控制中心/锁屏预览是否显示深色样式,取决于系统是否识别你的 App 支持暗黑模式。iOS 和 Android 均通过原生层读取配置来决定预览界面主题,不是靠 JS 判断。
-
app-plus、mp-weixin、h5、app-harmony等所有启用的平台节点,都必须单独写入"darkmode": true和"themeLocation": "theme.json" - 只在
h5节点配了,而app-plus没配 → iOS 控制中心仍按亮色渲染,即使你 JS 里切了 dark class -
"themeLocation"必须是字符串"theme.json",不能带路径前缀(如"./theme.json"或"static/theme.json"),否则 HBuilderX 4.83+ 直接忽略,且无任何报错提示
theme.json 文件位置和结构必须严格合规
系统控制中心能否正确加载深色变量,取决于 theme.json 是否被原生容器成功解析。它不是普通静态资源,而是编译期注入的配置文件。
- 文件必须放在项目**根目录**(与
manifest.json同级),命名大小写敏感:theme.json≠Theme.json - 内容必须是标准 JSON,UTF-8 无 BOM 编码,结构仅允许两级:
{"light": {}, "dark": {}},键名不能是night、auto或大写Light -
dark对象内只能填 pages.json 中支持的字段对应值,例如:"navigationBarBackgroundColor": "#000000",不能放自定义颜色变量
pages.json 中 @变量仅影响原生层 UI,不作用于 Webview 内容
控制中心看到的导航栏、tabBar、背景色等,来自 pages.json 中引用 @xxx 变量的字段;但这些变量**不会透出到页面 DOM 中**,所以你在 <view style="background-color: @bgColor"> 里用会失效。
- 生效字段仅限:
navigationBarBackgroundColor、navigationBarTextStyle、backgroundColor、tabBar.color、tabBar.selectedColor、tabBar.backgroundColor、tabBar.borderStyle - 注意:
tabBar.borderStyle在微信小程序中只接受字符串"black"或"white",填"#000"或变量会 fallback 到默认值 - 这些值在 App 启动时由原生层注入,手动调用
uni.setStorageSync('theme', 'dark')不会自动刷新导航栏——必须配合uni.reLaunch()或完整重载页面才能生效
App.vue 中 data-theme/class 同步不等于控制中心适配
你在 App.vue 根节点加 class="theme-dark" 或设置 document.documentElement.setAttribute('data-theme', 'dark'),只影响当前 Webview 渲染,对控制中心、锁屏小部件、iOS 应用预览图完全无效。
- 控制中心显示样式由
theme.json+manifest.json共同决定,与运行时 JS 状态无关 - 用户手动切换主题后,若未立刻执行
uni.setStorageSync('theme', 'dark'),冷启动时控制中心仍按上次保存的主题(或默认 light)渲染 - 真机测试时,部分 Android 厂商(如 MIUI、ColorOS)会强制覆盖 JS 设置,需确认系统设置中“深色模式”开关已打开,且 App 权限未被限制
真正影响控制中心和锁屏预览的,只有 manifest 配置、theme.json 内容、以及原生容器是否成功加载这两者。JS 层的所有操作,都只是补足 Webview 内部样式,别指望它能改变系统级预览界面。


















