仅在flutter中热重装后才检索值

时间:2020-02-09 12:11:19

标签: firebase flutter dart google-cloud-firestore

我有点扑朔迷离,我一直在使用Firebase作为后端来构建一个小型应用程序,每当我尝试从Firebase加载数据时,直到重新加载应用程序时我都无法获取值,这不是不是整个代码, 我认为这些小部件是在数据本身之前加载的,是否真的可以使用我们的帮助,有什么方法可以使用状态来刷新值?

mycode:

import 'package:cloud_firestore/cloud_firestore.dart';
import 'package:firebase_auth/firebase_auth.dart';
import "package:flutter/material.dart";
import 'package:mine_app/textingpage.dart';

class FriendsPage extends StatefulWidget {
  @override
  State<StatefulWidget> createState() {
    return _FriendsPage();
  }
}

class Friends {
  final int theirTexts;
  final String username;
  final int  myTexts;
  final int totalTexts;
  final String friendId;

  Friends(this.theirTexts,this.totalTexts,this.username,this.myTexts,this.friendId);

  Friends.fromMap(DocumentSnapshot map)
    :assert(map["username"]!=null),
    assert(map["myTexts"]!=null),
    assert(map["theirTexts"]!=null),
    assert(map["totalTexts"]!=null),
    assert(map["uid"]!=null),
    username = map["username"],
    myTexts = map["myTexts"],
    theirTexts = map["theirTexts"],
    totalTexts = map["totalTexts"],
    friendId = map["uid"];
}


class _FriendsPage extends State<FriendsPage> {
  String user;
  String globalid = "";

  Future<void> getuser() async {
    user = (await FirebaseAuth.instance.currentUser()).uid;
  }

  @override
  void initState() {
    getuser();
    super.initState();
  }

