Flutter - 遍历 asynchrous/future 列表
Flutter - iterate over an asynchrous/future list
我正在尝试创建一个列表,其中包含通过 SharedPreferences 获得的值。但是,如果我想使用 SharedPreference,我必须使用异步方法/未来类型,但我不知道如何使用它们。我尝试遍历 sports
列表,但它是 asynchronous/future。那么我该如何迭代它(使用地图)?
class _MyHomePageState extends State<MyHomePage> {
@override
Widget build(BuildContext context) {
return MaterialApp(
Center(
child: Align(
alignment: Alignment.bottomCenter,
child: CarouselSlider(
options: CarouselOptions(
height: 565,
aspectRatio: 16/9,
enlargeCenterPage: true,
viewportFraction: .8,
),
items: sportsList.map((i) {
return Builder(builder: (BuildContext context) {
return Container(
.......
.........
.......
}
static Future<bool> initSharedPreference(String key) async {
final SharedPreferences prefs = await SharedPreferences.getInstance();
return prefs.getBool(key) ?? false;
}
Future<List> sportsList() async {
List sports=[
await initSharedPreference("test")),
....,
....,
....
];
}
此代码无效,原因如下:
The method 'map' isn't defined for the type 'Future'.
只需使用 FutureBuilder
小部件。
在下面的示例中,我的异步函数称为 getSportsList()
,其中 returns 一个 未来的字符串列表 (这可以从 SharedPreferences 中获取,一个API,等等。只要确保它是一个未来)。
class FutureList extends StatelessWidget {
@override
Widget build(BuildContext context) {
// THE FUTURE WIDGET
return FutureBuilder<List<String>>(
future: getSportsList(), // Add your asynchronous function here
builder: (context, AsyncSnapshot<List<String>> snapshot){
List<String> sports = snapshot.data;
// If there is no data in the snapshot, it is probably loading.
if(!snapshot.hasData) return CircularProgressIndicator();
// Now add the widget you want to return
else return CarouselSlider(
options: CarouselOptions(
height: 565,
aspectRatio: 16/9,
enlargeCenterPage: true,
viewportFraction: .8,
),
items: sportsList.map((String item) {
return Builder(builder: (BuildContext context) {
return Container(
.......
.........
.......
},
);
}
}
快照基本上提供了有关未来的信息。 snapshot.data
是从未来得到的结果。 snapshot.hasData
告诉我们未来是否返回值,还有一些其他有用的方法,如 snapshot.connectionState 或 snapshot.hasError 用于错误处理。
如需更多资源,请查看 this video by the flutter team. Also check out the documentation 以了解更多信息
你需要像这样使用FutureBuilder
..
FutureBuilder(
future: sportsList(),
builder: (context, snapshot) {
if (!snapshot.hasData) {
return CircularProgressIndicator();
} else {
return CarouselSlider(
items: snapshot.data.map(.....).toList(),
//other code
);
}
})
为什么会出现这个问题?
Future<List> sportsList() async {
List sports=[
await initSharedPreference("test")),
....,
....,
....
];
}
上面的代码不是一个简单的列表,这里可以直接渲染列表。它返回 Future<List>
必须作为后台工作获取。
所以使用FutureBuilder
。
FutureBuilder 是一次性调用,在其生命周期内将 运行 仅调用一次。所以你可以放心。
FutureBuilder(
future: sportsList(),
builder: (context, snapshot) {
if (!snapshot.hasData) {
return CircularProgressIndicator();
} else {
List<Widget> list = snapshot.data;
return CarouselSlider(
options: CarouselOptions(
height: 565,
aspectRatio: 16/9,
enlargeCenterPage: true,
viewportFraction: .8,
),
items: list.map(.....).toList(),
);
}
})
我正在尝试创建一个列表,其中包含通过 SharedPreferences 获得的值。但是,如果我想使用 SharedPreference,我必须使用异步方法/未来类型,但我不知道如何使用它们。我尝试遍历 sports
列表,但它是 asynchronous/future。那么我该如何迭代它(使用地图)?
class _MyHomePageState extends State<MyHomePage> {
@override
Widget build(BuildContext context) {
return MaterialApp(
Center(
child: Align(
alignment: Alignment.bottomCenter,
child: CarouselSlider(
options: CarouselOptions(
height: 565,
aspectRatio: 16/9,
enlargeCenterPage: true,
viewportFraction: .8,
),
items: sportsList.map((i) {
return Builder(builder: (BuildContext context) {
return Container(
.......
.........
.......
}
static Future<bool> initSharedPreference(String key) async {
final SharedPreferences prefs = await SharedPreferences.getInstance();
return prefs.getBool(key) ?? false;
}
Future<List> sportsList() async {
List sports=[
await initSharedPreference("test")),
....,
....,
....
];
}
此代码无效,原因如下:
The method 'map' isn't defined for the type 'Future'.
只需使用 FutureBuilder
小部件。
在下面的示例中,我的异步函数称为 getSportsList()
,其中 returns 一个 未来的字符串列表 (这可以从 SharedPreferences 中获取,一个API,等等。只要确保它是一个未来)。
class FutureList extends StatelessWidget {
@override
Widget build(BuildContext context) {
// THE FUTURE WIDGET
return FutureBuilder<List<String>>(
future: getSportsList(), // Add your asynchronous function here
builder: (context, AsyncSnapshot<List<String>> snapshot){
List<String> sports = snapshot.data;
// If there is no data in the snapshot, it is probably loading.
if(!snapshot.hasData) return CircularProgressIndicator();
// Now add the widget you want to return
else return CarouselSlider(
options: CarouselOptions(
height: 565,
aspectRatio: 16/9,
enlargeCenterPage: true,
viewportFraction: .8,
),
items: sportsList.map((String item) {
return Builder(builder: (BuildContext context) {
return Container(
.......
.........
.......
},
);
}
}
快照基本上提供了有关未来的信息。 snapshot.data
是从未来得到的结果。 snapshot.hasData
告诉我们未来是否返回值,还有一些其他有用的方法,如 snapshot.connectionState 或 snapshot.hasError 用于错误处理。
如需更多资源,请查看 this video by the flutter team. Also check out the documentation 以了解更多信息
你需要像这样使用FutureBuilder
..
FutureBuilder(
future: sportsList(),
builder: (context, snapshot) {
if (!snapshot.hasData) {
return CircularProgressIndicator();
} else {
return CarouselSlider(
items: snapshot.data.map(.....).toList(),
//other code
);
}
})
为什么会出现这个问题?
Future<List> sportsList() async {
List sports=[
await initSharedPreference("test")),
....,
....,
....
];
}
上面的代码不是一个简单的列表,这里可以直接渲染列表。它返回 Future<List>
必须作为后台工作获取。
所以使用FutureBuilder
。
FutureBuilder 是一次性调用,在其生命周期内将 运行 仅调用一次。所以你可以放心。
FutureBuilder(
future: sportsList(),
builder: (context, snapshot) {
if (!snapshot.hasData) {
return CircularProgressIndicator();
} else {
List<Widget> list = snapshot.data;
return CarouselSlider(
options: CarouselOptions(
height: 565,
aspectRatio: 16/9,
enlargeCenterPage: true,
viewportFraction: .8,
),
items: list.map(.....).toList(),
);
}
})