1. Windows Store apps made easy with Prism and Prism project templates
2. Views, ViewModels and navigation
Previously described application is unrealistically simple. In reality, your apps will include more than one page and you will need some navigation mechanism to help users to browse between these pages.
Adding new pages
In addition to the project templates, Prism extension provides several item templates – Page View, View Model, Model and others.
Use “Add New Item” dialog to add new Page View and View Model to Views and ViewModels folders correspondingly. Name them DetailsPage
and DetailsPageViewModel
.
Next step is to set new DetailsPageViewModel
as a data context for the DetailsPage
. You can setup context manually, but Prism provides a handy ViewModelLocator
class to do it semi-automatically. Why not fully automatically? Because you still need to setup ViewModelLocator.AutoWireViewModel
property for DetailsPage
.
<prism:VisualStateAwarePage
x:Name="pageRoot"
x:Class="PrismApp.ViewModels.DetailsPage"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:local="using:PrismApp.ViewModels"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:prism="using:Microsoft.Practices.Prism.StoreApps"
mc:Ignorable="d"
prism:ViewModelLocator.AutoWireViewModel="True">
...
</prism:VisualStateAwarePage>
How it works
For wiring Pages with ViewModels Prism framework uses a convention over configuration approach. Class names as well as Views and ViewModels folders are parts of this convention.
By setting AutoWireViewModel
for DetailsPage
to true
we instruct ViewModelLocator
to search DetailsPageViewModel
in ViewModels folder. If such class is found, Prism will construct it and use as a data context for the DetailsPage
.
Sounds logical, but let us look at the DetailsPageViewModel
code.
using Microsoft.Practices.Prism.StoreApps;
using Microsoft.Practices.Prism.StoreApps.Interfaces;
namespace PrismApp.ViewModels
{
public class DetailsPageViewModel : ViewModel
{
private INavigationService _navigationService;
public DetailsPageViewModel(INavigationService navigationService)
{
_navigationService = navigationService;
}
}
}
The class does not have default parameterless constructor, will Prism be able to construct the object? Actually no: if you will try to run the code as it is, ViewModelLocator
will throw an exception telling us that an appropriate constructor was not found.
As you may expect, there is a way to instruct Prism which constructor to use. We can override App. OnInitialize
method and properly configure ViewModelLocator
.
using Microsoft.Practices.Prism.StoreApps;
using PrismApp.ViewModels;
using PrismApp.Views;
using Windows.ApplicationModel.Activation;
namespace PrismApp
{
sealed partial class App : MvvmAppBase
{
public App()
{
InitializeComponent();
}
protected override void OnLaunchApplication(LaunchActivatedEventArgs args)
{
NavigationService.Navigate("Main", null);
}
protected override void OnInitialize(IActivatedEventArgs args)
{
ViewModelLocator.Register(typeof(MainPage).ToString(),
() => new MainPageViewModel(NavigationService));
ViewModelLocator.Register(typeof(DetailsPage).ToString(),
() => new DetailsPageViewModel(NavigationService));
}
}
}
Navigation
With the object provided in constructor and implementing INavigationService
interface, navigation is easy.
using Microsoft.Practices.Prism.StoreApps;
using Microsoft.Practices.Prism.StoreApps.Interfaces;
namespace PrismApp.ViewModels
{
public class MainPageViewModel : ViewModel
{
private INavigationService _navigationService;
public MainPageViewModel(INavigationService navigationService)
{
_navigationService = navigationService;
}
public void GoToDetails()
{
_navigationService.Navigate("Details", null);
}
...
}
}
Navigation service use the same Views/ViewModels convention as ViewModelLocator
. First parameter in Navigate()
function defines target page name, service constructs full class name by adding “Page” suffix. Second parameter allows you to pass some data to the next page.
This concludes Prism Views and ViewModels discussion. Next post will talk about additional configuration techniques.
blog comments powered by Disqus