【发布时间】:2019-07-24 22:10:54
【问题描述】:
我想使用 FutureBuilder 加载我手机中的歌曲,以显示加载页面。显示所有歌曲的页面包含在 TabBar 中,它是 PageView 的一部分。碰巧,当我从一个页面移动到另一个页面时,FutureBuilder 似乎冻结了 UI,等待操作完成。我无法弄清楚我做错了什么。我在这里报告我的代码和演示冻结的视频。
https://www.youtube.com/watch?v=Hlwj6TKACLc 我放了一个视频,以使问题尽可能清晰。如您所见,CircularProgressIndicator 冻结为每个 UI 组件
class MusicPage extends StatefulWidget {
@override
State createState() {
return _MusicPageState();
}
}
class _MusicPageState extends State<MusicPage> with
TickerProviderStateMixin {
Future<dynamic> _songs;
@override
Widget build(BuildContext context) {
TabController controller = TabController(
length: 3,
vsync: this,
);
return Scaffold(
appBar: TabBar(
isScrollable: true,
controller: controller,
indicatorColor: Colors.lightBlueAccent,
tabs: widget.tabs),
body: TabBarView(controller: controller, children: <Widget>[
FutureBuilder(
future: _songs,
builder: (context, snapshot){
switch(snapshot.connectionState){
case ConnectionState.done:
return Center(child: Text('done'),);
case ConnectionState.active:
case ConnectionState.none:
case ConnectionState.waiting:
return CircularProgressIndicator();
}
}),
AlbumsGrid(
albums: AlbumUtils.getCachedAllAlbums(),
),
AuthorsList(
authors: widget.authors,
)
]));
}
@override
void initState() {
_songs = MusicFinder.allSongs();
super.initState();
}
}
我希望它不会专注于 Future 加载(就像它是同步的),显然表明它是一个等待指示器。 最后一件事:我省略了一些变量以专注于 FutureBuilder 部分。不要介意他们。
提前感谢大家。
【问题讨论】:
-
我们需要
MusicFinder.allSongs()中的代码 -
MusicFinder 是一个 Flutter 插件,功能在这里:github.com/konaken73/Musicfinder/blob/master/…
-
您在主线程中执行繁重的操作,请考虑在单独的隔离中执行它们(使用
compute函数)。 Here 就是一个例子。 -
最后,我选择了另一种方法,使用单例和提供者。无论如何,我必须在更简单的上下文中使用 FutureBuilder(只是一个 StatefulWidget,它在按下按钮时向自身显示一些数据),并且它通过相同的实现完美地工作,如上所述。我想这是 Flutter 调度核心中处理不当的情况。同时,我也认为对我的问题投反对票的人没有正确阅读。