Most often when learning Microsoft’s Windows Presentation Foundation (WPF) you are provided with the standard technique of doing page navigation with the Forward and Back buttons.
For those who want a more fluid experience they are referred to the WPF Navigation Services, which provide an alternative form of page navigation and is the basis fro being able to develop complex WPF application that can load and unload pages at will. However, there is a minor caveat here.
In the case of page navigation with Navigation Services what is most proffered in terms of documentation is the use of a page URL such as with the following example…
frameMainFrame.NavigationService.Navigate(New Uri("Pages/CategoryManagement.xaml", UriKind.Relative))
In this case, we use the Navigation Services attached to a WPF frame component, which is fairly standard for doing page loads from a master menu. Using this technique will display a new page in a master window’s frame area.
However, we run into a problem if we need to do page refreshes of the same page based upon a selection of specific data from a component that exists in the master window’s frame space.
For example, if we load a page into a master window’s frame space that includes a tree-view component and a frame space within the page itself, we may want to change certain data in the same page that is supporting certain functionality in this sub-frame space based on selections from the tree-view component that would not be part of this sub-frame space. In this case we select from the tree-view for example, a node specified as a data category where new sub-nodes are to be added. To keep the user informed of the selected category node he or she may be working with we want to display the selected category description in the page itself.
Using the URL navigation method as shown in the code-snippet above will not do this other than on the first load of the expected page where the page loaded event will fire.
Subsequent selections on the tree-view nodes will not see any display updates to the current page in the sub-frame space for the simple reason is that once a page is loaded via a URL the WPF internals no longer see a requirement to reload the page since it is already in existence.
For people new to WPF, this can be a very frustrating experience when trying to build such complex forms of page loading. No doubt in such frustration many developers have sought answers in the MVVM design paradigm, which is often touted as the way to create such applications. However, this alternative only adds a lot of bloat to an application and is entirely unnecessary unless you want to achieve some form of “purity” of standardization in how you code your WPF applications.
Luckily there is a very simple solution to this issue, which takes advantage of a non-URL technique for loading pages. This technique simply assumes that all pages are objects\classes as they are and uses the New/new feature of object instantiation to force the page to re-fire its loading events each time the requested page is displayed anew.
Thus, we can remove the URL parameters from the frame Navigation Services and replace it with the following…
Dim loCategoryManagementItems As New CategoryManagementItems() framePageFrame.NavigationService.Navigate(loCategoryManagementItems)
As we can note from the code snippet above, the page we are instantiating as an object is CategoryManagementItems. And once we navigate to it to have it displayed, being a new object it will fire all the necessary load events to appear as if the page is being refreshed with any updated data we want displayed.
The way I described how this technique is used in an application I am currently implementing is most assuredly part of the WPF MVVM design pattern. However, having studied quite a number of tools that support this pattern I could not see the necessity to add yet another layer of abstraction, and some cases of substantial size, simply to do what can be easily done without it.
The problem is that WPF is not hard but that instead its documentation is so poorly designed and limited to such an extent towards the manner in which Microsoft and others hope people will use it that it appears that WPF has a very steep learning curve. To be sure WPF is not Windows Forms but neither is it rocket science and more accessible documentation would make this excellent foundation for developing desktop applications a far more accessible choice.
In this case, finding this solution took quiet a bit of research. Some would say that this technique should have been obvious to me and any other who have needed to use it. However, that is one of the issues that has plagued the Open Source Community since its inception and has now found its way into what should be credible technical documentation; the fact that most people can no longer take the time to create easy to understand documentation that covers the spectrum of how a product may be used. Instead today, we get such minimal amounts of credible documentation as to make many Open Source or freely available tools useless to many developers.
Hopefully however, the simple technique described here regarding page navigation will in fact make WPF somewhat more accessible for those that want to forego the complexities of the MVVM design pattern.