Flutter stream builder是否一次又一次地构建我的小部件而不改变流?
《颤振》中的“溪流建设者”被召回。我不知道为什么。我相信问题可能是我在StreamBuilder中有一个bloc提供者。My stream dataBloc.dataStream未更改,从而导致streambuilder重新生成。不确定,我做错了什么。stream builder是否一次又一次地构建我的小部件而不在流中进行任何更改。显然那不是真的!对吧?Flutter stream builder是否一次又一次地构建我的小部件而不改变流?,flutter,flutter-layout,flutter-dependencies,flutter-sliver,Flutter,Flutter Layout,Flutter Dependencies,Flutter Sliver,《颤振》中的“溪流建设者”被召回。我不知道为什么。我相信问题可能是我在StreamBuilder中有一个bloc提供者。My stream dataBloc.dataStream未更改,从而导致streambuilder重新生成。不确定,我做错了什么。stream builder是否一次又一次地构建我的小部件而不在流中进行任何更改。显然那不是真的!对吧? Widget build(context) { final DataBloc dataBloc = DataBlocProvi
Widget build(context) {
final DataBloc dataBloc = DataBlocProvider.of(context);
print("dropdown build called again");
// this doesn't print recursively so this is perfect.
// So my build is not getting called again.
return StreamBuilder(
stream: dataBloc.dataStream,
builder: (context, snapshot) {
//ToDo remove prints
print("dropdown ${snapshot.data}");
// there is no change in snapshot.data, however print is getting called recursively. This is bad and wrong
// so my stream builder is getting called again, and this is wrong
String key = dataElement.conditionalField;
String _valueArray = dataElement.conditionalValues.toString();
String conditionalValue =
_valueArray.substring(1, _valueArray.length - 1);
Map<String, String> dataMap = snapshot.hasData ? snapshot.data : {};
bool isVisible = true;
if (key != "" &&
dataMap.containsKey(key) &&
dataMap[key] == conditionalValue.toString()) {
isVisible = true;
} else if (key != "") {
isVisible = false;
}
return Visibility(
child: BlocDropDownProvider(
fieldName: dataElement.key,
dataBloc: dataBloc,
child: Card(
color: Colors.grey[100],
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
mainAxisAlignment: MainAxisAlignment.start,
children: <Widget>[
label,
new Container(
height: 8.0,
),
dropDown,
],
),
),
),
visible: isVisible? true:false,
);
根据给定的细节,我无法以1:1的准确度复制此问题。我遇到的类似情况是,
StreamBuilder
中的构建在ConnectionState
更改时再次被调用
这里有一个使用StreamBuilder发送HTTP请求的最小复制。这里的HTTP请求示例基于此
导入'dart:async';
进口“包装:颤振/材料.省道”;
将“package:http/http.dart”导入为http;
导入“dart:convert”;
void main(){
runApp(MyApp());
}
类MyApp扩展了无状态小部件{
@凌驾
小部件构建(构建上下文){
返回材料PP(
标题:“颤振演示”,
主题:主题数据(
主样本:颜色。蓝色,
),
主页:MyHomePage(标题:“颤振演示主页”),
);
}
}
类MyHomePage扩展StatefulWidget{
MyHomePage({Key,this.title}):超级(Key:Key);
最后的字符串标题;
@凌驾
_MyHomePageState createState()=>\u MyHomePageState();
}
类_MyHomePageState扩展状态{
最终streamController=streamController();
@凌驾
void initState(){
super.initState();
fetchAlbum()。然后((响应)=>streamController.add(响应));
}
@凌驾
无效处置(){
super.dispose();
streamController.close();
}
@凌驾
小部件构建(构建上下文){
debugPrint('build');
返回流生成器(
stream:streamController.stream,
生成器:(BuildContext上下文,异步快照){
debugPrint('Stream$snapshot');
返回脚手架(
appBar:appBar(
标题:文本(widget.title),
),
正文:中(
子项:snapshot.hasData
文本('Album${snapshot.data.title}')
:Text('Waiting…'),
),
);
},
);
}
未来
然后,我再次建议,只要构建中的小部件是可管理的,就不要过于关注构建成本。本文讨论了有关颤振最佳实践的更多细节。可能不是StreamBuilder
,但如果build()
(包含StreamBuilder的那一个)调用,则StreamBuilder添加的小部件也会再次生成。我添加了我的第一个打印语句以检查这一点。我的生成不会再次被调用。我添加了注释。问题在于我的StreamBuilder。那里有些不正确!这也可能是流一次又一次地发出相同的值。({idnumber:10}
)如果值与前一个值相等,可以使用诸如seeStream\distinct()
method之类的方法来过滤这些值
I/flutter (14422): dropdown {idnumber: 10}
I/flutter (14422): dropdown {idnumber: 10}