uni-app 不能直接用原生 tabbar 实现自定义图标和文字,因其仅支持 80×80 png 图标、不支持 svg/字体图标及动态样式,文字样式完全不可控,且 h5 端降级为 div 模拟导致行为不一致;必须设置 "tabbar": {"custom": true} 并手动实现 custom-tab-bar/index.vue。

uni-app 里为什么不能直接用原生 tabBar 做自定义图标和文字?
因为 uni-app 的 tabBar 配置只支持微信小程序、App 和 H5 的基础能力,图标必须是 80×80 PNG,不支持 SVG、字体图标或动态颜色;文字样式(如加粗、行高、间距)完全不可控,且 H5 端会 fallback 成 div 模拟,行为不一致。
真正要“自定义”,就得关掉原生 tabBar,自己手写一个——也就是设置 "tabBar": {"custom": true},然后在项目根目录放 custom-tab-bar/index.vue。
- 必须在
pages.json中显式关闭:"tabBar": {"custom": true},否则自定义组件不会被加载 -
custom-tab-bar/index.vue路径不能错,大小写敏感,uni-app 不会报错提示路径不存在 - H5 端需额外处理:
position: fixed容易被页面滚动内容盖住,得加z-index和bottom: 0
custom-tab-bar/index.vue 怎么响应页面切换并高亮当前项?
uni-app 不会自动把当前页面路径传给自定义 tabBar 组件,得自己监听 onTabItemTap 或用 getCurrentPages() 推断。
推荐做法是:在 tabBar 组件的 mounted 钩子中调用 uni.getTabBar()(仅 App 和小程序有效),但 H5 不支持;更稳妥的是在每个 tab 页面的 onShow 里触发全局事件,或用 uni.$emit 通知 tabBar 更新 currentIndex。
- 别依赖
uni.getTabBar()在 H5 使用,它返回undefined,会直接报错 - 用
getCurrentPages().pop().route可以拿到当前页面路径,但要注意路由带参数时(如pages/user/user?id=1)需截取?前部分再匹配 - 高亮状态建议用 class 切换,而不是内联 style,避免 SSR 或多端渲染不一致
点击 tab 时怎么跳转页面又不重复 push?
直接 uni.navigateTo({ url: 'xxx' }) 会导致栈里堆叠多个相同页面;而 uni.switchTab() 只对 tabBar 配置里的页面生效——但你已经关了原生 tabBar,所以它会静默失败,控制台也不报错。
正确做法是:先用 uni.getPages() 查找目标页面是否已在栈中,有则 uni.navigateBack 回退到它;没有则 uni.switchTab(仅小程序/App)或 uni.reLaunch(H5 兼容性更好)。
- 小程序端
uni.switchTab仍可用,即使custom: true,只要目标页在tabBar.list配置里 - H5 必须用
uni.reLaunch,否则 URL 不刷新,页面状态也不会重置 - 不要在 tabBar 组件里直接调用
uni.navigateTo,容易导致页面栈混乱
图标用 iconfont 或 svg 时为什么在小程序里不显示?
微信小程序不支持直接引用外部字体文件(如 iconfont.css),也不支持 <svg></svg> 标签渲染(除非用 canvas 或 base64 内联);App 端对字体支持较好,但需要把 ttf 文件放进 static 并在 css 中用 @font-face 声明。
最稳方案是:所有图标转成 base64 图片,或使用 uni-app 官方推荐的 uni-icons 组件(它内部做了多端兼容处理)。
- 别在
custom-tab-bar/index.vue里用@import引入 iconfont.css,小程序编译后失效 - 如果坚持用字体图标,App 端需确认 ttf 文件放在
static/fonts/,且 css 中src: url('~@/static/fonts/iconfont.ttf')写法在 HBuilderX 3.9+ 才支持 - SVG 推荐用
<image src="data:image/svg+xml;base64,..."></image>,但注意 base64 字符串不能换行,需压缩
自定义 tabBar 表面只是个导航栏,实际牵扯路由控制、跨端差异、生命周期同步、图标资源管理——最容易被忽略的是 H5 和小程序在 switchTab 行为上的根本分歧,以及图标资源在不同平台的加载机制。这些地方一动就出问题,但错误信息往往不明确,得靠日志和真机反复验证。










