我有从网站抓取数据的异步函数。(我使用http和html插件)。
这个函数用url填充我的**imageUrls List
。我在initState和FutureBuilder中调用这个函数。我把这个列表作为参数传递给MyCard
**。
1.)这是用户第一次看到loadingCard()
,(当函数从网站收集url的数据时)。如下所示:
一米三米一x
FutureBuilder(
future: getWebsiteBasics(),
builder: ((context, snapshot) {
if (snapshot.connectionState == ConnectionState.waiting) {
return ListView(children: [
loadingCard(),
loadingCard(),
loadingCard(),
loadingCard(),
loadingCard(),
]);
} else if (snapshot.connectionState == ConnectionState.done) {
if (snapshot.hasError) {
return const Text('Error');
} else {
return ListView(
children: List.generate(10,
(index) => MyCard(
imgUrl: imageUrls[index],
)));
}
} else {
return Text('State: ${snapshot.connectionState}');
}
}))
我正在**MyCard class()
**中加载这些图像。
2.)这是第二个加载屏幕,(在看到loadingCard()
之后,用户看到CircularProgressIndicator()
),最后向用户显示图像。如下所示:
一米七三
Image.network(
widget.imgUrl[0],
loadingBuilder: (BuildContext context, Widget child,
ImageChunkEvent? loadingProgress) {
if (loadingProgress == null) {
return child;
}
return const CircularProgressIndicator();
}),
问题在哪里
我想摆脱第二次加载**CircularProgressIndicator()
,并在loadingCard()
消失后首先加载图像。我想将加载图像(2.)sub)纳入函数,并在一个加载屏幕上加载所有内容(loadingCard()
)**。
我的刮取数据功能:
Future getWebsiteBasics() async {
final response = await http.get(Uri.parse(
"url"));
dom.Document html = dom.Document.html(response.body);
final imgs = html
.querySelectorAll("picking up correct selectors")
.toList()
.map((e) =>
e.querySelectorAll('img').map((a) => a.attributes['src']!).toList())
.toList();
imageUrls = imgs;
}
2条答案
按热度按时间imzjd6km1#
别想挽回。
这个问题的真实的解决方案是状态管理。有几个很好的解决方案作为概念和flutter包提供。我个人经常使用BLoC模式。
您需要将视图(小部件)与模型(要显示的数据)和控制器(从网页加载数据)分开。
最后可能会得到一个StreamBuilder()小部件,它在控制器接收到新图像时更新视图。
k3bvogb12#
如果我明白问题是什么的话,那就是当你接收到一个新的图像或者构建中的更改时,它会再次渲染,所以你必须再次等待所有图像加载完毕。
最好的办法是我来处理这是使用一个flutter包cached_network_image这保存在手机的缓存图像。如果你收到一个新的图像从服务器这只会加载新的图像。如果如果一个变化的建设加载的图像将在那里不需要等待了。
希望对你有用,问候