Silverlight / WPF, MVVM and Dependencies

As promised I will write some technical Windows Phone related things. I will start off with a MVVM specific framework I have developed during some projects.

I like MVVM. The whole Idea of separating the view logic from the view is awesome and really fits into the Silverlight / WPF (I will refer to them as XAML from now on) world. As with every technology there are ups and downs and so has XAML its own downs. Two of them I want to explain here and show solutions for them.

String parameter passing for PropertyChanged events.

This problem will be gone with the next .NET version. The problem is that the compiler doesn’t check string contents :). Lets assume you have the following class:

public class ContactViewModelTraditional : INotifyPropertyChanged
{
	private string _Name;
	public string Name
	{
		get
		{
			return _Name;
		}
		set
		{
			bool changed = value != _Name;
			_Name = value;
			if (changed)
				OnPropertyChanged("Name");
		}
	}

	public event PropertyChangedEventHandler PropertyChanged;

	private void OnPropertyChanged(string propertyName)
	{
		if (PropertyChanged != null)
			PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
	}
}

If you now want to change the property name „Name“ to something else you have to think of the string parameter for the OnPropertyChanged method. If you forget to rename this string the compiler will not complain. You can see your error only at runtime (if you are lucky).

To solve this issue Microsoft has introduced the [CallerMemberName] attribute to make the parameter generated automatically.
For now, as we don’t have such a feature, I have chosen to (mis)use Lambda expressions to pass the property name. This way costs performance but ensures that the property name is correct or the compiler will detect it.

The class from above would look like this using my approach (I will explain the function call to „SetPropertyValue“ later):

public class ContactViewModelTraditional : INotifyPropertyChanged
{
	private string _Name;

	public string Name
	{
		get
		{
			return _Name;
		}
		set
		{
			this.SetPropertyValue(p => p.Name, ref _Name, value);
		}
	}

	public event PropertyChangedEventHandler PropertyChanged;

	private void OnPropertyChanged(string propertyName)
	{
		if (PropertyChanged != null)
			PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
	}
}

The key in this example is the setter of the Name property. Here you can see that the name of the property gets passed as a Lambda expression. The „SetPropertyValue“ method then has to get the name from the lambda expression and pass it to the „OnPropertyChanged“ method.

Property dependencies and raising the correct PropertyChanged events

Another big problem arises when the ViewModel structure gets more complex and / or if properties are based on other properties and only change implicitly.

So lets assume we have a simple ViewModel and this ViewModel contains a ContactViewModel. We want a property „CurrentContactNameString“ on the ViewModel that returns the Name of the current contact or the string „No Contact selected“ if there is no current contact.

The ViewModel would look like this:

public class MainViewModelTraditional : INotifyPropertyChanged
{
	private ContactViewModelTraditional _CurrentContact;
	public ContactViewModelTraditional CurrentContact
	{
		get
		{
			return _CurrentContact;
		}
		set
		{
			bool changed = _CurrentContact != value;
			if (changed)
			{
				if (_CurrentContact != null)
					_CurrentContact.PropertyChanged -= CurrentContact_PropertyChanged;
				_CurrentContact = value;
				if (_CurrentContact != null)
					_CurrentContact.PropertyChanged += CurrentContact_PropertyChanged;
				OnPropertyChanged("CurrentContact");
				OnPropertyChanged("ContactNameString");
			}
		}
	}

	void CurrentContact_PropertyChanged(object sender, PropertyChangedEventArgs e)
	{
		if (e.PropertyName == "Name")
			OnPropertyChanged("ContactNameString");
	}

	public string CurrentContactNameString
	{
		get
		{
			if (CurrentContact != null)
				return CurrentContact.Name;
			return "No Contact selected";
		}
	}

	public event PropertyChangedEventHandler PropertyChanged;

	private void OnPropertyChanged(string propertyName)
	{
		if (PropertyChanged != null)
			PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
	}
}

