【问题标题】:Passing data from page to page在页面之间传递数据
【发布时间】:2011-02-10 04:47:23
【问题描述】:

我正在寻找有关如何在页面之间传递数据的最佳实践。

在页面 A 中,我有一个触发页面 B 的按钮。
在页面 B 我有 6 个文本框,允许用户输入信息。 当用户完成后,点击一个按钮将他们带回页面 A。

我想将该数据传递回页面 A。

我看到了以下建议:

  • 构建 XML 文档并保存到独立存储中
  • 使用 App 类在属性中存储信息
  • 像查询字符串一样传递它

我正在寻找最佳实践。有没有一种是 Microsoft 推荐的,或者是公认的最佳方法?

谢谢

【问题讨论】:

    标签: windows-phone-7


    【解决方案1】:
    PhoneApplicationService.Current.State["yourparam"] = param
    NavigationService.Navigate(new Uri("/view/Page.xaml", UriKind.Relative));
    

    然后在其他页面中简单地

    var k = PhoneApplicationService.Current.State["yourparam"];
    

    【讨论】:

      【解决方案2】:

      我个人会将在页面 B 上输入的值存储在页面 A 也可以访问的模型(对象)中。

      根据您第二次导航到页面 A 的方式,以下一项或多项可能有助于理解页面之间的传递值:

      How to pass the image value in one xaml page to another xaml page in windows phone 7?

      Passing a complex object to a page while navigating in a WP7 Silverlight application

      How to pass an object from a xaml page to another?

      How to pass a value between Silverlight pages for WP7?

      How do I navigate from one xaml page to another, and pass values?

      【讨论】:

        【解决方案3】:

        您可以考虑使用 MVC:让您的 App 成为控制器,将所有数据存储在模型中,页面只是包含纯 UI 逻辑的视图。在这种情况下,您的页面是画家,并且您传递模型对象。这样可以很好地隔离业务逻辑和 UI,以便您轻松修改它们。

        顺便说一句,Silverlight 和 XAML 是 MVC 的绝佳工具,因此自然而然地匹配。

        【讨论】:

        • 是否有一个非常简单的例子说明我如何使用 MVC 和 WP7 做这样的事情?
        • 我没有一个非常简单的示例,但我只是启动了“数据绑定应用程序”模板并仔细观察它,直到我看到它是如何工作的。
        • 这可能会对你有所帮助(虽然它是在 ASP 中,但它实际上很好地演示了 MVC)agilewarrior.wordpress.com/2010/09/18/…
        • @PtG - 这实际上是一个非常好的演示。甚至海报也承认这是很多工作。但这是一个好的开始。谢谢你的链接。
        【解决方案4】:

        这里有几件事在起作用。首先,如果/当用户使用返回按钮而不是您的按钮返回页面 A 时,是否交换了文本框中的信息(返回 = 取消,还是返回 = 确定?)

        也就是说,如果您使用的是 NavigationService.GoBack(您应该使用 NavigationService.Navigate 而不是 NavigationService.Navigate,因为如果您使用 Navigate 调用,重复点击后退键会给您的用户带来各种糟糕的用户体验) , 那么 QueryStrings 不是一个选项。因为页面在 WP7 Silverlight 导航系统中确实无法相互引用,所以您需要使用第 3 方来保存您的数据。为此,您可以转向 (a) 隔离存储(慢且重,但故障安全),(b) 使用 PhoneApplicationService.State 字典,或 (c) 使用某种全局属性,或者挂起应用程序对象,或使用静态/单例...

        请记住在执行此操作时注意 Tombstoning 行为 - 当 (a) 您在应用程序中导航到它 (b) 当您在页面 B 上完成工作时导航回它时,您的页面将处理 OnNavigatedTo 方法,或者(c) 您从该页面删除您的应用程序并使用返回键返回您的应用程序。

        抱歉,我没有给出更直接的答案——很大程度上取决于您的具体情况。在最一般的情况下,我强烈考虑在 PhoneApplicationService 上使用 App State Dictionary ...它是轻量级的、易于使用的,并且可以在墓碑中幸存下来。只需确保您的密钥是独一无二的即可。

        【讨论】:

        • 有没有办法清除状态?假设我想重新开始,而无需重新启动应用程序。
        【解决方案5】:

        如果您创建一个新的 Windows Phone 项目并使用 Windows Phone 数据绑定模板,您将完成大部分工作。

        您要做的是设置 ViewModel 以包含您应用的所有数据。您可以使用 IsolatedStorage 对这些数据进行序列化和反序列化,以便在应用程序会话和 Tombstoning 时保存这些数据。

        在模板中,您会注意到 MailViewModelItemViewModel。 MainViewModel 存储您的应用程序需要的所有数据,包括 ItemViewModel 的 ObservableCollection,而 ItemViewModel 代表您的应用程序的单个数据类型。

        在 DetailsPage.xaml 页面上,您需要将每个文本框数据绑定到 App.MainViewModel 项。如果您希望 ViewModel 在用户操作 DetailsPage.xaml 上的数据时立即更新,请将绑定设置为 TwoWay。您可以选择将 Binding 设置为 OneWay,然后使用 OK 按钮将更改写回 ViewModel 并保存到 IsolatedStorage。

        下面是 Binding 的示例:

        <TextBlock x:Name="ListTitle" Text="{Binding LineOne}" Margin="9,-7,0,0" Style="{StaticResource PhoneTextTitle1Style}"/>
        

        在这种情况下,LineOne 是 ItemViewModel 中的一个属性,当用户从 MainPage.xaml 中选择一个项目时,页面会从查询字符串中获取此数据。页面的 DataContext 决定了数据绑定信息的来源。

        这是 MainPage 将所选项目从 ViewModel 传递到 DetailsPage 的 sn-p。

        // Handle selection changed on ListBox
        private void MainListBox_SelectionChanged(object sender, SelectionChangedEventArgs e)
        {
            // If selected index is -1 (no selection) do nothing
            if (MainListBox.SelectedIndex == -1)
                return;
        
            // Navigate to the new page
            NavigationService.Navigate(new Uri("/DetailsPage.xaml?selectedItem=" + MainListBox.SelectedIndex, UriKind.Relative));
        
            // Reset selected index to -1 (no selection)
            MainListBox.SelectedIndex = -1;
        }
        

        这是 DetailsPage 如何获取所选项目的。

        protected override void OnNavigatedTo(NavigationEventArgs e)
        {
            string selectedIndex = "";
            if (NavigationContext.QueryString.TryGetValue("selectedItem", out selectedIndex))
            {
                int index = int.Parse(selectedIndex);
                DataContext = App.ViewModel.Items[index];
            }
        }
        

        使用上面的默认模板并提出任何其他问题。

        数据绑定和 ObservableCollection 的美妙之处在于,您只需更新数据,用户体验就会立即反映这些变化。这是因为对数据的任何更改都会触发一个事件:

        public string LineOne
        {
            get
            {
                return _lineOne;
            }
            set
            {
                if (value != _lineOne)
                {
                    _lineOne = value;
                    NotifyPropertyChanged("LineOne");
                }
            }
        }
        

        NotifyPropertyChanged() 将此信息广播到视图。

        【讨论】:

          【解决方案6】:

          您也可以保持简单并使用基本上是哈希表的 PhoneApplicationService.Current.State。如果您希望任何东西比应用程序更长寿,您将需要实现自己的编组与隔离存储。

          Omar 建议使用 Windows Phone 数据绑定模板可能是此页面上的最佳主意。它与我的建议相同,但你会以更长更陡峭的学习曲线为代价获得更好的结果(更可维护的代码)。

          我建议你按照我的方式做,然后再按照奥马尔的方式做。

          【讨论】:

            【解决方案7】:

            因为我是这样实现的..它是否正确我不知道..

            当您单击新闻列表页面时,它应该打开新闻详细信息页面。 我想将选定的新闻项目内容从新闻列表页面传递到新闻详细信息页面。

            新闻列表页面包含以下方法。

             protected override void OnNavigatedFrom(System.Windows.Navigation.NavigationEventArgs e)
                {
                    NewsDetailsPage newsDetailPage = (e.Content as NewsDetailsPage);
                    if (newsDetailPage != null)
                        newsDetailPage.SelectedNewsItem = SelectedNewsItem; //Contains the news details
                    base.OnNavigatedFrom(e);
                }
            

            在新闻详情页面中。你可以访问那个(SelectedNewsItem) 对象。

            这可能正确也可能不正确。

            【讨论】:

              【解决方案8】:

              一种选择是使用 Application.Resources:

              存储数据:

              Application.Current.Resources.Add("NavigationParam", customers);
              
              NavigationService.Navigate(new Uri("/Page2.xaml", UriKind.Relative));
              

              检索数据:

              var customers = (List<Customer>) Application.Current.Resources["NavigationParam"];
              

              这里有一篇博文详细描述了这一点:http://mikaelkoskinen.net/windows-phone-pass-data-between-pages-application-resources/(作者:我)

              【讨论】:

                猜你喜欢
                • 2011-02-08
                • 1970-01-01
                • 1970-01-01
                • 1970-01-01
                • 2018-01-06
                • 2016-11-10
                • 2011-04-02
                • 1970-01-01
                相关资源
                最近更新 更多