uni-app 中间凸起按钮需放弃原生 tabbar,改用 custom-tab-bar 自定义组件,通过绝对定位覆盖中间区域,并适配 ios 安全区、安卓点击穿透及路由栈一致性问题。

uni-app 中间凸起按钮怎么加进 Tabbar
直接在 tabBar 配置里加不了——uni-app 官方的 tabBar 不支持中间按钮凸起或自定义形状,哪怕你写死 list 五项、把第三项图标放大,它也只是“看起来像”,实际点击区域、高亮逻辑、iOS/Android 行为都不一致。
所以必须放弃原生 tabBar,改用自定义 Tabbar + 绝对定位盖住中间区域。
- 用
custom-tab-bar目录结构(uni-app 2.7+ 官方推荐方式),在每个 tab 页面手动引入组件 - 中间按钮不能是
tabBar.list的一项,而是独立<view></view>,用position: absolute居中覆盖 - 注意 z-index:按钮层级必须高于 tabbar 底色,但低于页面内容(比如弹窗),否则点不到
- 安卓下部分机型(尤其华为 EMUI)会拦截绝对定位按钮的点击,需加
pointer-events: auto显式声明
自定义 Tabbar 组件里如何处理选中态和跳转
官方 custom-tab-bar 组件不自动同步当前页面路径,得自己监听 onShow 或用 getCurrentPages() 判断,再更新 current 状态。
- 别依赖
uni.getTabBar()—— 自定义 Tabbar 下这个方法返回undefined - 用
uni.switchTab({ url: '/pages/home/home' })跳转,不是uni.navigateTo;否则 tabbar 高亮错乱 - 中间按钮通常不走 tab 切换,而是触发业务逻辑(如发布商品),所以它的
click事件里不要调switchTab,避免误触返回首页 - 如果中间按钮也要“高亮”(比如带红点),得单独维护一个状态变量,和 tab 选中态解耦
为什么 iOS 上中间按钮总被截掉一截
因为 iOS 安全区域(safe area)默认把底部 tabbar 往上顶,而你用 absolute 盖上去的按钮没适配 env(safe-area-inset-bottom),导致被屏幕底边裁切。
- 给按钮容器加
padding-bottom: env(safe-area-inset-bottom)是错的——这会让按钮整体下移 - 正确做法:按钮用
bottom: calc(env(safe-area-inset-bottom) + 10px),把偏移量“补回来” - uni-app 的
custom-tab-bar默认高度是50px,但 iPhone X+ 实际可用高度是83px(含安全区),按钮垂直居中时得按这个算 - 别用固定
height: 60px,不同机型 safe area 高度不同,要用calc()动态计算
发布按钮点击后怎么避免白屏或路由卡住
常见现象:点中间按钮跳转发布页,页面闪一下白屏,或者返回时 tabbar 不恢复高亮。根本原因是生命周期和路由栈没对齐。
- 发布页不能是
tabBar页面(即不能写进tabBar.list),否则switchTab会清空栈,导致返回时丢失上一页状态 - 应该用
uni.navigateTo({ url: '/pages/publish/publish' }),并确保该页面不在tabBar配置中 - 自定义 Tabbar 组件里,
onLoad和onShow都要重新检查当前路径,不然从发布页返回时,tabbar 还显示着旧的 active 状态 - 如果发布页需要权限(如摄像头),首次拒绝后再次打开容易卡在 loading,建议加个
setTimeout延迟 100ms 再执行导航,避开 uni-app 的路由抢占问题
中间按钮最难的不是样式,是它游离在 tabbar 机制之外,又得和 tabbar 视觉、状态、生命周期强耦合。稍不注意,iOS 安全区、安卓点击穿透、路由栈混乱就全来了。