You can see many „problems“ in this little example:

  1. Event passing between INotifyPropertyChanged instances
    You can clearly see in the setter of the CurrentContact property what has to be done if you rely on data inside a „foreign“ INotifyPropertyChanged instance.
    You have to make sure to listen to the PropertyChanged event of the instance to set and remove the event handler from the instance that leaves.
    If you e.g. forget to remove the event handler from the „old“ instance then you will get too many change-events. It’s very hard to detect something like this.
  2. The property logic is spread all over the class
    To fire the correct PropertyChanged events the source of the event has to know exactly what properties rely on it.
    In this example the setter for „CurrentContact“ and the event handler for the „Name“ property of the current contact have to know that the property „CurrentContactNameString“ uses them. In this example the dependencies are relatively simple but if this gets more complex you easily loose the overview.
    Every change on the target implies a reorganization of all the PropertyChanged sources to match the used logic again.

Results only change if the data used to get it changes

For those two problems I have developed a dependency tracking system. The central idea is that every result only changes whenever any data changes that has been used to get the result.
Sounds simple, right? It is that simple!

So I have developed a tracking mechanism that tracks all data that gets used to get a result (finally for a property getter). Whenever data changes all PropertyChanged events for results that depend on this data get fired.

The ViewModel sample using this approach looks like this:

public class MainViewModel : IFireNotifyPropertyChanged
{
	private ContactViewModel _CurrentContact;
	public ContactViewModel CurrentContact
	{
		get
		{
			using (this.Track(p => p.CurrentContact))
				return _CurrentContact;
		}
		set
		{
			this.SetPropertyValue(p => p.CurrentContact, ref _CurrentContact, value);
		}
	}

	public string CurrentContactNameString
	{
		get
		{
			using (this.Track(p => p.CurrentContactNameString))
			{
				if (CurrentContact != null)
					return CurrentContact.Name;
				return "No Contact selected";
			}
		}
	}

	public void FireNotifyPropertyChanged(string propertyName)
	{
		if (PropertyChanged != null)
			PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
	}

	public event PropertyChangedEventHandler PropertyChanged;
}

As you can see the property „CurrentContactNameString“ only has to use the „CurrentContact“ and the „Name“ property. Whenever one of them changes the PropertyChanged event for „CurrentContactNameString“ gets fired.

The integration of the framework is relatively simple:

  1. every getter (that is relevant) uses a Tracker instance as long as relevant data gets accessed. The creation of this Tracker instance is hidden by a extension method „Track“ for INotifyPropertyChanged.
  2. setter have to use the SetPropertyValue extension that triggers all the logic to notify dependent properties about this change
  3. (Only Silverlight for now) Instead of INotifyPropertyChanged the classes have to implement IFireNotifyPropertyChanged which extends INotifyPropertyChanged by a method to trigger a PropertyChanged event. This is necessary because Silverlight doesn’t allow to access private fields through reflection (and this is the only way to trigger an event from outside an instance)

The downside of this framework is that it can get slow very fast. Because every change triggers the PropertyChanged event for all dependent properties the amount of triggered events can explode easily. So use it with care 🙂
The real benefit is that you don’t have to care about dependencies between Properties or INotifyPropertyChanged instances and – even more important – don’t have to think about them during a refactoring!

I will explain the implementation of this framework in the next post after I have reorganized and published it to some Open Source hoster. So stay tuned 😉

Devmil

Windows Phone development

Currently I’m trying to get my way back to .NET by experimenting with Windows Phone.

I have been a .NET guy almost since I started developing software.

The beginning: Delphi

After finishing high school I started developing in Delphi during my vocational training. In my free time I came across the .NET Framework 1.1 (2003) and fell in love with it. From that very moment on I tried to use .NET and especially C# whenever I had the oportunity to do so. After finishing my vocational training in the end of 2003 I began to study computer sciences. The University of Applied Sciences I have been at had a very strong C and Java focus so C# was limited to my fun projects and my little side business I started to finance my studies.

My first mobile contact

At this time I discovered Windows Mobile and was blown away by the possibility to develop applications using C# for my handset. I developed many little applications for my handset and had much fun. One of those fun projects has been SniffThat.
I also worked as a freelancer for some firms. The most important condition for me to offer my work has been – you guess it – .NET. I always had the choice so every time I looked for a job I found one that had .NET involved. And sometimes I have found one that involved .NET and Windows Mobile. I have been a very happy jung man 😉

