Flutter应用运行时触发RenderBox未布局错误,求解决方案
Flutter布局渲染异常解决方法
问题原因
你在SingleChildScrollView嵌套的Column中直接使用了ListView,而ListView默认会尝试占用无限的垂直空间,父组件无法为其提供明确的尺寸约束,导致渲染库抛出RenderBox was not laid out异常。
解决方案
有两种常用修复方式:
方式一:给ListView添加shrinkWrap: true
让ListView根据子项总高度自适应自身尺寸,不再强制占用无限空间,同时禁用自身滚动避免与外层SingleChildScrollView冲突:
修改后的代码:
body: SingleChildScrollView( child: Column( children: [ StreamBuilder( stream: FirebaseFirestore.instance.collection('Ads').snapshots(), builder: (BuildContext context, AsyncSnapshot<QuerySnapshot> snapshot) { if (!snapshot.hasData) { return const Center( child: CircularProgressIndicator(), ); } return ListView( shrinkWrap: true, physics: const NeverScrollableScrollPhysics(), children: snapshot.data!.docs.map((document) { return Card( child: ListTile( leading: Image.asset('assets/images/facebook.png'), title: Text(document['Title']), subtitle: Text(document['Description']), trailing: const Icon(Icons.car_crash), ), ); }).toList(), ); }) ], ), ),
方式二:移除外层SingleChildScrollView
ListView本身具备滚动能力,嵌套SingleChildScrollView会造成滚动冲突,直接将ListView作为body子组件即可:
修改后的代码:
body: StreamBuilder( stream: FirebaseFirestore.instance.collection('Ads').snapshots(), builder: (BuildContext context, AsyncSnapshot<QuerySnapshot> snapshot) { if (!snapshot.hasData) { return const Center( child: CircularProgressIndicator(), ); } return ListView( children: snapshot.data!.docs.map((document) { return Card( child: ListTile( leading: Image.asset('assets/images/facebook.png'), title: Text(document['Title']), subtitle: Text(document['Description']), trailing: const Icon(Icons.car_crash), ), ); }).toList(), ); }, ),
说明
- 方式一适合需要在
ListView上下方添加固定内容的场景; - 方式二更简洁,适用于页面主体就是列表的场景,避免不必要的滚动嵌套。
内容的提问来源于stack exchange,提问作者Alex Ali
相关产品推荐
相关产品推荐

