请勿使用
Widget
在你的业务逻辑中
你应该避免使用
小装置
在ui代码之外。
InitInterfaceState
应直接接收数据,并根据数据决定布局:
class _InitInterfaceState extends State<InitInterface> {
late Future<Data> data;
late Stream<Data> streamOfData;
...
然后定义一个方法,该方法实际决定
Column
或
Row
应该在widget树中使用:
Widget getLayout(Data? data) {
if (data == null) {
// Throw exception if the data is null
throw Exception(...);
}
if (data.needsColumn) {
return Column(...);
} else {
return Row(...);
}
}
然后,您可以在FutureBuilder中调用此函数:
@override
Widget build(BuildContext context) {
return Column(
children: [
FutureBuilder<Widget>(
// Use data instead of widget here
future: data,
builder: (BuildContext context, AsyncSnapshot<Widget> snapshot) {
if (snapshot.hasData) {
return getLayout(snapshot.data);
} else if (snapshot.hasError) {
return Text('Error: ${snapshot.error}');
} else {
return const Loading();
}
},
),
ElevatedButton(
onPressed: () {
readyToInstall = updateLayout();
setState(() {});
},
child: Text('Update')
),
],
);
}
避免使用
setState
里面
initState
这里没有问题的原因是
setState
在回叫中被调用,这很好。但这仍然不是一个好的做法,所以你应该考虑将其移动到例如。
getLayout
函数或定义一个新的函数并调用它。
我不知道你到底需要ValueNotifier做什么,所以我帮不了你。
不要在内部编写ui逻辑
build
有副作用的方法
别担心,你没有那样做。它之所以不好,是因为
建造
方法可以按顺序调用多次。这就是为什么你
print("ok")
被多次呼叫。