2012-11-30 30 views
11

我正在將Windows應用商店應用轉換爲Windows Phone 8.對於WinRT,您可以在調用frame.navigate時將任何對象作爲參數傳遞。 (frame.navigate(type sourcePageType,object parameter))如何在Windows Phone 8的頁面之間傳遞非字符串參數?

導航似乎對windows phone有不同的作用,你可以通過調用uri來導航,如:frame.navigate(new uri(「mypage.xaml」,UriKind .Relative))

windows文檔注意到您可以通過將字符串添加到uri來傳遞字符串作爲參數。

是否有一種可接受的方式在頁面之間傳遞複合對象,而我還沒有找到?

+2

您可以用名稱保存在隔離存儲中,然後從其他頁面中取回。 –

+0

http://stackoverflow.com/questions/12444816/how-to-pass-values-parameters-between-xaml-pages/12444817#12444817 –

回答

0

我在我的應用程序中所做的是將某種標識符(索引,GUID,無論)作爲字符串傳遞,然後在要導航到的頁面的OnNavigatedTo()方法中查找該對象。所以這些對象將保存在ViewModel(或任何地方)中,您只需傳遞一個字符串即可。

0

我建議在兩個視圖模型之間使用服務代理。

首先,定義一個視圖模型定位器。在app.xaml的資源字典中創建此類的一個實例。將每個頁面的DataContext設置爲視圖模型定位器的屬性。一個例子見John Papa's blog

其次,使用GetAllItems()和GetItem(string id)等方法創建服務代理。在視圖模型定位器中創建此服務代理的實例。將此參考傳遞給兩個視圖模型。

第三,通過將DataContext轉換爲視圖模型類型,從第二個視圖訪問視圖模型。將導航參數傳遞給視圖模型,以便它可以調用GetItem並填充其屬性。

0

無法發送不是字符串的導航參數。我通常使用DataContractJsonSerializer來序列化我需要傳輸的數據(但要小心Uri長度限制)。 還記得使用Uri.EscapeDataString(參數)來轉義querystring參數中的字符。

0

正如@gregstoll所說,Windows Phone中最好的方法是發送一個標識符,然後利用你的App.ViewModel中的數據來訪問你想要的實際數據。 QueryString的長度有一些限制,而且絕大多數情況下,你真的不想強調這是限制。

如果您可以更多地瞭解您的項目情況,我們可以更好地幫助您確定採取的最佳路徑。

+4

這將是更好的評論 –

15

我結束了擴展的NavigationService類,如下所示:

public static class NavigationExtensions 
{ 
    private static object _navigationData = null; 

    public static void Navigate(this NavigationService service, string page, object data) 
    { 
     _navigationData = data; 
     service.Navigate(new Uri(page, UriKind.Relative)); 
    } 

    public static object GetLastNavigationData(this NavigationService service) 
    { 
     object data = _navigationData; 
     _navigationData = null; 
     return data; 
    } 
} 

然後你會打電話NavigationService.Navigate("mypage.xaml", myParameter);源頁面上,並在目標頁面調用var myParameter = NavigationService.GetLastNavigationData();的的OnNavigatedTo方法來獲取參數數據。

3

我想剛剛添加一個由Zik上面提供的偉大答案的VB.net版本。一旦我想出瞭如何將他的代碼翻譯成VB,我就立即進行了類似於WinRT/Windows 8的導航工作。

我創建了下面的代碼模塊:

Module NavigationExtensionsModule 

Sub New() 
End Sub 
Private _navigationData As Object = Nothing 

<System.Runtime.CompilerServices.Extension> _ 
Public Sub Navigate(service As NavigationService, page As String, data As Object) 
    _navigationData = data 
    service.Navigate(New Uri(page, UriKind.Relative)) 
End Sub 

<System.Runtime.CompilerServices.Extension> _ 
Public Function GetLastNavigationData(service As NavigationService) As Object 
    Dim data As Object = _navigationData 
    _navigationData = Nothing 
    Return data 
End Function 
End Module 

,然後導航到另一個頁面這樣的:

