9 Comments

Until we get the great frameworks like Caliburn.Micro up-to-date with WinRT, one possible solution for doing navigation when using MVVM pattern is to wrap the Frame-object. Here’s a simple implementation (which could be further enhanced by extracting an interface from it): 

public class NavigationService
    {
        readonly Frame frame;

        public NavigationService(Frame frame)
        {
            this.frame = frame;
        }

        public void GoBack()
        {
            frame.GoBack();
        }

        public void GoForward()
        {
            frame.GoForward();
        }

        public bool Navigate<T>(object parameter = null)
        {
            var type = typeof(T);

            return Navigate(type, parameter);
        }

        public bool Navigate(Type source, object parameter = null)
        {
            return frame.Navigate(source, parameter);
        }
    }

The NavigationService can be initialized by passing in the root frame, for example in the App.xaml.cs where the root frame is created: 

// Create a Frame to act navigation context and navigate to the first page
            var rootFrame = new Frame();
            App.NavigationService = new NavigationService(rootFrame);

            rootFrame.Navigate(typeof(BlankPage));

If you’re using some container to create your view models, the NavigationService-instance can be registered into it as a singleton. If you’re using a simple ViewModelLocator without a container, the NavigationService can be added as a property to the App-class and it can be accessed when creating the view models. In either case, the NavigationService should be passed to the VM through the constructor, after which navigation from a view model is a straightforward task.

Here’s an example of a view model which uses the NavigationService to navigate forward to a new page:

public class BlankPageViewModel
    {
        private readonly NavigationService navigation;

        public BlankPageViewModel(NavigationService navigation)
        {
            this.navigation = navigation;
        }

        public DelegateCommand GoToNextPage
        {
            get
            {
                return new DelegateCommand(x => navigation.Navigate<SecondPage>(), x => true);
            }
        }
    }

The BlankPageViewModel is constructed inside the ViewModelLocator-class: 

public BlankPageViewModel BlankPageViewModel
        {
            get
            {
                return new BlankPageViewModel(App.NavigationService);
            }
        }

A sample app containing two pages and the NavigationService-wrapper can be found from GitHub. The sample app also shows a basic implementation of the view model locator.

Comments

Comment by link vao dafabet

link vao dafabet...

Food cravings may occur when someone tries to quit smoking due to increased anxiety....

Comment by max air nike

max air nike...

Hey would you mind letting me know which web host you're using? I've loaded your blog in 3 different web browsers and I must say this blog loads a lot faster then most. Can you suggest a good hosting provider at a reasonable price? Thank you, I appre...

Comment by Oakley Sunglasses Outlet

Oakley Sunglasses Outlet...

There are some interesting deadlines in this article but I donꊰ know if I see all of them center to heart. There may be some validity but I will take maintain opinion until I....

Comment by cheap oakley sunglasses

cheap oakley sunglasses...

as a result of I found it for him.. smile. So let me reword that: Thnx for the deal with! But yeah Thnkx for spending the time to debate this....

Comment by Michael Kors Watches

Michael Kors Watches...

This is the best weblog for anyone who wants to search out out about this topic. You realize a lot its nearly laborious to argue....

Comment by ugg sale

ugg sale...

You made some respectable points there. I seemed on the web for the problem and located most individuals will go along with with your website....

Comment by Michael Kors Purses Outlet

Michael Kors Purses Outlet...

you may have a great weblog here! would you like to make some invite posts on my blog?...

Comment by Stian

This is way overdue actually, but cheers!
You should check for CanGoBack & CanGoForward though.

Stian
Comment by Andy Charalambous

Should you be referencing view related types in the viewmodel? SecondPage is presumably a XAML Page sub-class - my impression of MVVM is that it should not be tightly coupled to any view related types. I like this idea in general, my $.02 would be that NavigateTo should probably take a string that is a label for what the NavigationService should navigate to - and all concrete references to XAML view types be restricted to it, not the viewmodel

Andy Charalambous