After finishing my studies (2007) I hired at a company that – you already know this – develops applications using the .NET Framework. Mainly ASP.NET intranet business applications. I had a very good time there, learned very much about clean code, performance optimizations and databases.
But something in my mind told me to try something different. I don’t know if I have been bored by the business requirements (finance) or if the birth of our first child triggered considerations regarding our long term future. I don’t know. Propably a mixture.

So 2011 I hired at a company to develop embedded software (user interfaces for home appliances). A complete new world. C++, embedded software, a big company.

My way to Android

Around 2008 I had lost my focus on handsets. I had a „standard“ phone (Sony Ericcsson I think) and did some Silverlight stuff in my free time. At one day my brother showed me his cool new phone: An iPhone. He told me that this phone has Apps, has nice specs and everybody needs one.
I checked the options to develop for this new handset and discovered some things that I didn’t like on developer side.
The two things that finally hold me off have been

  1. It is an Apple product. Come on! I only knew few people using Apple computers at this time. And these few people were so proud of beeing able to spend so much money for their computer that they had to show and tell this to everybody. I really hate that.
  2. Pay 100 bucks a year and buy a Mac only to develop for a phone as a hobby? Err – no.

A year or so later – after he almost bricked it trying to jailbreak – he bought another phone. This phone – so he said – is based on Linux and much more open than Apples iOS. He showed me his new Motorola Milestone. I liked the progress this techology has made since my Windows Mobile days and decided to get such a phone for my next contract renewal.

This is how I got my Galaxy S. I found out that the development for Android is based on Java (not so good) and is free (very good). I developed some little sample apps and started to rebuild an app called Clockr. A clock widget that shows the clock as text. After I had replicated Clockr I started to improve it. Added multiple language support, some settings here, some settings there, a layout editor and that is the story of Minimalistic Text.

My current way back

So, O.K. you may ask. What the heck has this story to do with the title of this post? I will tell you:

Before I bought the Galaxy S I checked what Microsoft will do with their Windows Mobile (that wasn’t able to compete with iOS or Android). As a C# fanboy I would have taken some drawbacks as a tradeoff to develop apps in C#. I found out that they (Microsoft) are going to use the „Apple approach“.
„If you like to load your own apps onto your own phone please give us 100 bucks a year“.
„If you don’t want me, you don’t get me“ I thought and ordered the Galaxy S. Man I have been pissed off.

In the beginning of 2012 – Minimalistic Text is over a year old – I have a small business again (for the donations that come for Minimalistic Text and some jobs that came alive through Minimalistic Text) the rumors about Windows (Phone) 8 are getting louder and louder so I started to look into the Windows Phone world again. I really turned off all Windows Mobile / Windows Phone related RSS feeds because I have been so damn pissed off. So I didn’t get any news about Windows Phone. I realized that Windows Phone has progressed (Copy and Paste, some kind of multithreading, …) and that if Microsoft can get back into the smartphone game then with the help of Windows 8 on PCs, Tablets and Smartphones.

Driven by the never dying love for C# 😉 I decided to prepare for Windows 8 by playing around with Windows Phone 7 and ordered a Samsung Omnia W.

I have to say that I have been amazed by this phone. I have a Galaxy Nexus right here on the desk but this little Omnia W smokes the Galaxy Nexus regarding smooth animations / transitions and overall response behavior.
Windows has its drawbacks – no doubt. The biggest one is that googlemail emails can’t be starred on the phone (sorry if I didn’t respond to some emails the past 2 months) and that you can’t access the file system (from your phone and from your computer).
But despite these drawbacks I use my Omnia W since I got it as my daily driver. My Galaxy Nexus is in my backpack as a backup 🙂 I simply can no longer ignore this micro stuttering when swiping through the home screen or app drawer.

Today I know that one can earn those 100 bucks in one year with some Marketplace activity so this argument isn’t that heavy any more. I don’t like it because I think that many hobbyists are held off developing for Windows Phone, but I can live with it.

So to explain this blog title: I’m currently developing some fun apps for Windows Phone using C#. So expect some technical C# / Silverlight / Windows Phone posts in the near future.

And if Microsoft does some things right then I will be very glad to provide some apps for the Windows Phone 8 marketplace.

Ah, and don’t worry: I will continue developing Minimalistic Text. The user base is too big and I am too proud of it to leave it behind 🙂