Flutter Provider,当他的参数改变时更新 StreamProvider

Posted

技术标签:

【中文标题】Flutter Provider,当他的参数改变时更新 StreamProvider【英文标题】:Flutter Provider, update StreamProvider when his parameter changes 【发布时间】:2021-02-07 11:28:49 【问题描述】:

我一直在开发这个 Flutter 应用程序,其中一个小部件需要从 firestore 数据库中读取对象列表。

为此,我有一个特定对象的模型(称为 Polizza)。

我有一个名为 DatabaseService 的类,其中包含获取 Streams 的方法。

在这种情况下,这是我用来查询数据库并获取流的方法:

Stream<List<Polizza>> streamPolizze(String id, String filter = '') 
    var ref = _db
        .collection('polizze')
        .doc(id)
        .collection('elenco')
        .orderBy('indice');

    if (filter.isNotEmpty) 
      List<String> list = filter.split(' ').map((e) => e.toUpperCase());
      ref = ref.where('indice', arrayContainsAny: list);
    

    return ref.limit(10).snapshots().map(
        (list) => list.docs.map((doc) => Polizza.fromFirestore(doc)).toList());
  

在父窗口小部件中,我使用 StreamProvider 让他的孩子能够访问 Polizza 列表:

@override
  Widget build(BuildContext context) 
    var user = Provider.of<User>(context);
    var filter = Provider.of<FilterPolizze>(context);
    return MultiProvider(
      providers: [
        StreamProvider(create: (BuildContext context) => DatabaseService().streamPolizze(id: user.uid))
      ],
      child: ...
    );
  

成功了。

但现在我想对查询应用过滤器。 为此,我构建了一个简单的 TextField 小部件,它能够通过 ChangeNotifierProvider 为我提供过滤器值。 这很好用,事实上我可以从 Provider.of(context) 读取过滤器和他的更新。 FilterPolizze 是我为过滤器构建的 Object 类型。

我尝试过这样更新 StreamProvider:

StreamProvider(create: (BuildContext context) => DatabaseService().streamPolizze(id: user.uid, filter: filter.value))

但它似乎没有重建。

如果 StreamProvider 的其中一个参数发生变化,我如何通知 StreamProvider 进行自我重建?

【问题讨论】:

我不认为它对你有用,我会将收到的数据分配给一些 changenotifireprovider 的值并在重建某些页面或小部件之前对其进行过滤。分配将在流中进行,过滤将在使用 changeNotifier 重建页面或小部件之前进行。 你指的是 Pieter van Loon 的回答吗? 【参考方案1】:

SteamProvider 一个Key,当过滤器更改时您会更改它。 因此,例如使用值为'polizze$filter.value'的键

【讨论】:

我不清楚为什么要添加密钥。如果这种情况发生变化,它会触发小部件更新吗? 该键将发出信号,表明您已为它提供了与以前不同的流提供程序,因此该小部件将从头开始构建,删除任何先前的状态,因此应再次调用创建 它工作了,但是由于小部件被重建,它会导致很多其他问题。例如,我失去了对过滤器文本字段的关注,过滤器本身被清理了。 我解决了这个问题,方法是将我有兴趣重建的部分包装在一个新的小部件中,并将提供程序移动到那个新的小部件。这样我只重建必要的东西。我会考虑将您的答案标记为解决方案。

以上是关于Flutter Provider,当他的参数改变时更新 StreamProvider的主要内容,如果未能解决你的问题,请参考以下文章

Flutter:如何用 Provider 播放动画?

Flutter - Provider 变量更改时触发导航

Flutter + Firebase 手机 OTP 不适用于其他国家/地区

从 Selector 访问多个字段(在 Flutter 中使用 Provider 状态管理时)?

Provider 调用 notifyListeners() 时 Flutter View 不更新视图

有啥方法可以用 Provider 在 Flutter 中全局登录学生吗?