结论:navigationstyle: "custom" 仅交出控制权,不自动留白;必须用 padding-top: var(--status-bar-height) 或占位 view 主动避开状态栏,否则内容被顶入状态栏。

直接给结论:不是“覆盖了状态栏”,而是你没让内容主动避开它——navigationStyle: "custom" 只是关掉原生导航栏,不负责留白;必须用 var(--status-bar-height) 做 padding 或占位,否则 iOS/Android 都会把第一行内容顶进状态栏里。
为什么自定义导航栏后内容被“吃掉一截”
常见错误现象:页面顶部文字或按钮看不见,调试器里发现根 <view></view> 的 top 是 0,但手机状态栏(20–44px)压在上面;尤其 iOS 刘海屏、Android 挖孔屏下更明显。
-
navigationStyle: "custom"不等于“沉浸式”,它只是把控制权交给你,但不自动处理状态栏占位 - 微信小程序端更危险:它压根不注入
--status-bar-height,且不会预留空间,设了 custom 就直接贴顶渲染 - H5 端该变量恒为
0px,不能靠它做逻辑分支,否则样式崩
正确做法:用 CSS 变量占位,别调 JS 获取高度
uni-app 在 App 端运行时会注入 --status-bar-height,已适配各机型刘海/挖孔,比 uni.getSystemInfoSync().statusBarHeight 稳定得多。
- 页面根容器加
padding-top: var(--status-bar-height)(推荐),或用空<view class="status-bar"></view>占位 - 自定义导航栏(如
<view class="nav"></view>)必须设background-color: transparent,禁用box-shadow和border - 别在
onLoad里调uni.getSystemInfoSync()——此时 DOM 未挂载,statusBarHeight常为 0 - 真需 JS 读取,等
onReady后用getComputedStyle(document.documentElement).getPropertyValue('--status-bar-height')
小程序端胶囊按钮遮挡怎么办
微信小程序右上角的胶囊按钮(“···”)是原生控件,navigationStyle: "custom" 后它还在,但你的自定义导航栏没为它留空间,结果搜索框、返回按钮被盖住。
- 必须用
uni.getMenuButtonBoundingClientRect()拿胶囊尺寸,再结合uni.getSystemInfoSync().statusBarHeight算出安全区域 - iOS 胶囊下沿距状态栏底约 6px,Android 约 8px,这个差值不能硬编码,得动态算
- 不要只适配高度——胶囊宽度也影响右侧按钮布局,
right和width都要参与计算 - 用
#ifdef MP-WEIXIN包裹胶囊相关逻辑,H5/App 端直接忽略
下拉刷新时状态栏变黑或闪烁
开启 "enablePullDownRefresh": true 后,webview 整体下拉,透明导航栏下的内容就会穿到状态栏区域,Android 尤其容易渲染异常。
- 这不是样式问题,是原生层叠加顺序导致的,
z-index无效 - 正确解法:下拉中临时关闭透明效果,比如绑定
class="{ 'nav-transparent': !isPulling }" - 在
onPullDownRefresh设isPulling = true,stopPullDownRefresh后设isPulling = false - 如果导航栏里有输入框,软键盘弹出也会顶起内容,这类页面建议直接放弃 custom 模式,改用原生
uni-nav-bar或平台原生组件
最易被忽略的一点:pages.json 里设了 navigationStyle: "custom",但忘了同步关掉 "titleNView": false ——App 端下,titleNView 默认为 true,它会和 custom 冲突,导致自定义导航栏被部分覆盖或错位。











