导航到新屏幕时无法访问提供程序

Posted

技术标签:

【中文标题】导航到新屏幕时无法访问提供程序【英文标题】:Provider not accesable when Navigate to new screen 【发布时间】:2020-02-05 15:14:34 【问题描述】:

有一个问题,我现在坐了几天。 有一个应用程序:

根据 AUTH 状态,显示“LoginScreen”或“MainScreen”。

在 MainScreen 中,我设置了底部导航(HomeScreen、ShoppingScreen、MyFavorites)

我还使用 MultiProvider 在那里设置了我的 StreamProviders(那些依赖于 Auth) 当我使用 Provider.of(context) 时,在 HomeScreen 上它的工作原理应该是这样的

但是当我使用时:

`Navigator.push(
  context,
  MaterialPageRoute(
    builder: (_) => ProfileScreen(),
  ),
);

` 并在此处使用 Provider.of(context) 我得到“找不到正确的 Provider..above this...widget

我阅读了一些关于这方面的问题,并且解决方案是在 MaterailApp 上方取消提供程序,在我的情况下我不能这样做,因为我只能在 Auth 成功后设置这些。

尝试将上下文(从 HomeScreen)传递给 ProfileScreen(通过构造函数)并且可以工作,但是当 UserData 的值更改时,它没有更新屏幕(猜测是因为不同的“上下文”)

我在这里做错了什么,有什么想法吗?:S

【问题讨论】:

【参考方案1】:

提供者是“范围内的”。

这意味着如果将它们放置在屏幕内,则无法在该屏幕外访问它们。

这意味着如果提供程序是作用域但需要在创建它的路由之外访问,我们有两种解决方案:

取消范围提供程序。这涉及将提供者移动到需要获取值的两个小部件的共同祖先。

如果这两个小部件位于两个不同的路由上,那么它基本上意味着“将提供程序移到MaterialApp/CupertinoApp 上方。

手动将提供程序传递到新屏幕(使用Navigator.push时需要)

我们的想法是,我们有 两个 提供者,而不是 一个 提供者,它们都使用与此处解释的相同的值,请参阅 How to scope a ChangeNotifier to some routes using Provider? 以获取实际示例。

对于Navigator.push,可能如下所示:

final myModel = Provider.of<MyModel>(context);
Navigator.push(
  context,
  MaterialPageRoute(
    builder: (_) =>
      ChangeNotifierProvider.value(
        value: myModel,
        child: MyScreen(),
    ),
  ),
);

【讨论】:

TY 非常感谢@Remi 完美信息 - 也想给你打勾,因为你和 Kushagra 的回答都对我有很大帮助,所以我只选择第一个:S【参考方案2】:

请确保您的应用程序的根小部件是Provider 小部件,它应该是MaterialWidget 的父级。如果已经是这种情况,我将需要您的代码进行调查。像这样的

class AppState 
 User loggedInUser;

 bool get isLoggedIn 
  return loggedInUser != null;
 

 // Other states as per the requirements
 // ...

【讨论】:

嗨,不,不是 - 所以你在那里是正确的 - 但我有不能在应用程序根目录中声明的 StreamProviders,即“Stream”,可以在 AUTH 成功后添加为提供者意味着它不会在应用程序根目录中声明......我该如何解决?: 在这种情况下,我认为您的应用程序应该公开一个根状态,该状态应该包含所有后续状态,如loggedInUserPosts 等(根据用例)来自上方的父 StreamProvider MaterialWidget 直到用户没有注册authloggedInUser 密钥可以为空。 这就像我理解但我仍然不...:)。你的意思是我应该为每个身份验证状态有两个单独的材料小部件?-或者我错过了理解所有内容?:S 不,你不会有两个 Material 小部件,只是简单地说上面的解释。将 StreamProvider 保持在所有的根目录,就像我提到的那样,在用户未通过身份验证之前,这些值将为 null,并且在用户登录后更新状态中的这些值。 hmmm 我想*我理解(我的意思是:我希望我理解:)) - 我会尝试回馈给你,当然标记你的答案(也许明天虽然- 远离电脑自动取款机)感谢您的时间/帮助

以上是关于导航到新屏幕时无法访问提供程序的主要内容,如果未能解决你的问题,请参考以下文章

在按钮单击 SwiftUI 时导航到新屏幕

根据对提供值的更改更改 UI

nvda关闭时无法使用回车键单击

单击图标时无法导航到新页面

iOS 可访问性无法识别屏幕上的任何内容

使用React-Native进行入职后导航到新页面