我想导航到另一个页面并使用 Firestore 数据进行解析,但是当我使用 MaterialPageRoute 时该怎么做?

Posted

技术标签:

【中文标题】我想导航到另一个页面并使用 Firestore 数据进行解析,但是当我使用 MaterialPageRoute 时该怎么做?【英文标题】:I want to Navigate to another page and parse with firestore data but how do I do that when I am using MaterialPageRoute? 【发布时间】:2021-09-24 15:57:48 【问题描述】:

我想从产品页面导航到 ProductDetail 页面,但我直接使用来自 firebase firestore 的数据。我在 MaterialPageRoute 中放入什么作为参数?我还使用 StreamBuilder 从 firebase 获取数据快照。 下面是代码。这是产品页面。

class PopularRecipes extends StatefulWidget 
  const PopularRecipes(Key key) : super(key: key);

  @override
  _PopularRecipesState createState() => _PopularRecipesState();


class _PopularRecipesState extends State<PopularRecipes> 
  final Stream _productStream =
      FirebaseFirestore.instance.collection('products').snapshots();
  @override
  Widget build(BuildContext context) 
    return Column(
      crossAxisAlignment: CrossAxisAlignment.start,
      mainAxisAlignment: MainAxisAlignment.start,
      children: [
        Padding(
          padding: const EdgeInsets.symmetric(vertical: 10.0, horizontal: 20),
          child: CustomText(
            text: 'Popular Recipes',
            size: 20,
          ),
        ),
        Container(
          height: 500,
          child: StreamBuilder(
              stream: _productStream,
              builder: (context, snapshot) 
                if (snapshot.data == null)
                  return Center(
                    child: CircularProgressIndicator(
                      backgroundColor: Colors.teal,
                    ),
                  );
                return ListView.builder(
                    itemCount: snapshot.data.docs.length,
                    itemBuilder: (context, index) =>
                        _popularWidget(context, snapshot.data.docs[index]));
              ),
        ),
      ],
    );
  

  Widget _popularWidget(BuildContext context, DocumentSnapshot document) 
    return Stack(
      children: [
        Container(
          margin: EdgeInsets.fromLTRB(40, 5, 20, 5),
          height: 160,
          width: double.infinity,
          decoration: BoxDecoration(
              color: Colors.white, borderRadius: BorderRadius.circular(20)),
          child: Padding(
            padding: const EdgeInsets.fromLTRB(100, 20, 10, 20.0),
            child: Column(
              crossAxisAlignment: CrossAxisAlignment.start,
              mainAxisAlignment: MainAxisAlignment.center,
              children: [
                Row(
                  mainAxisAlignment: MainAxisAlignment.spaceBetween,
                  crossAxisAlignment: CrossAxisAlignment.start,
                  children: [
                    GestureDetector(
                      onTap: () => Navigator.push(context,
                          MaterialPageRoute(builder: (_) => DetailsScreen())),
                      child: Container(
                        width: 160,
                        child: Text(
                          document['name'],
                          style: TextStyle(
                              fontSize: 19.0, fontWeight: FontWeight.w600),
                          overflow: TextOverflow.ellipsis,
                          maxLines: 2,
                        ),
                      ),
                    ),
                    Column(
                      children: [
                        CustomText(
                          text: 'Ush.',
                          size: 14,
                          color: Colors.grey,
                        ),
                        CustomText(
                          text: document['price'],
                        ),
                      ],
                    )
                  ],
                ),
                RatingBarIndicator(
                  rating: document['rating'].toDouble(),
                  itemBuilder: (context, index) => Icon(
                    Icons.star,
                    color: Colors.amber.shade200,
                  ),
                  itemCount: 5,
                  itemSize: 15.0,
                  unratedColor: Colors.grey.shade300,
                  direction: Axis.horizontal,
                ),
                SizedBox(
                  height: 10,
                ),
                Container(
                  height: 40,
                  child: ListView(
                    scrollDirection: Axis.horizontal,
                    children: [
                      Row(
                        children: [
                          for (var tag in document['tags'])
                            Container(
                              decoration: BoxDecoration(
                                borderRadius: BorderRadius.circular(6),
                                color: Colors.grey.shade200,
                              ),
                              margin: EdgeInsets.only(right: 4),
                              child: Padding(
                                padding: const EdgeInsets.symmetric(
                                    horizontal: 8.0, vertical: 6),
                                child: Text(
                                  tag.toString(),
                                  style: TextStyle(
                                    fontSize: 14,
                                  ),
                                  textAlign: TextAlign.center,
                                ),
                              ),
                            )
                        ],
                      ),
                    ],
                  ),
                ),
              ],
            ),
          ),
        ),
        Positioned(
          top: 10,
          left: 20,
          bottom: 10,
          child: GestureDetector(
            onTap: () => Navigator.push(
                context, MaterialPageRoute(builder: (_) => DetailsScreen())),
            child: ClipRRect(
              borderRadius: BorderRadius.circular(20),
              child: Image.network(
                document['image'],
                width: 110,
                fit: BoxFit.cover,
              ),
            ),
          ),
        )
      ],
    );
  

这是当我单击特定产品卡时想要转到的 DetailsS​​creen 页面。

class DetailsScreen extends StatefulWidget 
  const DetailsScreen(Key key) : super(key: key);

  @override
  _DetailsScreenState createState() => _DetailsScreenState();


class _DetailsScreenState extends State<DetailsScreen> 
  @override
  Widget build(BuildContext context) 
    return Text(document['name']);
  

在使用 firebase 数据时,如何使用 MaterialPageRoute 将数据从上一页传递到详细信息页面?谢谢。

【问题讨论】:

【参考方案1】:

在您的 DetailsScreen 页面中添加产品变量

class DetailsScreen extends StatefulWidget 
  final DocumentSnapshot product;
  const DetailsScreen(Key key, @required this.product) : super(key: key);

  @override
  _DetailsScreenState createState() => _DetailsScreenState();


class _DetailsScreenState extends State<DetailsScreen> 
  @override
  Widget build(BuildContext context) 
    return Text(widget.product['name']);
  

onTap里面:

GestureDetector(
  onTap: () => Navigator.push(context,
     MaterialPageRoute(builder: (_) => DetailsScreen(document))), //pass the product

【讨论】:

我想知道,如果它是一张地图,我会用什么? final Map&lt;dynamic, dynamic&gt; someName; 或者你可以定义类型&lt;String, String&gt;&lt;String, int&gt;等。

以上是关于我想导航到另一个页面并使用 Firestore 数据进行解析,但是当我使用 MaterialPageRoute 时该怎么做?的主要内容,如果未能解决你的问题,请参考以下文章

如何使用 StreamBuilder 从一页导航到另一页

按下按钮并成功重定向到另一个页面后,如何禁用导航栏链接?

通过 Angular js 在 index.html 页面中将一个页面导航到另一个页面

[ViewPager - 如何使用按钮从一个页面导航到另一个页面?

如何导航到另一个页面而不会弹出抽屉?

Oracle Apex 页面在导航到另一个页面并返回后无法获取数据