  @override
  Widget build(BuildContext context) {
    return DefaultTabController(
      length: 2,
      child: Scaffold(
          appBar: AppBar(
            backgroundColor: Color(0xff723881),
            centerTitle: true,
            title: Text(
              "Chats",
            bottom: TabBar(
              tabs: [
                Tab(icon: Icon(Icons.people), text: "People"),
                Tab(icon: Icon(Icons.search), text: "Find"),
              ],
              indicatorColor: Colors.white,
            ),
          ),
          body: TabBarView(
            children: <Widget>[
              Container(
                child: snapShotBuilder(context)
              ),
              Container()
            ],
          )),
    );
  }

  Widget snapShotBuilder(BuildContext context){
    return StreamBuilder<QuerySnapshot>(
      stream: Firestore.instance.collection("users").document(user).collection("friends").snapshots(),
      builder:(context,snapshot){
        if (!snapshot.hasData) {
          return LinearProgressIndicator();
        }
          return myListView(context,snapshot.data.documents); 
    } );
  }

  Widget myListView(BuildContext context,List<DocumentSnapshot> snapshot){
    return Container(
      child: ListView(
        children: snapshot.map((data)=>myfriends(Friends.fromMap(data))).toList(),
      ),
    );
  }

  Widget myfriends(Friends friend) {
    return Container(
      margin: EdgeInsets.only(top: 10.0),
      padding: EdgeInsets.all(5.0),
      child: ListTile(
        onTap:(){
          setState(() {
            globalid = friend.friendId;
          });
          print(friend.friendId);
          Navigator.push(context, MaterialPageRoute(builder: (context)=>ChatPage(userid:friend.friendId)));
        },
        trailing: Container(
            // margin: EdgeInsets.only(top:30.0,left:10.0,right:0.0),
            child: Text(
          friend.totalTexts.toString(),),
        leading: Container(
          width: 60.0,
          height: 60.0,
        ),
        title: Text(friend.username,),
      ),
    );
  }
}

2 个答案:

答案 0 :(得分:2)

您需要在getUser()中设置setState()并检查快照是否也有数据,因此修改后的代码将是

import 'package:cloud_firestore/cloud_firestore.dart';
import 'package:firebase_auth/firebase_auth.dart';
import "package:flutter/material.dart";
import 'package:mine_app/textingpage.dart';

class FriendsPage extends StatefulWidget {
  @override
  State<StatefulWidget> createState() {
    return _FriendsPage();
  }
}

class Friends {
  final int theirTexts;
  final String username;
  final int  myTexts;
  final int totalTexts;
  final String friendId;

  Friends(this.theirTexts,this.totalTexts,this.username,this.myTexts,this.friendId);

  Friends.fromMap(DocumentSnapshot map)
    :assert(map["username"]!=null),
    assert(map["myTexts"]!=null),
    assert(map["theirTexts"]!=null),
    assert(map["totalTexts"]!=null),
    assert(map["uid"]!=null),
    username = map["username"],
    myTexts = map["myTexts"],
    theirTexts = map["theirTexts"],
    totalTexts = map["totalTexts"],
    friendId = map["uid"];
}


class _FriendsPage extends State<FriendsPage> {
  String user;
  String globalid = "";

  Future<void> getuser() async{
    setState((){
       user = (await FirebaseAuth.instance.currentUser()).uid;
    });
  }

  @override
  void initState() {
    getuser();
    super.initState();
  }

  @override
  Widget build(BuildContext context) {
    return DefaultTabController(
      length: 2,
      child: Scaffold(
          appBar: AppBar(
            backgroundColor: Color(0xff723881),
            centerTitle: true,
            title: Text(
              "Chats",
            bottom: TabBar(
              tabs: [
                Tab(icon: Icon(Icons.people), text: "People"),
                Tab(icon: Icon(Icons.search), text: "Find"),
              ],
              indicatorColor: Colors.white,
            ),
          ),
          body: TabBarView(
            children: <Widget>[
              Container(
                child: snapShotBuilder(context)
              ),
              Container()
            ],
          )),
    );
  }

  Widget snapShotBuilder(BuildContext context){
    return StreamBuilder<QuerySnapshot>(
      stream: Firestore.instance.collection("users").document(user).collection("friends").snapshots(),
      builder:(context,snapshot){
        if (snapshot.hasData) {
          return myListView(context,snapshot.data.documents); 
        }else if(snapshot.hasError){
          return Center(
          child:Text(snapshot.error.toString()));
        }else{
          return LinearProgressIndicator();
        }

    } );
  }

  Widget myListView(BuildContext context,List<DocumentSnapshot> snapshot){
    return Container(
      child: ListView(
        children: snapshot.map((data)=>myfriends(Friends.fromMap(data))).toList(),
      ),
    );
  }

  Widget myfriends(Friends friend) {
    return Container(
      margin: EdgeInsets.only(top: 10.0),
      padding: EdgeInsets.all(5.0),
      child: ListTile(
        onTap:(){
          setState(() {
            globalid = friend.friendId;
          });
          print(friend.friendId);
          Navigator.push(context, MaterialPageRoute(builder: (context)=>ChatPage(userid:friend.friendId)));
        },
        trailing: Container(
            // margin: EdgeInsets.only(top:30.0,left:10.0,right:0.0),
            child: Text(
          friend.totalTexts.toString(),),
        leading: Container(
          width: 60.0,
          height: 60.0,
        ),
        title: Text(friend.username,),
      ),
    );
  }
}

答案 1 :(得分:0)

您是对的。在调用initState之后立即构建了窗口小部件,但是您使用Future获取了用户数据,因此很可能Future尚未完成。因此,您只需要用FutureBuilder包装主窗口小部件:

@override
Widget build(BuildContext context) {
  return FutureBuilder<String>(
    future: getUser(), // <-- your future
    builder: (context,snapshot) {
      return DefaultTabController(
        length: 2,
        child: Scaffold(
          appBar: AppBar(
            backgroundColor: Color(0xff723881),
            centerTitle: true,
            title: Text(
              "Chats",
            bottom: TabBar(
              tabs: [
                Tab(icon: Icon(Icons.people), text: "People"),
                Tab(icon: Icon(Icons.search), text: "Find"),
              ],
              indicatorColor: Colors.white,
            ),
          ),
          body: TabBarView(
            children: <Widget>[
              Container(
                child: snapShotBuilder(context)
              ),
              Container()
            ],
          ),
        ),
      ),
    },
  );
}