If you have programed against any of Microsoft’s Xaml based user interface frameworks then you might have heard about the MVVM (Model-View-ViewModel) pattern. One of the benefits of this pattern is the separation of the view from the view model. All of the logic lives in the view model which is then bound to the view. This separation allows for rapid revolutions of the visual components. All that is needed is to recreate the Xaml and go. What is you do that across Xaml technologies? As of now Microsoft has three Xaml based UI Frameworks, WPF, Silverlight, WP7 (which is of course is a variant of Silverlight 3). There is even a hint of a new/revamped Xaml Framework in Windows 8.
I have recently started to look at reusing a Silverlight 4 ViewModels in a WP7 applications. I figured this would probably be the easiest place to start since they are both Silverlight. I was recently asked what would it take to make a component reusable across Silverlight and WPF. That figures right into my ViewModel sharing research. I will start by looking at different ways to share code across all three frameworks. In a future post I will explore ways to reuse Xaml.
Let’s start off by examining the challenges associated with this task. The first challenge is the fact that they are three different frameworks that are designed for three different use cases. That means that any reusable code would have to be coded to the lowest common denominator. In this case it means WP7.
For this post I don’t have any working code to share but I have been trying a few things. One of the first things I ran into was in the System.ServiceModel namespace. Each framework handles calling web services differently. Silverlight and WP7 can only make calls asynchronously and WPF defaults to synchronous calls. I am still working out how I want to handle this. There are other challenges too, take third party libraries for instance.
Another challenge that you are going to face is keeping consistent namespaces across the frameworks. If your organization has a strict naming convention then this could become a challenge. Luckily you control what your namespaces are but it can become quite hairy if you are not careful.
Third Party Libraries are usually compiled against specific runtimes. The third party library that I consistently use when working with Xaml is the MVVM Light Toolkit. Luckily the MVVM Light Toolkit is compiled against the different Xaml runtimes and the functionality is consistent across the frameworks. But with other libraries you may not be as lucky. Now it is time to talk about the different options available for reuse.
Copy and Paste
The most basic method is copy and paste. This is a quick and dirty solution. First you create a file that works in one framework. Then you create that same file in the other projects copying the code from the original class to the new class. The up side to this method is that you can tweak the code for each framework. But red flags should be waving and alarms sounding.
Copy and paste architecture is NOT the key to a reusable strategy. There is no means to update the code once it resides in each project since the code is not linked together. Any change would need to be propagated across the different files. Which may be ok if there is one “shared” file and more than that and you are asking for a nightmare. In other words there is no maintainability or scalability with this option.
Add As a Link
The next option I explored is add linked files to the projects. For this method you create a class in on project and then add it as a link to another project. In the “Add Existing Items” dialog you can navigate to the file you want to link and select “Add As Link” from the “Add” button dropdown.
You can tell the file is linked by the icon of the file in the linked project. With this solution there is only one physical copy of the file. Each project then compiles the file against the proper framework. The up side to this approach is that there is only one file to maintain. On the downside namespaces can become an issue. You may also have to use conditional compile tags if modifications are needed. Conditional tag will allow for the use of different using statements when it comes to third part libraries as long as the internal namespaces are consistent.
Portable Library Tools
The final method I looked at was the Portable Library Tools from Microsoft. The Portable Library tools
is a new Visual Studio add-in from Microsoft that enables you to create C# and Visual Basic libraries that run on a variety of .NET-based platforms without recompilation. – Visual Studio Gallery Description
The add-in can be downloaded from the Visual Studio Gallery. This method allows you to create a class library that can run against many of the .Net runtimes. To accomplish this the class library compiles against a very restrictive version of the .Net framework. This can be a challenge when planning out what to include in a reusable library.
Since this project is still in the CTP/Beta phase not all of the available frameworks libraries have been included. Most notably there is no odata support so you cannot create a reusable odata access library with this tool. According to the Q and A tab in the gallery there is a product road map that plans to include more of the framework.
On a side note it looks like this tool is part of the developer story for Windows 8. Take a look at the response, on the Q and A Tab, to the “System.Threading.Thread problem” question.
We needed to remove explictly thread creation for a reason that we’re not ready to discuss yet (ask me again in 3 months).
Note that the Build Windows Conference is three months away.
Sorry there is not any working code for this post. I am still mulling over how I want to accomplish my goals. I wanted to put this together to organize my thoughts and get feedback from others who have tried for reusable nirvana. One of the lessons that I have learned so far is be picky about what you include. The different frameworks kind of take care of that for you by restricting what libraries are available.
The other early lesson I have garnered from my investigation is that you have to be more aware of Framework updates that could break your reusable code. There is a lot of churn happening right now with Xaml frameworks (Silverlight 5 and WP7.1). New releases may break what you are doing but they may also bring in more components that can be reusable!
Next I will be looking to see how compatible Xmal is across the different frameworks. The ultimate goal is to develop a strategy that allows components to be used across Silverlight, WPF and Windows Phone.