如何从我的流中获取数据并使用它?

Posted

技术标签:

【中文标题】如何从我的流中获取数据并使用它?【英文标题】:How do I get data from my stream and work with it? 【发布时间】:2021-11-30 18:57:56 【问题描述】:

我在 Cloud Firestore 中存储了以下数据:

我还有一个检查数据的流。

class StufenService 
  String userID;
  StufenService(this.userID);
  
  
  final CollectionReference userTodos =
      FirebaseFirestore.instance.collection('userTodos');
  
  Stream<QuerySnapshot> getStufe() 
    var stufe = userTodos.where('Stufe', isEqualTo: 1);
    stufe = stufe.where('userID', isEqualTo: userID);
    return stufe.snapshots();
  

我在 StreamBuilder 中使用流:

@override
  Widget build(BuildContext context) 
      return Scaffold(
          appBar: AppBar(
            title: Text('Home'),
            backgroundColor: Color.fromRGBO(35, 112, 192, 1),
          ),
          body: FutureBuilder(
              future: standard(),
              builder: (BuildContext context, AsyncSnapshot<void> snapshot) 
                if (snapshot.connectionState != ConnectionState.done) 
                  return Center(child: CircularProgressIndicator());
                 else 
                  return StreamBuilder<QuerySnapshot>(
                    stream: stufenService.getStufe(),
                    builder:
                        (context, AsyncSnapshot<QuerySnapshot> snapshot) 
                      if (!snapshot.hasData) 
                        return Center(child: CircularProgressIndicator());
                        
                      if (snapshot == ('Stufe', 1)) 
                        return ToDo1F(); else
                      return ListView.separated(
                          separatorBuilder: (BuildContext context, int index) 
                            return SizedBox(
                              height: 10,
                            );
                          ,
                          padding: EdgeInsets.all(10),
                          itemCount: Stufen.length,
                          itemBuilder: (BuildContext, i) 
                            String key = Stufen.keys.elementAt(i);
                            return StufenItem(
                              key,
                              Stufen[key]!,
                              () => toggleDone(key),
                              () => select(key),
                            );
                          );
                    ,
                  );
                
              ));
    
  

很遗憾,我无法返回流的数据。 我在这里试试:

if (snapshot.data == ('Stufe', 1)) 
                        return ToDo1F();

我不认为这是要走的路。有谁知道这是怎么做到的吗?还有什么问题吗? 感谢您的宝贵时间!

【问题讨论】:

你遇到了什么错误? 嗨..所以你想在 ListView 中显示 userTodos 的文档数据? @AsimJawad 没有错误。当我在 ListView 中选择一个 Stufe (= Level) 时,我希望 Stream 能够识别这一点并将我分配给用户选择的 Level 的页面返回 @Garth 我希望 Stream 观看 'Stufe:int' (= Level:int) 并返回不同的页面,因为级别数发生了变化。 if (snapshot.data == ('Stufe', 1)) return ToDo1F();例如,如果level:1存储在用户的文档中,则流应该返回ToDoF1()。 【参考方案1】:

查看您的 Firestore DB 中的数据结构。似乎您只想从 Stream 中检索文档数据。

为此:

更新

   @override
  Widget build(BuildContext context) 
    return Scaffold(
      body: SingleChildScrollView(
        child: Column(
          children: [
            SizedBox(
              height: 50,
            ),
            Container(
              height: 500,
              child: StreamBuilder<QuerySnapshot>(
                stream: db.collection('userTodos').snapshots(),
                builder: (BuildContext context,
                    AsyncSnapshot<QuerySnapshot> snapshot) 
                  if (snapshot.hasData) 
                    if (snapshot.data!.docs[0]['Stufe'] == '1') 
                      Navigator.push(
                        context,
                        MaterialPageRoute(
                          builder: (context) => GotoDesiredScreen(),
                        ),
                      );
                    

                    if (snapshot.data!.docs[0]['Stufe'] == '2') 
                      Navigator.push(
                        context,
                        MaterialPageRoute(
                          builder: (context) => GotoDesiredScreen(),
                        ),
                      );
                    

                    if (snapshot.data!.docs[0]['Stufe'] == '3') 
                      Navigator.push(
                        context,
                        MaterialPageRoute(
                          builder: (context) => GotoDesiredScreen(),
                        ),
                      );
                     else 
                      return Text('select');
                    
                  
                  return Center(
                    child: Text('Loading ...'),
                  );
                ,
              ),
            ),
          ],
        ),
      ),
    );
  

如果这就是你想要的 Stream 的全部内容,请告诉我

【讨论】:

我想在相应用户的文档中检查特定的 'Stufe: int = (level: int)。对于不同的关卡,我准备了当用户选择关卡时流应该播放的不同页面。在上面的代码中,我只是检查了快照中是否包含级别 1 以查看它是否有效。但事实并非如此。 在 ListView 中,只有允许用户选择级别 1、2 或 3 的按钮。如果这样做,新级别将存储在相应用户的文档中。我希望流自动切换到我分配给所选级别的页面。 @Lars 我明白了......然后会更新答案 看起来很棒!我已经按照你的方式编辑了我的代码。一个问题仍然存在。我收到以下错误:RangeError (index): Invalid value: Valid value range is empty: 0 我认为这里是零:snapshot.data!.docs[0]['Stufe']。两个问题。 1. 我需要改变什么? 2.Doc[0]是做什么的?除了这个,我什么都懂。 如果您不知道该怎么做,没关系。告诉我 docs[0] 是做什么的。

以上是关于如何从我的流中获取数据并使用它?的主要内容,如果未能解决你的问题,请参考以下文章

如何从 iOS 中的流中接收数据(swift)

我应该如何从我的数据库中获取所有消息并返回它

如何从 .NET 中的流中获取 MemoryStream?

如何从使用 Futures/async/await 的流中正确生成?

如何从我的SQL SERVER获取我的数据库列表,并使用javafx将其添加到组合框中

Azure媒体服务实时流中的流键