Flutter go_router:如何使用ShellRoute实现占满剩余空间的子组件?
问题描述
我配置了如下GoRouter路由:
GoRouter( initialLocation: "/one", routes: [ ShellRoute( builder: (_, __, child) => Scaffold(body: Column(children: [const Text("Header"), child],)), routes: [ GoRoute( path: '/one', builder: (_, __) => const Expanded(child: Text("one")), ), ], ), ], )
运行后框架无法渲染组件树,抛出错误:Assertion failed: ... hasSize。我知道这是因为ShellRoute会把其子组件包裹在Navigator中,而Navigator会对嵌套内容施加最大约束。
请问怎么构建这种嵌套导航结构,让Shell的Column里既有固定元素,子路由又能垂直填充剩余可用空间?
解决方案
核心问题是ShellRoute传递的child(即嵌套的Navigator)在Column中没有明确的尺寸约束,导致后续Expanded无法正确计算剩余空间。调整方案如下:
- 在ShellRoute的builder中,给
child包裹一层Expanded,让它占据Column的剩余垂直空间 - 子路由的组件无需再用Expanded包裹,直接返回内容即可
修改后的完整代码:
GoRouter( initialLocation: "/one", routes: [ ShellRoute( builder: (_, __, child) => Scaffold( body: Column( children: [ const Text("Header"), // 让嵌套的Navigator占满Column剩余空间 Expanded(child: child), ], ), ), routes: [ GoRoute( path: '/one', builder: (_, __) => const Text("one"), ), ], ), ], )
原理说明
Column中固定尺寸的Header会先占据对应空间,剩余空间由Expanded分配给嵌套的Navigator。Navigator拿到明确的布局约束后,内部的子路由组件就能正常渲染,不会再触发hasSize断言错误。如果子路由内部需要填充自身容器的空间,可以在组件内部再使用Expanded或其他布局组件。
内容的提问来源于stack exchange,提问作者András Szepesházi
相关产品推荐
相关产品推荐

