Flutter StreamBuilder 在加载时删除旧数据

Flutter StreamBuilder removes old data while loading

目前,我有一个 StreamBuilder 从 Firebase 中为群发消息应用提取数据。我有一个 snapshot.hasData 检查以确保在显示消息之前有数据。问题是,当 setState 重建小部件时,它还会重建 StreamBuilder,导致它在再次完成加载数据之前显示静态 snapshot.hasData == false 内容。这看起来真的很糟糕,因为它的加载速度太快了,以至于每次重建时屏幕看起来都在闪烁一秒钟。

我该如何在数据自行重新加载时保留数据,使其看起来不会闪烁?

有什么方法可以阻止 StreamBuilder 在特定情况下重建?

谢谢!

编辑添加的当前代码。

var firebaseStream;
  @override
  void initState() {
    super.initState();
    firebaseStream = Firestore.instance
        .collection('groups')
        .document(groupID)
        .collection('messages')
        .orderBy('date', descending: true)
        .limit(15)
        .snapshots();

StreamBuilder(
  stream: firebaseStream,
  builder: (context, snapshot) {
     if (!snapshot.hasData)
        return Container(
           color: Colors.red,);
        return ListView.builder(

听起来好像您是直接在 StreamBuilder 流中获取数据 属性:

StreamBuilder(
  stream: firebase.getData(),
  ...
)

这个问题是每次调用 setState 时都会创建一个新流,并且总是给出初始 null 值。相反,您应该使用 StatefulWidget 并在 initState 期间在您的状态中创建一个变量,以便它只运行一次。然后使用此变量作为 StreamBuilder 中的流 属性。这是一个非常简单的例子:

class Example extends StatefulWidget {
  Example({Key key}) : super(key: key);

  @override
  _ExampleState createState() => _ExampleState();
}

class _ExampleState extends State<Example> {
  Stream firebaseData;

  @override
  void initState() {
    super.initState();
    firebaseData = Firebase.fetchData(); //Or whatever function you use
  }

  @override
  Widget build(BuildContext context) {
    return StreamBuilder(
      stream: firebaseData,
      builder: (BuildContext context, AsyncSnapshot snapshot) {
        if (snapshot.hasData) {
          return Text(snapshot.data);
        } else {
          return Loading();
        }
      },
    );
  }
}

您尝试过使用 snapshot.Connection 状态吗?

@override
      Widget build(BuildContext context) {
        return StreamBuilder(
          stream: firebaseData,
          builder: (BuildContext context, AsyncSnapshot snapshot) {
            if (snapshot.connectionState == ConnectionState.active && snapshot.hasData) {
final data = snapshot.data;
              return Text(data);
            } else if (snapshot.connectionState == ConnectionState.waiting) {
              return Loading(); // OR CircularProgressIndicator()
            } else // Handle error here.
          },
        );
      }