NavigationService.Navigate("pagename.xaml", ObjectToPassToThePage) 

最後,讓該對象在我的其他頁面,在OnNavigatedTo子:

ThisPageData = NavigationService.GetLastNavigationData() 

Me.DataContext = ThisPageData 

感謝Zik的實際答案。

0

MSDN概述了3種在頁面之間傳遞非字符串參數的方法。這些包括:自定義導航擴展,靜態屬性和JSON +獨立存儲。從Microsoft採取代碼:

/// <summary> 
    /// Custom Navigation Extensions. 
    /// </summary> 
    /// <param name="sender"></param> 
    /// <param name="e"></param> 
    private void btnMethod1_Click(object sender, RoutedEventArgs e) 
    { 
     NavigationService.Navigate("/Result.xaml?name=1", listString); 
    } 


    /// <summary> 
    /// Static properties 
    /// </summary> 
    /// <param name="sender"></param> 
    /// <param name="e"></param> 
    private void btnMethod2_Click(object sender, RoutedEventArgs e) 
    { 
     App.ObjectNavigationData = listString; 
     NavigationService.Navigate(new Uri("/Result.xaml?name=2", UriKind.Relative)); 
    } 


    /// <summary> 
    /// Json + IsolatedStorage 
    /// </summary> 
    /// <param name="sender"></param> 
    /// <param name="e"></param> 
    private void btnMethod3_Click(object sender, RoutedEventArgs e) 
    { 
     string filePath = "objectData"; 


     using (IsolatedStorageFile isolatedStorage = IsolatedStorageFile.GetUserStoreForApplication()) 
     { 
      if (isolatedStorage.FileExists(filePath)) 
      { 
       isolatedStorage.DeleteFile(filePath); 
      } 


      using (IsolatedStorageFileStream fileStream = isolatedStorage.OpenFile(filePath, FileMode.Create, FileAccess.Write)) 
      { 
       string writeDate = string.Empty; 


       // Json serialization. 
       using (MemoryStream ms = new MemoryStream()) 
       { 
        var ser = new DataContractJsonSerializer(typeof(List<string>)); 
        ser.WriteObject(ms, listString); 
        ms.Seek(0, SeekOrigin.Begin); 
        var reader = new StreamReader(ms); 
        writeDate = reader.ReadToEnd(); 
       } 


       // Save to IsolatedStorage. 
       using (StreamWriter writer = new StreamWriter(fileStream)) 
       { 
        writer.WriteLine(writeDate); 
       } 
      } 
     } 


     NavigationService.Navigate(new Uri("/Result.xaml?name=3", UriKind.Relative)); 
    } 
2

如果使用MVVM架構,那麼你可以傳遞字符串或使用Messenger的註冊後,任何價值。用一個字符串(比如消息)變量創建一個模型類(比如說PageMes​​sage)。你想通過從homepage.xaml字符串newpage.xaml,然後在homepage.xaml只需發送郵件這樣

Messenger.Default.Send(new PageMessage{message="Hello World"}); 

在newpage.xaml,你應該這樣註冊的使者,

Messenger.Default.Register<PageMessage>(this, (action) => ReceiveMessage(action)); 

private object ReceiveMessage(PageMessage action) 
{ 
    string receivedMessage=action.message; 
    return null; 
} 
0
Yes there is a way to use a complex object in different pages in wp8 or wp7. You can use complex objects between pages by IsolatedStorageSettings. 

IsolatedStorageSettings AppSettings = IsolatedStorageSettings.ApplicationSettings; 

// to save an object in isolatedstoragesettings 
if (!AppSettings.Contains("ObjectKey")) 
     AppSettings.Add("ObjectKey", Your object value); 
else 
     AppSettings["ObjectKey"] = Your object value; 

// to retrieve value of an object from isolatedstoragesettings 
if(AppSettings.Contains("ObjectKey")) 
    { 
    var objectValue = (Cast object to type)AppSettings["ObjectKey"]; 
    //Remove 
    AppSettings.Remove("ObjectKey"); 
    }