Flutter:如何在导航栏上方添加定位图标(persistent_bottom_nav_bar)
解决方案
要实现中间图标悬浮在导航栏上方的效果,核心问题是当前固定高度的SizedBox会截断向上偏移的图标。通过Stack分层布局配合Positioned即可解决,具体修改如下:
class MyCustomNavigationBar extends StatelessWidget { final List<PersistentBottomNavBarItem> items; final int selectedIndex; final ValueChanged<int> onItemSelected; const MyCustomNavigationBar({ required this.items, required this.selectedIndex, required this.onItemSelected, Key? key, }) : super(key: key); @override Widget build(BuildContext context) { // 外层容器增加高度,给悬浮图标预留显示空间 return SizedBox( width: double.infinity, height: 80.0, child: Stack( alignment: Alignment.bottomCenter, children: [ // 底层:常规导航栏区域(高度保持原60) SizedBox( height: 60.0, child: Row( mainAxisAlignment: MainAxisAlignment.spaceAround, children: items.map((item) { int index = items.indexOf(item); // 跳过中间图标,用占位容器保持布局对称 if (index == 2) return const SizedBox(width: 60); Widget icon = IconTheme( data: IconThemeData( size: item.iconSize, color: selectedIndex == index ? item.activeColorPrimary : item.inactiveColorPrimary, ), child: item.icon, ); return GestureDetector( onTap: () => onItemSelected(index), child: icon, ); }).toList(), ), ), // 上层:悬浮的中间图标 Positioned( bottom: 20.0, // 向上偏移,悬浮在导航栏上方 child: GestureDetector( onTap: () => onItemSelected(2), child: DecoratedBox( decoration: BoxDecoration( borderRadius: BorderRadius.circular(30), color: Colors.blue, boxShadow: [ BoxShadow( color: Colors.black12, blurRadius: 4, offset: const Offset(0, 2), ) ], ), child: Padding( padding: const EdgeInsets.all(12.0), child: IconTheme( data: IconThemeData( size: items[2].iconSize, color: items[2].activeColorPrimary, ), child: items[2].icon, ), ), ), ), ), ], ), ); } }
关键调整说明:
- 用
Stack实现分层:底层是常规导航栏,上层单独放置悬浮图标,避免图标被容器截断 - 给中间图标通过
Positioned设置偏移量,让它悬浮在导航栏上方 - 原导航栏的Row中给中间位置留空,保证左右图标布局对称
- 给悬浮图标添加点击事件,确保页面切换逻辑正常触发
- 外层容器高度调整为80,为悬浮图标预留足够显示空间
内容的提问来源于stack exchange,提问作者Linesofcode
相关产品推荐
相关产品推荐

