Asynchronous 是否使用带有ListView.builder的FutureBuilder初始化应用程序,并在每个ListItem中单击一次?
我正在构建一个带有颤振的应用程序,在使用FutureBuilder时遇到了一个问题。情况是,我在应用程序中的主页应该向我的服务器发出请求,并获取一些Json。对getData方法的调用发生在主屏幕的build方法中,不确定这是否正确。 build方法中的下一个调用具有快照并生成ListView 问题是: 每次我点击一个按钮或转到不同的屏幕时,Future Builder都会被触发!这意味着我有一堆无用的API调用 问题是: 我必须改变什么,让未来的建设者只在我进入主屏幕时运行Asynchronous 是否使用带有ListView.builder的FutureBuilder初始化应用程序,并在每个ListItem中单击一次?,asynchronous,flutter,state,future,Asynchronous,Flutter,State,Future,我正在构建一个带有颤振的应用程序,在使用FutureBuilder时遇到了一个问题。情况是,我在应用程序中的主页应该向我的服务器发出请求,并获取一些Json。对getData方法的调用发生在主屏幕的build方法中,不确定这是否正确。 build方法中的下一个调用具有快照并生成ListView 问题是: 每次我点击一个按钮或转到不同的屏幕时,Future Builder都会被触发!这意味着我有一堆无用的API调用 问题是: 我必须改变什么,让未来的建设者只在我进入主屏幕时运行 class Hom
class HomeState extends State<Home> {
int count = 0;
final homeScaffoldKey = GlobalKey<ScaffoldState>();
List compList = new List();
Future<List> getData() async {
final response = await http.get(
Uri.encodeFull("http://10.0.2.2:5000/foruser"),
headers: {
"Authorization":
"JWT eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJleHAiOjE1NTk2NDM4ODcsImlhdCI6MTU1NzA1MTg4NywibmJmIjoxNTU3MDUxODg3LCJpZGVudGl0eSI6MX0.OhuUgX9IIYFX7u0o_6MXlrMYwk7oMCywlmHLw-vbNSY",
"charset": "utf-8"
},
);
if (response.statusCode == 200) {
compList = jsonDecode(response.body);
List<Comp> result = [];
count++;
for (var c in compList) {
Comp comp = Comp.fromJson(c);
result.add(comp);
}
return result;
} else {
throw Exception('Failed to load');
}
}
@override
Widget build(BuildContext context) {
return new Scaffold(
backgroundColor: Colors.white10,
body: Stack(
children: <Widget>[
new Container(
child: FutureBuilder(
future: getData(),
builder: (BuildContext context, AsyncSnapshot snapshot) {
if (snapshot.connectionState == ConnectionState.done) {
if (snapshot.data == null) {
return new Container(
child: Text("whoops"),
);
}
if (snapshot.hasData) {
if (snapshot.data != null) {
if (snapshot.data.toString() == "[]") {
print("no comps - called API: $count");
return new ListView(
key: Key("1"),
children: <Widget>[
new Column(
mainAxisSize: MainAxisSize.max,
children: <Widget>[
SizedBox(
height: 30.0,
),
Card(
color: Colors.blue,
child: Column(
mainAxisSize: MainAxisSize.min,
children: <Widget>[
ListTile(
title: Text(
"Welcome, you have no comps",
style:
TextStyle(color: Colors.white),
),
),
],
),
),
],
),
],
);
}
return ListView.builder(
itemCount: snapshot.data.length,
itemBuilder: (BuildContext context, int index) {
print(index);
if (index == 0) {
return new Column(
children: <Widget>[
Card(
color: Colors.blue,
child: Column(
mainAxisSize: MainAxisSize.min,
children: <Widget>[
ListTile(
title: Text(
"Welcome back, these are your comps",
style:
TextStyle(color: Colors.white),
),
),
],
),
),
SizedBox(
height: 10.0,
),
new CompListItem(
new Comp(
snapshot.data[index].left_name,
snapshot.data[index].right_name,
snapshot.data[index].left,
snapshot.data[index].right,
snapshot.data[index].left_city,
snapshot.data[index].right_city,
snapshot.data[index].latitude_left,
snapshot.data[index].longitude_left,
snapshot.data[index].latitude_right,
snapshot.data[index].longitude_right,
snapshot.data[index].points,
),
"left")
],
);
}
Comp tmp = new Comp(
snapshot.data[index].left_name,
snapshot.data[index].right_name,
snapshot.data[index].left,
snapshot.data[index].right,
snapshot.data[index].left_city,
snapshot.data[index].right_city,
snapshot.data[index].latitude_left,
snapshot.data[index].longitude_left,
snapshot.data[index].latitude_right,
snapshot.data[index].longitude_right,
snapshot.data[index].points,
);
return new CompListItem(tmp, "left");
},
);
} else if (snapshot.data == null) {
return new Container(
child: Text("Sorry, there seems to be a problem :("),
);
}
}
} else {
return CircularProgressIndicator();
}
},
),
),
],
),
floatingActionButton: Column(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
mainAxisSize: MainAxisSize.min,
children: <Widget>[
FloatingActionButton(
heroTag: null,
child: Icon(
Icons.add_location,
color: Colors.white,
),
onPressed: () {
Navigator.push(
context,
MaterialPageRoute(
builder: (context) => MakeComp(),
),
);
},
backgroundColor: Colors.blue,
),
SizedBox(
height: 10.0,
),
FloatingActionButton(
heroTag: null,
child: Icon(Icons.compare_arrows),
onPressed: () {
Navigator.push(
context,
MaterialPageRoute(
builder: (context) => GetComps(),
),
);
},
backgroundColor: Colors.blue,
),
],
));
}
}
实际结果:
打开应用程序->未来构建器运行->显示数据列表->导航到另一个小部件->未来构建器运行->单击一些按钮->未来构建器运行
预期成果:
打开应用程序->Future Builder runs->显示数据列表->导航到另一个小部件->单击某些按钮->在另一个屏幕上执行操作->返回主屏幕->Future Builder runs,在我发布这个问题的那一刻,我找到了答案:D 感谢Rémi Rousselet在这里回答了这个问题: 答案很简单,就是在需要加载数据时,将对未来的调用放入initState方法中,该方法正好被调用 祝大家快乐