Flutter中如何在Sliver里用Future Builder实现API数据网格布局
在Flutter Sliver组件中用FutureBuilder加载API数据并实现网格布局的解决方案
你当前的写法存在两个核心问题:一是把FutureBuilder嵌套在每个网格项的构建逻辑里,导致每个item都会发起一次API请求,既浪费资源又可能出现数据不一致;二是childCount硬写死为固定值,无法适配API返回的动态数据长度。
正确的做法是把FutureBuilder放在SliverGrid的外层,先统一获取API数据,再根据数据渲染网格。以下是修正后的完整代码示例:
slivers: [ FutureBuilder<List<dynamic>>( future: getProducts(), // 仅发起一次API请求 builder: (context, snapshot) { // 处理数据加载中的状态 if (snapshot.connectionState == ConnectionState.waiting) { return const SliverToBoxAdapter( child: Center(child: CircularProgressIndicator()), ); } // 处理数据加载失败的状态 if (snapshot.hasError) { return const SliverToBoxAdapter( child: Center(child: Text('加载数据失败,请稍后重试')), ); } // 数据加载成功,渲染网格 final products = snapshot.data ?? []; return SliverGrid( delegate: SliverChildBuilderDelegate( (context, index) { final product = products[index]; return Container( alignment: Alignment.center, color: Colors.teal[100 * (index % 9)], child: Text(product['title'] ?? '商品 $index'), // 替换为你API返回的实际字段 ); }, childCount: products.length, // 用API返回数据的长度动态设置childCount ), gridDelegate: const SliverGridDelegateWithFixedCrossAxisCount( crossAxisCount: 3, mainAxisSpacing: 15, crossAxisSpacing: 15, childAspectRatio: 2.0, ), ); }, ), ]
关键注意事项
- 避免重复请求:将FutureBuilder放在SliverGrid外层,确保API请求只执行一次,而非每个网格项都发起请求。
- 状态全覆盖:通过
connectionState和hasError处理加载中、错误、成功三种状态,避免出现空白或异常界面。 - 动态childCount:直接使用API返回数据的长度作为
childCount,保证网格项数量与数据完全匹配。
内容的提问来源于stack exchange,提问作者swapnil mane
相关产品推荐
相关产品推荐

