Передача данных из класса в класс - Flutter - PullRequest
0 голосов
/ 21 мая 2018

У меня есть List Builder, который создает список на основе документов, перечисленных в Firestore.Я пытаюсь взять значение, сгенерированное из снимка Firestore, и передать его из класса в переменную, которая обновляется каждый раз, когда пользователь нажимает на другую запись в построителе списков.Вот класс, выполняющий взаимодействие с Firestore и возвращающий ListBuilder:

class DeviceBuilderListState extends State<DeviceBuilderList> {
  final flutterWebviewPlugin = new FlutterWebviewPlugin();

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

    // Listen for our auth event (on reload or start)
    // Go to our device page once logged in
    _auth.onAuthStateChanged
        .where((user) {
      new MaterialPageRoute(builder: (context) => new DeviceScreen());
    });

    // Give the navigation animations, etc, some time to finish
    new Future.delayed(new Duration(seconds: 1))
        .then((_) => signInWithGoogle());
  }

  void setLoggedIn() {
    _auth.onAuthStateChanged
        .where((user) {
      Navigator.of(context).pushNamed('/');
    });
    }

  @override
  Widget build(BuildContext context) {
    return new FutureBuilder<FirebaseUser>(
        future: FirebaseAuth.instance.currentUser(),
        builder: (BuildContext context, AsyncSnapshot<FirebaseUser> snapshot) {
              if (snapshot.data != null)
                return new StreamBuilder(
                  stream: Firestore.instance
                      .collection('users')
                      .document(snapshot.data.uid)
                      .collection('devices')
                      .snapshots,
                  builder: (context, snapshot) {
                    if (!snapshot.hasData)
                      return new Container();
                    return new Container(
                      margin: const EdgeInsets.symmetric(vertical: 10.0),
                        child: new ListView.builder(
                            itemCount: snapshot.data.documents.length,
                            padding: const EdgeInsets.all(10.0),
                            itemBuilder: (context, index) {
                              DocumentSnapshot ds =
                              snapshot.data.documents[index];
                              return new Card(
                                  child: new GestureDetector(
                                  onTap: () {

                                      var initialStateLink = "${ds['name']}";

                                Navigator.of(context).pushNamed("/widget");
                              },
                              child: new Text(
                                " ${ds['name']}",
                                style: new TextStyle(fontSize: 48.0),
                              ),
                              ));
                            }),

                    );
                  },
                );
              else return new Container();
          }

    );}
}  

Затем я хочу отправить var initialStateLink другой функции в том же файле dart:

Future<String> initialStateUrl() async {
  final FirebaseUser currentUser = await _auth.currentUser();

  Firestore.instance.collection('users')
      .document(currentUser.uid).collection('devices').document(initialStateLink).get()
      .then((docSnap) {
    var initialStateLink = ['initialStateLink'];
      return initialStateLink.toString();
      });
  return initialStateUrl().toString();
}  

Итакчто он возвращает мне правильную строку.Я совершенно не понимаю, как это сделать, и мне не удалось найти еще один вопрос, который ответил на это.Спасибо за идеи.

Ответы [ 3 ]

0 голосов
/ 22 мая 2018

Вы можете использовать Navigator.push(Route route) вместо Navigator.pushNamed(String routeName)

И я не призываю вас размещать код навигации глубоко в дереве виджетов, сложно поддерживать логику потока приложений, потому что вы в конечном итогесо многими частями кода навигации во многих классах.Мое решение - разместить навигационный код в одном месте (один класс).Давайте назовем это AppRoute, это выглядит так:

class AppRoute {

  static Function(BuildContext, String) onInitialStateLinkSelected =
      (context, item) =>
      Navigator.of(context).push(
          new MaterialPageRoute(builder: (context) {
              return new NewScreen(initialStateLink: initialStateLink);
            }
          ));

}

и заменим ваш код на onTap:

onTap: () {
  var initialStateLink = "${ds['name']}";
  AppRoute.onInitialStateLinkSelected(context, initialStateLink);
}

Теперь вы можете не только передавать данные из класса в другойкласс, но также может легко контролировать поток ваших приложений (просто посмотрите на AppRoute класс)

0 голосов
/ 22 мая 2018

Я закончил тем, что нашел другое решение, которое решило проблему (например, путем обхода актуальной проблемы).

A MaterialPageRoute позволяет создавать новый виджет на месте при отправке варгументы.Так что это сделало так, чтобы мне не нужно было отправлять какие-либо данные за пределы класса, вот мой код:

return new Card(
    child: new GestureDetector(
    onTap: () {
        Navigator.push(context,
            new MaterialPageRoute(
            builder: (BuildContext context) => new WebviewScaffold(
        url: ds['initialStateLink'],
        appBar: new AppBar(
            title: new Text("Your Device: "+'${ds['name']}'),
        ),
        withZoom: true,
        withLocalStorage: true,)
));},
0 голосов
/ 21 мая 2018
Just make initialStateLink variable Global and send it as an argument to the another class like below,

a) Specify route as follows

'/widget' : (Buildcontext context) => new Anotherscreen(initialStateLink)

b) Navigate to the Anotherscreen()

c) Then the Anotherscreen () will be like this,

class Anotherscreen () extends StatelessWidget {
var initialStateLink;

Anotherscreen (this.initialStateLink);

......
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...