【问题标题】:Xamarin Forms and Prism Navigation historyXamarin Forms 和 Prism 导航历史
【发布时间】:2018-02-09 15:11:36
【问题描述】:

我正在 MVVM 架构中使用 Prism 框架开发 Xamarin.Forms 应用程序。 在每个页面中,我都使用 INavigationService 对象进行导航,如下所示:

_navigationService.NavigateAsync("PageB");

在应用程序的左下角,我有返回按钮,我可以返回页面。

我有这样的导航:

MainPage -> PageA -> PageB -> PageC -> PageD

当我在 PageD 中时,我需要一个跳转到 PageA 的按钮,但我需要保留部分导航历史记录,如下所示:

MainPage -> PageA

我该怎么做?

【问题讨论】:

    标签: c# mvvm xamarin.forms prism


    【解决方案1】:

    最后我用这段代码解决了问题:

    _navigationService.NavigateAsync("/NavigationPage/MainPage/PageA", null,false,false);
    

    我希望它对某人有用。

    【讨论】:

    • 你能告诉我你最初的导航是什么样子的吗?我面临同样的问题,但我仍然收到 "Cannot destroy NavigationPage" 异常。最初,我使用this.NavigationService.NavigateAsync("/NavigationRootPage/DevicesPage"); 导航到我的起始页面,稍后我尝试使用await NavigationService.NavigateAsync("/NavigationRootPage/DevicesPage/SettingsPage", null, false); 返回我的设置页面 - 仍然是同样的例外。
    • 好的,知道了。在这里使用 await 是错误的。由于您的答案是已接受的答案,您是否可以添加信息,等待调用 NavigateAsync 将导致上述异常?
    • 你不是在那里做一个绝对重定向吗?你正在重新创建你的整个导航 stacl
    【解决方案2】:

    使用相对导航。 如果您知道自己领先三页,则可以简单地导航到目标页面。

    // using 3x '..'
    _navigationService.NavigateAsync("../../..");
    
    /* 
    
    Current stack: MainPage -> PageA -> PageB -> PageC -> PageD
    
    ..          -> MainPage -> PageA -> PageB -> PageC
    ../..       -> MainPage -> PageA -> PageB
    ../../..    -> MainPage -> PageA  
    
    */
    

    您还可以向后导航四次,然后导航到创建以下导航堆栈的不同页面(基本上替换 PageA):

    _navigationService.NavigateAsync("../../../../AnotherPage"); // -> MainPage/AnotherPage
    

    【讨论】:

      【解决方案3】:

      NavigationService 一次只能处理从 NavigationStack 中弹出一个视图。这为您的方案留下了两种选择:

      1. _navigationService.NavigateAsync("/MainPage/PageA") 这会将您带回您想要的视图,但会重新创建 MainPage 和 PageA。

      2. 可能更好的选择是将 NavigationParameters 与 INavigatedAware 一起使用。为此,您的 Go Back 命令可能会执行类似的操作

        _navigationService.GoBackAsync(新的 NavigationParameters { { "goBackTo" : "PageA" } });

      然后您可以更新您的 ViewModel 以执行以下操作:

      public class PageBViewModel : BindableBase, INavigationAware
      {
          public const string Key = "PageB";
      
          public void OnNavigatedTo(NavigationParameters parameters)
          {
              switch(parameters.GetNavigationMode())
              {
                  case NavigationMode.Back:
                      var goBackTo == parameters.GetValue<string>("goBackTo");
                      if(!string.IsNullOrWhiteSpace(goBackTo) && goBackTo != Key)
                      {
                          _navigationService.GoBackAsync(parameters);
                          return;
                      }
                      break;
              }
          }
      }
      

      【讨论】:

      • 我尝试了第一个解决方案,但收到此异常:“无法销毁 Xamarin.Forms.NavigationPage。”
      • 您需要提供一个示例来演示该问题...如果您正在执行我作为选项 1 显示的操作,那么您正在重置 Application.MainPage
      • 我也尝试了第二种解决方案,但它不起作用。在第一页(例如 PageC 参数中存在参数“goBackTo”,在下一页(PageB)中,当我再次将其放入参数中时,该参数不存在。我还尝试创建一个新的 NavigationParameters 对象并放入里面有参数,但是第二跳就丢了,很奇怪。
      • 如果没有复制问题的样本,很难说发生了什么。我给出的任何一个例子都应该有效。
      • 更新:我尝试检查第二个登陆页面(PageB)中的参数。在 OnNavigatingTo 方法中变量存在,在 OnNavigatedTo 方法中它不存在。似乎它失去了这两个步骤之间的价值。
      【解决方案4】:

      您需要执行绝对导航。 这是通过在你的 uri 前面加上一个“/”来完成的。

      _navigationService.NavigateAsync("/MainPage/PageA")
      

      这将重置您的 App.MainPage

      ========================更新==================== =====

      您需要在 Container 中注册您的所有页面。 所以,请确保您的应用程序文件代码在我的代码下方:

      public partial class App : PrismApplication
      {
          public App(IPlatformInitializer initializer = null) : base(initializer) { }
          protected override void OnInitialized()
          {
              InitializeComponent();
              NavigationService.NavigateAsync("NavigationPage/MainPage");
          }
          protected override void RegisterTypes()
          {
              Container.RegisterTypeForNavigation<MainPage>();
              Container.RegisterTypeForNavigation<PageA>();
              Container.RegisterTypeForNavigation<PageB>();
              Container.RegisterTypeForNavigation<PageC>();
              Container.RegisterTypeForNavigation<PageD>();
              Container.RegisterType<ITsApiService, TsApiService>();
          }
      }
      

      【讨论】:

      • 我尝试过,但收到此异常:“无法销毁 Xamarin.Forms.NavigationPage。”
      • 我已经用代码 _navigationService.NavigateAsync("/MainPage/PageA") 更新了我的答案,请尝试并告诉我
      • 是的,我第一次尝试了这段代码,我收到了提到的异常
      • @TeoVr81,我已经更新了我的答案,请看看并告诉我。
      • 是的,所有页面都已注册。我没有RegisterType,不知道什么是ITsApiService和TsApiService。
      猜你喜欢
      • 2016-06-06
      • 2016-11-21
      • 2017-01-21
      • 1970-01-01
      • 2017-09-14
      • 2021-03-15
      • 2017-05-08
      • 2019-03-21
      • 1970-01-01
      相关资源
      最近更新 更多