Вы находитесь на странице: 1из 388

1. Catel documentation Home . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .

1.1 Introduction . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.1.1 Why Catel? . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.1.2 Support for multiple platforms . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.1.2.1 Caveats in WPF . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.1.2.2 Caveats in Silverlight . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.1.2.3 Caveats in Windows Phone . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.1.2.4 Caveats in Windows RT . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.1.2.5 Caveats in Android . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.1.2.6 Caveats in iOS . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.1.3 Introduction to data objects . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.1.4 Introduction to MVVM . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.1.4.1 MVVM framework comparison sheet . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.1.4.2 Different interpretations of MVVM . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.1.4.3 Validation in model or view model? . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.1.4.4 Introduction to MVVM and models . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.1.4.5 Creating view models with Catel . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.1.4.6 Introduction to services . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.1.4.7 Introduction to the nested user controls problem . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.1.4.8 Introduction to unit testing in MVVM . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.1.5 Introduction to MVC . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.2 FAQ . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.2.1 General . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.2.2 MVVM . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.3 Setup, deployment and projects . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.3.1 Getting prerelease (beta) versions via NuGet . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.3.2 Stepping through the code . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.3.3 Compiling from source . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.3.4 Code snippets & templates . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.3.4.1 Using the code snippets . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.3.4.2 Using the item templates . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.3.4.3 Using the project templates . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.3.5 Updating to a new version via NuGet . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.3.6 Update guides . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.3.6.1 Catel 4.0.0 . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.3.6.2 Catel 4.1.0 . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.4 Getting started . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.4.1 Quick introduction for developers . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.4.2 Getting started with WPF . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.4.2.1 Creating the project . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.4.2.2 Creating the models . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.4.2.3 Serializing data from/to disk . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.4.2.4 Creating the view models . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.4.2.5 Creating the views (user controls) . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.4.2.6 Creating the views (windows) . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.4.2.7 Hooking up everything together . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.4.2.8 Finalizing the application . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.5 Examples . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.5.1 WPF Examples . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.5.1.1 Advanced WPF example . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.5.1.2 Authentication example . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.5.1.3 Browser application example . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.5.1.4 Master/detail example . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.5.1.5 Multilingual example . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.5.1.6 MVVM communication styles . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.5.1.7 Person application WPF example . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.5.1.8 Validation example . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.5.1.9 Viewmodel lifetime example . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.5.2 Silverlight examples . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.5.2.1 Advanced Silverlight example . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.5.2.2 Navigation example . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.5.2.3 Nested user controls example . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.5.2.4 Person application Silverlight example . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.5.3 Windows Phone examples . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.5.3.1 Bing maps example . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.5.3.2 Sensors example . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.5.3.3 Shopping list example . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.5.4 Open source using Catel . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.6 Problem solving . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.7 Performance considerations . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8 Catel.Core . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.1 ApiCop . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .

5
7
8
8
11
11
11
11
11
12
12
20
20
22
23
24
24
31
33
41
42
42
42
43
47
47
49
49
49
50
50
52
53
54
54
58
59
59
61
62
65
70
74
78
80
82
89
95
96
96
98
99
100
100
101
102
103
104
105
105
108
109
110
111
111
113
115
116
116
119
121
121

1.8.1.1 Cops . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.1.2 Rules . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.1.3 Listeners . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.2 Argument checking . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.3 Caching . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.4 Configuration . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.5 Data handling . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.5.1 ObservableObject . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.5.2 DispatcherObservableObject . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.5.3 ModelBase . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.5.4 Using ModelBase as base for entities . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.5.5 Advanced property change notifications . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.5.6 WCF services . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.6 Exception handling . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.7 IoC (ServiceLocator and TypeFactory) . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.7.1 Dependency injection . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.7.2 Introductions to IoC components . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.7.2.1 Introduction to the ServiceLocator . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.7.2.2 Introduction to the TypeFactory . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.7.2.3 Introduction to DependencyResolver and DependencyResolverManager . . . . . . . . . . . . . . . . . . . . . .
1.8.7.2.4 Ensuring integrity of the ServiceLocator . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.7.3 Automatic type registration . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.7.3.1 Automatically registering types using attributes . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.7.3.2 Automatically registering types using conventions . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.7.4 Setting up the ServiceLocator using configuration . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.7.5 Replacing the default components . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.8 Logging . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.8.1 Log listeners . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.8.1.1 Batch log listeners . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.8.1.2 ConsoleLogListener . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.8.1.3 DebugLogListener . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.8.1.4 EventLogListener . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.8.1.5 Event Tracing for Windows (ETW) . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.8.1.6 FileLogListener . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.8.1.7 RollingInMemoryLogListener . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.8.1.8 SeqLogListener . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.8.2 Customizing listeners . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.8.3 Creating log listeners via configuration . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.8.4 Integration with external loggers . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.8.4.1 Log4net . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.8.4.2 NLog . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.8.5 Anotar.Catel.Fody . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.9 Messaging . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.9.1 MessageBase . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.9.2 Message mediator . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.9.3 Messaging via attributes . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.10 Multilingual . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.11 Parallel invocation and tasks . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.12 Preventing memory leaks . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.12.1 Change notification wrapper . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.12.2 Weak events . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.13 Reflection . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.14 Scoping . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.15 Serialization . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.15.1 Introduction to serialization . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.15.2 Specifying what gets serialized . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.15.3 Customizing serialization . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.15.4 Supported serializers . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.15.4.1 BinarySerializer . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.15.4.2 JsonSerializer . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.15.4.3 XmlSerializer . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.16 Thread safe code . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.17 Validation . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.17.1 Validation via validate methods . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.17.2 Validation via data annotations . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.17.3 Validation via special model validators . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.17.4 Validation via IValidator . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.17.5 Using the validation context . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.17.6 Getting a summary of validation results . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.8.17.7 Deferring validation . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9 Catel.MVVM . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.1 Auditing . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .

124
124
126
126
127
130
132
133
134
135
138
139
140
142
146
147
152
152
153
155
159
161
161
162
163
166
166
168
168
170
171
171
172
172
173
174
175
175
176
176
177
178
179
180
181
181
183
186
187
187
188
190
191
191
192
194
201
204
204
204
206
206
209
210
210
211
212
215
216
216
217
218

1.9.2 Behaviors & triggers . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .


1.9.2.1 Authentication . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.2.2 AutoCompletionBehavior . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.2.3 AutoScroll . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.2.4 DelayBindingUpdate . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.2.5 DoubleClickToCommand . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.2.6 EventToCommand . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.2.7 Focus . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.2.8 FocusFirstControl . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.2.9 FocusOnKeyPress . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.2.10 HideUntilViewModelLoaded . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.2.11 KeyPressToCommand . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.2.12 MouseInfo . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.2.13 Navigate . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.2.14 NumericTextBox . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.2.15 SelectTextOnFocus . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.2.16 UpdateBindingOnPasswordChanged . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.2.17 UpdateBindingOnTextChanged . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.3 Bindings . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.3.1 Property bindings . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.3.2 Command bindings . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.4 Commands & events . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.4.1 Commands . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.4.2 CommandManager and command containers (Application-wide commands) . . . . . . . . . . . . . . . . . . . . . . . .
1.9.4.3 Asynchronous commands . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.4.4 Commands authentication . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.4.5 Hooking a command to validation automatically . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.5 Converters . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.6 Designers . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.6.1 Design-time view models . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.6.2 Running code at design-time . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.7 Handling application initialization parameters . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.8 Locators and naming conventions . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.8.1 ViewModelLocator . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.8.2 ViewLocator . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.8.3 UrlLocator . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.8.4 Naming conventions . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.9 Services . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.9.1 AccelerometerService . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.9.2 CameraService . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.9.3 CompassService . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.9.4 GyroscopeService . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.9.5 LocationService . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.9.6 MessageService . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.9.7 NavigationService . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.9.8 OpenFileService . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.9.9 PleaseWaitService . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.9.10 ProcessService . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.9.11 SaveFileService . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.9.12 SchedulerService . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.9.13 SelectDirectoryService . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.9.14 SplashScreenService . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.9.15 UIVisualizerService . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.9.16 VibrateService . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.9.17 ViewExportService . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.10 View models . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.10.1 Creating a basic view model . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.10.2 Creating a view model that watches over other view models . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.10.3 Creating a view model with a model . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.10.4 Creating a view model with a model and mappings . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.10.5 Mapping properties from view to view model . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.10.6 Nested view models . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.10.7 Validation in view models . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.10.8 Advanced view models . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.10.8.1 Keeping view models alive . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.10.8.2 Exposing properties of a model automatically . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.10.8.3 Determine the view model type dynamically at runtime . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.10.8.4 Controlling the instantiation of view models . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.11 Views . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.11.1 Android . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.11.1.1 Activities (pages) . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.11.1.2 Fragments (user controls) . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .

219
220
222
223
223
224
225
226
227
228
228
228
229
229
230
230
231
231
232
233
235
235
236
237
241
243
244
245
247
248
251
252
253
253
255
257
258
260
260
261
264
265
267
268
270
272
273
275
276
277
277
278
281
283
284
284
285
286
289
293
296
298
298
302
303
303
305
305
307
308
310
312

1.9.11.2 iOS . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.11.3 XAML . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.11.3.1 Window and DataWindow . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.11.3.2 UserControl . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.11.3.3 MVVM behaviors . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.11.3.4 Validation controls . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.11.3.5 Using external controls . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.11.3.6 Advanced information about views . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.11.3.7 Customizing DataContext subscription behavior . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.11.4 Tips & tricks . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.9.11.4.1 Finding the view of a view model . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.10 Catel.Mvc . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.10.1 Configuring dependency injection . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.11 Catel.Extensions.Controls . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.11.1 Controls . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.11.1.1 StackGrid . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.11.1.2 TabControl . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.11.1.3 TraceOutputControl . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.11.1.4 WatermarkTextBox . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.11.2 Pixel shaders . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.11.3 StyleHelper . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.11.4 Themes . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.12 Catel.Extensions.CSLA . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.13 Catel.Extensions.Data . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.13.1 Specifications . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.14 Catel.Extensions.DynamicObjects . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.15 Catel.Extensions.EntityFramework . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.15.1 Getting started with Entity Framework in Catel . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.15.2 Using the DbContextManager . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.15.3 Using the repositories and unit of work . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.15.4 Using the ModelBase as base class for code-first entities . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.15.5 Using stored procedures and functions . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.16 Catel.Extensions.FluentValidation . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.17 Catel.Extensions.Interception . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.17.1 Method interception . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.17.2 Property interception . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.18 Catel.Extensions.Memento . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.18.1 Memento and collections . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.18.2 Memento and methods . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.18.3 Memento and properties . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.19 Catel.Extensions.Prism . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.19.1 Using the bootstrapper . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.19.2 Declaring modules . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.19.3 Module catalogs . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.19.3.1 CompositeModuleCatalog . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.19.3.2 DownloadingModuleCatalog . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.19.3.3 NuGetBasedModuleCatalog . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.19.3.4 SafeDirectoryModuleCatalog . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.19.4 Translating or customizing the initialization task messages . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.20 Catel.Extensions.Wcf.Server . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.21 Catel.Fody . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.21.1 Weaving properties . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.21.2 Weaving argument checks . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.21.3 Exposing properties on view models . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.21.4 XmlSchema generation . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.22 Catel.ReSharper . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.22.1 Checking arguments of a method . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.22.2 Converting regular properties into Catel properties . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
1.23 Reference documentation . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .

314
314
314
317
322
323
325
329
335
336
336
337
337
339
339
339
340
340
341
342
343
344
345
345
345
346
347
347
350
351
353
353
354
355
355
360
361
363
363
365
366
369
371
372
372
373
373
377
377
377
378
379
381
382
384
385
385
386
387

Catel documentation Home


Welcome to the documentation of Catel. The framework consists of several projects. Each project has it's reference documentation. The actual
technical documentation is available in the downloads sections. However, the wiki contains some real-life examples and additional explanation of
some of the features of Catel.
Don't want to read much? Make sure that you at least read the quick introduction with the absolute basics

Supported platforms
Looking for documentation of other versions?
Articles or documentation?
Explanation about the documentation
Catel is an application development platform with the focus on MVVM (WPF, Silverlight, Windows Phone and WinRT) and MVC (ASP.NET
MVC). The goal of Catel is to provide a complete set of modular functionality for Line of Business applications written in any .NET technology,
from client to server.
Catel distinguishes itself by unique features to aid in the development of MVVM applications and server-side application development. Since Catel
focuses on Line of Business applications, it provides professional support and excellent documentation which ensures a safe bet by professional
companies and developers.
Besides the core of Catel, lots of extensions are available so developers can pick whatever they need for their applications to be built. Among
these extensions are support for Dynamic Objects, Entity Framework, Fluent Validation, Memento patterns and Prism.
Below is a visual representation of the available blocks in Catel:

Supported platforms
The following platforms are supported by Catel:

For detailed information about platform support, see Platform support explanation

Looking for documentation of other versions?


Updating from an older version? Check out the update guides

Catel LATEST
Catel 4.1
Catel 4.0
Catel 3.9
Catel 3.8
Catel 3.7
Catel 3.6
Catel 3.5

Articles or documentation?
You have probably also found the articles on The Code Project. These articles are meant to be an introduction to a specific field of techniques that
can be found inside Catel. If you are looking for documentation, this is the place to be.
Are you missing documentation?
If you are missing documentation or feel that documentation is out of date, please let us know and we will will fix it!
Don't forget to take a look at the code snippets and project templates, they will make your life much easier

Explanation about the documentation


You can either navigate through the left bar or via the search at the right top. Below are the top parts of the documentation:

Introduction
FAQ
Setup, deployment and projects
Getting started
Examples
Problem solving
Performance considerations
Catel.Core
Catel.MVVM
Catel.Mvc
Catel.Extensions.Controls
Catel.Extensions.CSLA
Catel.Extensions.Data
Catel.Extensions.DynamicObjects
Catel.Extensions.EntityFramework
Catel.Extensions.FluentValidation
Catel.Extensions.Interception
Catel.Extensions.Memento
Catel.Extensions.Prism
Catel.Extensions.Wcf.Server
Catel.Fody
Catel.ReSharper
Reference documentation

Introduction
Welcome to the introduction of Catel. Catel is a framework (or enterprise library, just use whatever you like) with data handling, diagnostics,
logging, WPF controls, and an MVVM-framework. So Catel is more than "just" another MVVM-framework or some nice Extension Methods that
can be used. It's more like a library that you want to include in all the XAML applications you are going to develop in the near future.
Note that Catel is primarily meant for Line of Business (LoB) applications

It's important to realize that Catel is not just another Extension Methods library, nor only an MVVM-framework, but it is a combination of basic data
handling, useful controls, and an MVVM-framework.

Why another framework?


You might be thinking: why another framework, there are literally thousands of them out there. Well, first of all, thousands of them is quite a lot,
let's just say there are hundreds of them. A few years ago, the lead developer of Catel was using serialization to serialize data from/to disk. But,
as he noticed, he had to take care of different versions after every release. After every release, he had to take care of the serialization and
backwards compatibility. Also, he had to implement some very basic interfaces (such as INotifyPropertyChanged) for every data object. Then, he
decided to write a base class for data handling which can take care of different versions and serialization by itself, and implements the most basic
interfaces of the .NET Framework out of the box. The article was published on CodeProject as DataObjectBase.
Then, he was working on a WPF project with five other developers and needed an MVVM-framework since the application was not using MVVM
at the moment. Writing an MVVM-framework was no option because there were so many other frameworks out there. But, after looking at some
Open-Source MVVM-frameworks (such as the excellent Cinch framework, which was the best one we could find), none of them seemed to be a
real option. Creating the View Models was too much work, and the View Models still contained lots of repetitive code in, for example, the property
definitions. After taking a closer look at the source code of Cinch and other frameworks, the lead developer thought: if we use the DataObjectBase
published before as the base for a View Model class, it should be possible to create a framework in a very short amount of time.
Then, all other developers of the team he was working on the project got enthusiastic, and then the whole team decided to merge their personal
libraries into one big enterprise library, and Catel was born.

Why use this framework?


Before reading any further, it's important to know why you should use the framework. Below are a few reasons why Catel might be interesting for
you:
Catel is Open-Source. This way, you can customize it any way you want. If you want a new feature request, and the team does not
respond fast enough, you can simply implement it yourself.
The codebase for Catel is available on GitHub. This way, you have the option to either download the latest stable release, or live on the
edge by downloading the latest source code.

Catel uses unit tests to make sure that new updates do not break existing functionality.
Catel is very well documented. Every method and property has comments, and the comments are available in a separate reference help
file. There is also a lot of documentation available, and in the future, in-depth articles will be written.
Catel is developed by a group of talented software developers, and is heavily under development. This is a great advantage because the
knowledge is not at just one person, but at a whole group. The developers of Catel all have more than three years of development
experience with WPF, and are using Catel in real life applications for at least 2 years.

Continue reading
Why Catel?
Support for multiple platforms
Introduction to data objects
Introduction to MVVM
Introduction to MVC

Why Catel?
We care a lot about the freedom you need as a software developer. Most frameworks require a developer to learn its conventions, or use the
whole framework or nothing at all. When we, the developers of Catel, use an external framework, we choose that framework for a specific reason,
and dont want to be bothered by all the other superb stuff it has to offer (maybe later, but not now).
During the development of Catel, we tried to maintain this freedom aspect which is very important to us. Therefore, all functionality is loosely
coupled. Sounds great, but everything is called loosely coupled nowadays. Catel contains a lot of different aspects, such as logging, diagnostics,
Reflection, MVVM, user controls, windows, etc. All these aspects are complementary to each other, but the great thing about Catel is that you
decide whether to use just one, some, or maybe all aspects.
As an example: you have a legacy application and want to use the DataWindow to write simple entry windows, but you are not ready for MVVM
yet. No problem, the DataWindow is complementary to MVVM, but does not require it. Therefore, you have all the freedom to use just what you
need, whenever you need it.
Most frameworks require a bootstrapper that completely decides how your application structure should look like. For example, your Views must
have this name, your controls must have that name. Again, in Catel, we wanted to give you the freedom you would expect from a framework.
The great thing about this freedom is that the different aspects of Catel can be used side-by-side with other frameworks, so you as a developer
can use the best framework for every aspect in your application.
Another nice thing is that Catel is WPF-based. Now you might be thinking: but hey, I use Silverlight! However, the upside of this approach is that
all goodies that are well known in WPF, but not in Silverlight are also brought to Silverlight. For example, in Silverlight there is no automatic
command re-evaluation. Catel does this out of the box, even in Silverlight.
Catel offers a solution in the following fields:
Data handling
MVVM
And much more which you will find out during the use of Catel!

Support for multiple platforms


Catel is available on a lot of platforms.
Introducing "true PCL"
Xaml
Android
iOS
Platform support by component
Fundamental differences
For a list of caveats per platform, check out the following links:
Caveats in WPF
Caveats in Silverlight
Caveats in Windows Phone
Caveats in Windows RT
Caveats in Android
Caveats in iOS

Introducing "true PCL"


Portable Class Libraries (PCL) is a technique where developers can develop a single assembly that can be used by multiple platforms. The
reason the team decided not to use PCL is that it brings in too many limitations. We wanted to provide the developer all the possibilities of the
platform they are developing in, not the least platform supported.
As you can see in the diagram below, each platform has its own set of functionality (orange). When using PCL, the functionality will be
downgraded to the "least" platform (thus lots of features will be lost). Catel works the other way around by adding features of other platforms. For
example, checking for dependency property changed is available on all platforms and works exactly the same for all platforms.

A great example of the advantages are the services that are provided by Catel. All the platforms that support some sort of GPS functionality have
the ILocationService (which is an interface that is platform independent). Each platform (Windows Phone, WinRT, Xamarin, etc) have their own
implementation but the developer can use them in exactly the same manner without losing functionality. This means that instead of losing
functionality, Catel adds functionality by not using PCL but platform dependent assemblies instead.

Supported platforms
Xaml
WPF 4.0
WPF 4.5
Silverlight 5
Windows Phone 8.0
Windows Phone 8.1
Windows RT 8.0
Windows RT 8.1

Android
Android 4.0+ (Xamarin)

iOS
iOS 6.0+ (Xamarin)

Platform support by component

This page explains in detail what parts of Catel are available on specific platforms.
NET 4.0

Catel.Core

Catel.MVVM

Catel.MVC4

Catel.MVC5

Catel.Extensions.Controls

Catel.Extensions.CSLA

Catel.Extensions.Data

Catel.Extensions.DynamicObjects
Catel.Extensions.EntityFramework5

Catel.Extensions.EntityFramework6
Catel.Extensions.FluentValidation

Catel.Extensions.Interception

Catel.Extensions.Memento

NET 4.5

SL 5

WP 8.0

WP 8.1

WIN 8.0

WIN 8.1

Catel.Extensions.Prism

Fundamental differences
There are some fundamental differences between platforms (such as Xaml and Android). The table below explains the differences so it is easy to
understand for a developer what to use when. Note that all services are defined by interfaces and can be used on all the platforms in the same
manner. The platform-specific implementations are hidden as much as possible to keep the view models very re-usable.
Feature

Xaml

Android

iOS

Phone pages

PhonePage or Page

Activity

TODO

Nested user controls

UserControl

Fragment

TODO

Caveats in WPF
Below are all caveats in WPF.

Know caveats? Feel free to add them!

Caveats in Silverlight
Below are all caveats in Silverlight.

Know caveats? Feel free to add them!

Caveats in Windows Phone


Below are all caveats in Windows Phone.

Know caveats? Feel free to add them!

Caveats in Windows RT
Below are all caveats in Windows RT.

Know caveats? Feel free to add them!

Caveats in Android
Below are all caveats in Android.
Linker settings
Know caveats? Feel free to add them!

Linker settings
When linking in release mode (or debug if you would like), the linker will remove all non-used items from the final application assembly. Since the

binding system in Catel uses reflection, it might break when the linker is too aggressive when optimizing the app. To prevent optimalization, create
a dummy file that uses the members of each type so the linker will not exclude them. Note that this class will never be instantiated, nor will its
methods be invoked. It is purely to let the static analysis be notified of the usage.
Note that this applies to both properties and bindings

Below is an example class to force the inclusion of members in Android. For each type and its members, a method is added. Then each used
property is accessed and each used event is subscribed to.

public class LinkerInclude


{
public void IncludeActivity(Activity activity)
{
activity.Title = activity.Title = string.Empty;
}
public void IncludeButton(Button button)
{
button.Text = button.Text + string.Empty;
button.Click += (sender, e) => {

};

}
public void IncludeEditText(EditText editText)
{
editText.Text = editText.Text + string.Empty;
editText.TextChanged += (sender, e) => { };
}
public void IncludeCommand(ICatelCommand command)
{
command.CanExecuteChanged += (sender, e) => { };
}
}

Caveats in iOS
Below are all caveats in iOS.

Know caveats? Feel free to add them!

Introduction to data objects


It is very important to understand the data objects in Catel because they form the base pillar of all components used by the MVVM framework.
The ObservableObject class
The ModelBase class
Creating your first data object
Declaring properties
Simple properties
Properties with property change callback
Adding validation
Saving objects
Loading an object
Saving an object

The ObservableObject class


This documentation is to be written in the future

The ModelBase class


This documentation is to be written in the future

Creating your first data object


First of all, it is very important to realize that you shouldn't bore yourself with writing all the code below yourself. Catel contains lots of code
snippets that allow you to create data objects very easily in a short amount of time.
This example shows the simplest way to declare a data object using the ModelBase class. By using a code snippet, the class is created in just 10
seconds.
Code snippets
model - Declares a data object based on the ModelBase class
Steps
1. Create a new class file called FirstModel.cs.
2. Inside the namespace, use the model codesnippet and fill in the name of the class, in this case FirstModel.
Code

/// <summary>
/// FirstModel class which fully supports serialization, property changed
notifications,
/// backwards compatibility and error checking.
/// </summary>
[Serializable]
public class FirstModel : ModelBase
{
#region Fields
#endregion
#region Constructors
/// <summary>
/// Initializes a new object from scratch.
/// </summary>
public FirstModel()
{ }
/// <summary>
/// Initializes a new object based on <see cref="SerializationInfo"/>.
/// </summary>
/// <param name="info"><see cref="SerializationInfo"/> that contains the
information.
/// </param>
/// <param name="context"><see cref="StreamingContext"/>.</param>
protected FirstModel(SerializationInfo info, StreamingContext context)
: base(info, context) { }
#endregion
#region Properties
// TODO: Define your custom properties here using the propdata code snippet
#endregion
#region Methods
/// <summary>
/// Validates the field values of this object. Override this method to enable
/// validation of field values.
/// </summary>
/// <param name="validationResults">The validation results, add additional results
to this list.</param>
protected override void ValidateFields(List<FieldValidationResult>
validationResults)
{
}
/// <summary>
/// Validates the field values of this object. Override this method to enable
/// validation of field values.
/// </summary>
/// <param name="validationResults">The validation results, add additional results
to this list.</param>
protected override void ValidateBusinessRules(List<BusinessRuleValidationResult>
validationResults)
{
}
#endregion
}

Declaring properties
The next step to learn on the ModelBase class is how to declare properties. There are several types of properties, and they will all be handled in
this part of the documentation.
The ModelBase class uses a dependency property a-like notation of properties.

Simple properties
This example shows how to declare the simplest property. In this example, a string property with a default value will be declared with the use of a
code snippet.
Code snippets
modelprop - Declares a simple property on a model
Steps
1. Open FirstModel.cs created in the previous step.
2. In the Properties region, use the code snippet modelprop, and use the following values:
Code snippet item

Value

description

Gets or sets the simple property

type

string

name

SimpleProperty

defaultvalue

"Simple property"

Code

/// <summary>
/// Gets or sets the simple property.
/// </summary>
public string SimpleProperty
{
get { return GetValue<string>(SimplePropertyProperty); }
set { SetValue(SimplePropertyProperty, value); }
}
/// <summary>
/// Register the SimpleProperty property so it is known in the class.
/// </summary>
public static readonly PropertyDataSimplePropertyProperty =
RegisterProperty("SimpleProperty", typeof(string), "Simple property");

Properties with property change callback


Code snippets
modelpropchanged - Declares a simple property on a model with a property changed callback
Steps
1. Open FirstModel.cs created in the previous step.
2. In the Properties region, use the code snippet modelpropchanged, and use the following values:
Code snippet item

Value

description

Gets or sets the callback property

type

string

name

CallbackProperty

defaultvalue

"Callback property"

Code

/// <summary>
/// Gets or sets the callback property.
/// </summary>
public string CallbackProperty
{
get { return GetValue<string>(CallbackPropertyProperty); }
set { SetValue(CallbackPropertyProperty, value); }
}
/// <summary>
/// Register the CallbackProperty property so it is known in the class.
/// </summary>
public static readonly PropertyDataCallbackPropertyProperty =
RegisterProperty("CallbackProperty", typeof(string), "Callback property",
(sender, e) => ((FirstDataObject)sender).OnCallbackPropertyChanged());
/// <summary>
/// Called when the CallbackProperty property has changed.
/// </summary>
private void OnCallbackPropertyChanged()
{
// TODO: Implement logic
}

Adding validation
It is very easy to add validation to a class (both the ModelBase and ViewModelBase). There are several ways, but this getting started guide will
handle only the most simple one.
To enable validation, you must override at least one of the following methods:

/// <summary>
/// Validates the field values of this object. Override this method to enable
/// validation of field values.
/// </summary>
/// <param name="validationResults">The validation results, add additional results to
this list.</param>
protected override void ValidateFields(List<FieldValidationResult> validationResults)
{
if (string.IsNullOrEmpty(FirstName))
{
validationResults.Add(FieldValidationResult.CreateError(FirstNameProperty,
"First name cannot be empty"));
}
}
/// <summary>
/// Validates the field values of this object. Override this method to enable
/// validation of field values.
/// </summary>
/// <param name="validationResults">The validation results, add additional results to
this list.</param>
protected override void ValidateBusinessRules(List<BusinessRuleValidationResult>
validationResults)
{
if (SomeBusinessErrorOccurs)
{
validationResults.Add(BusinessRuleValidationResult.CreateError("A business
error occurred"));
}
}

After the validation is implemented into the object, the validation will occur every time a property on the object changes. It is also possible to
manually validate by calling the Validate method.
There are also other ways to add validation to a data object:
Validation via data annotations - attributes such as the RequiredAttribute
Validation via IValidator - custom validation such as FluentValidation
The great thing is that Catel will gather all validation results from all different mappings and combine these into the ValidationContext. This context
can be used to query all sorts of validation info about an object.
Note that this is just an introduction, more information about validation can be found in other parts of the documentation

Saving objects
Saving and loading objects out of the box has never been so easy. SavableModelBase can automatically save/load objects in several ways, such
as memory, file in different modes (binary and XML). This example shows that making your objects savable is very easy and does not take any
time!
Code snippets
model - Declare a model based on the ModelBase class
modelprop - Declare a simple property on a model
Steps
1. Create a new class file called Person.cs.
2. Inside the namespace, use the model codesnippet and fill in the name of the class, in this case Person.
3. Change the base class from ModelBase to SavableModelBase.
4.

4. In the Properties region, use the code snippet modelprop, and use the following values:
Code snippet item

Value

description

Gets or sets the name

type

string

name

Name

defaultvalue

"MyName"

Code

/// <summary>
/// Person class which fully supports serialization, property changed notifications,
/// backwards compatibility and error checking.
/// </summary>
[Serializable]
public class Person : SavableModelBase<Person>
{
#region Fields
#endregion
#region Constructors
/// <summary>
/// Initializes a new object from scratch.
/// </summary>
public Person()
{ }
/// <summary>
/// Initializes a new object based on <see cref="SerializationInfo"/>.
/// </summary>
/// <param name="info"><see
///
cref="SerializationInfo"/> that contains the information.
/// </param>
/// <param name="context"><see
//
cref="StreamingContext"/>.</param>
protected Person(SerializationInfo info, StreamingContext context)
: base(info, context) { }
#endregion
#region Properties
/// <summary>
/// Gets or sets the name.
/// </summary>
public string Name
{
get { return GetValue<string>(NameProperty); }
set { SetValue(NameProperty, value); }
}
/// <summary>
/// Register the Name property so it is known in the class.
/// </summary>
public static readonly PropertyData NameProperty = RegisterProperty("Name",
typeof(string), "MyName");
#endregion
#region Methods
#endregion
}

Loading an object
Loading an object is really simple once the class has been created. It is important to use the static method on the class:

var person = Person.Load(@"c:\person.dob");

Saving an object
To save an object, an instance is required. Then simply call the Save method.

var person = new Person();


person.Name = "John Doe";
person.Save(@"c:\person.dob");

Introduction to MVVM
This part gives an introduction to MVVM in Catel.
MVVM framework comparison sheet
Different interpretations of MVVM
Validation in model or view model?
Introduction to MVVM and models
Creating view models with Catel
Introduction to services
Introduction to the nested user controls problem
Introduction to unit testing in MVVM

MVVM framework comparison sheet


In this MVVM framework comparison sheet includes as many aspects as possible. However, it might be possible that some were missed. If you
have features that are not included in the comparison sheet, or you find that information is incorrect, please let us know!
Below is short list of definitions:
Definition

Explanation

VM

View-Model

This comparison sheet is last updated on September 4th, 2012

Frameworks reviewed
Framework

Description

Website

Catel

Catel is more than just an MVVM toolkit. It also includes user controls and lots of
enterprise library classes. The MVVM toolkit differs itself from other frameworks of
the simplicity and solves the "nested user control" problem with dynamic viewmodels
for user controls

http://catel.codeplex.com

Caliburn.Micro

A small, yet powerful implementation of Caliburn designed for WPF, Silverlight and
WP7. The framework implements a variety of UI patterns for solving real-world
problems. Patterns that are enabled include MVC, MVP, Presentation Model
(MVVM), and Application Controller.

http://caliburnmicro.codeplex.com

Cinch (V2)

Cinch is a MVVM framework that exposes a number of helper classes to allow the
developer to quickly get to grips with creating scalable testable MVVM frameworks
as quickly as possible.

http://cinch.codeplex.com

MVVM light

The MVVM Light Toolkit is a set of components helping people to get started in the
Model - View - ViewModel pattern in Silverlight and WPF. It is a light and pragmatic
framework that contains only the essential components needed.

http://mvvmlight.codeplex.com

Simple MVVM
toolkit

Simple MVVM Toolkit makes it easier to develop Silverlight, WPF and WP7
applications using the Model-View-ViewModel design pattern. The purpose of the
toolkit is to provide a simple framework and set of tools for getting up to speed
quickly with applications based on the MVVM design pattern. The emphasis is on
simplicity, but it contains everything you need to implement MVVM for real-world line
of business applications.

http://simplemvvmtoolkit.codeplex.com/

WAF

The WPF Application Framework (WAF) is a lightweight Framework that helps you
to create well structured WPF Applications. It supports you in applying a Layered
Architecture and the Model-View-ViewModel (aka MVVM, M-V-VM,
PresentationModel) pattern.

http://waf.codeplex.com/

Platform support
Catel

Caliburn.Micro

Cinch (V2)

MVVM light

Simple MVVM

WAF

WPF
Silverlight 4
Silverlight 5
Windows Phone 7
Windows Phone 8
WinRT
Available via NuGet

UI features
Catel

Caliburn.Micro

Cinch (V2)

MVVM light

Simple MVVM

WAF

MVVM specific window


MVVM specific user control
Dynamic view model injection
Lazy loading of view models
View to VM communication via attributes
Events when views are actually loaded

ViewModelBase functionality
Catel
INotifyPropertyChanged
IDataErrorInfo
IDataWarningInfo
Support for canceling data
Support for confirming data
Automatic property definitions
Automatic model communications (mappings)

Generate features

Caliburn.Micro

Cinch (V2)

MVVM light

Simple MVVM

WAF

Catel

Caliburn.Micro

Cinch (V2)

MVVM light

Simple MVVM

WAF

Communication with other VM via messenger


Communication with other VM via attributes
RelayCommand / DelegateCommand
EventToCommand trigger
IoC container support
Unity support
MEF support
Background task manager
ViewModelManager with live VM instances
Project and item templates
Design time example data support
Memento pattern

View model services


Catel

Caliburn.Micro

Cinch (V2)

MVVM light

Simple MVVM

WAF

IMessage(Box)Service
INavigationService
IOpenFileService
IPleaseWaitService
IProcessService
ISaveFileService
IUIVisualizerservice
Unit test versions of services

Windows Phone specific view model services


Catel

Caliburn.Micro

Cinch (V2)

MVVM light

Simple MVVM

WAF

IAccelerometerService
ICameraService
ICompassService
IGyroscopeService
ILocationService
INavigationService
IVibrateService

Different interpretations of MVVM


There are two different interpretations of MVVM, the "purist" way where the model is protected, or the "shortcut" way where the view model only
provides the instance of the model and the view then binds directly to the model.

Shortcut interpretation
This is what most people do. The view model once implements the model, and then provides the model to the view. The view then
Advantages
Easy to use
Fast since view model hardly contains any properties
Disadvantages
Always need to bind to Model.[PropertyName], but for view model properties it's just [PropertyName], might be confusing
Less control over validation (you cannot insert logic between View <=> Model where MVVM is all about

Purist interpretation
This is what the developers of Catel strongly believe in. It requires a bit more code, but gives great freedom and control and protection of the
model because all bindings go through the view model.
Advantages
Full contol and freedom, you can inject both logic and validation between view and model (what MVVM is actually about)
Everything is available on the view model, no need for "sub-bindings" (such as Model.[PropertyName])
Protection of your model from the view
Disadvantages
Needs a bit more code (but thanks to code snippets and the Expose attribute, this is not a big disadvantage)

Validation in model or view model?


I have had lots of discussion whether the validation should take place in the model or the view model. Some people think that the validation
should always occur inside the model because you dont want to persist invalid models to the persistence store. Others say that the models itself
dont need validation, but the state the view model is in requires the validation. I think both are true, and I will tell you why.
First of all, you dont want invalid models in your persistence store. Thus, the most basic checks such as type, ranges and required fields should
be validated in the model. But sometimes, it is required to restrict the user more than the model does, and thats where validation in the view

model comes in handy. Another reason why you want to implement (a part of) the validation in the view model is the state of the model inside a
workflow. If you have a workflow that updates the model step by step, the model isnt valid after the first step in the workflow. However, you
already want to persist the model because the user might decide to execute the following steps at a later time. You dont want to implement the
state logic of a workflow in your model (and if you did that, get rid of it, as soon as possible). This is another feature where the view model
validation comes in handy.
The good news is that with Catel, it doesnt matter what you want, because its all possible. If you want your model to do all the validation, then
this is possible using the Model and ViewModelToModel attributes which map the values of the properties and the errors directly to the model so
the view model acts as a proxy between the view and the model. If you want to do all of the validation inside the view model, then you can
implement the ValidateFields and ValidateBusinessRules methods in the view model. And, if you want the best of both worlds, such as me, than
you can use a combination of the techniques described above.

Introduction to MVVM and models


This part of the documentation will explain all the parts of MVVM, in the order in which we think they must be built. First of all, the Models, which
are the closest to the business. Then, the View Models which define what part of the Models should be visible to the user in a specific situation.
This also includes validation that is specific for the functionality that the View Model represents. Last, but not least, the View itself, which is the
final representation of the View Model to the end-user.
As you will notice (or maybe you don't), this framework has a lot in common with other MVVM frameworks out there. This is normal because all of
the frameworks are trying to implement the same pattern, which isn't that hard to understand if you think about it long enough. Before we started
writing the MVVM framework, we first investigated other frameworks because there already are enough, probably too many. However, even the
better (or best) still took too much time to use, and there was too much code we had to write to create a View Model. That's the point where we
decided to write our own framework that contains lots of luxury for lazy developers such as us.

Models
The Models part is one of the three major parts of MVVM. Therefore, I want to tell you a bit about what kind of Models we use to store our data.
Basically, you can use all types of objects as Models, as long as the Models implement the most commonly used interfaces required by WPF or
Silverlight.
For MVVM, it is very important that the following interfaces are implemented:
INotifyPropertyChanged
If this interface is not implemented, changes will not be reflected to the UI via bindings. In other words, your Model and View Model will
be useless in an MVVM setting.
Finally, it is strongly recommended to have your Models implement the following interfaces as well:
IDataErrorInfo
If this interface is not implemented, errors cannot be shown to the user.
IEditableObject
If this interface is not implemented, a Model cannot work with states. This means that a user cannot start editing an object and finally
cancel it (because there is no stored state that can be used to restore the values).

View Models
View models are the classes that contain the view logic. They can be seen as a container for all models in a specific view, including the behavior
to interact with these models (for example adding or removing them from a collection). It is very important that a view model also implements the I
NotifyPropertyChanged interfaces just like the models do.

Creating view models with Catel


The View Models in Catel are very easy to write, and give the end-user a great flexibility in how to approach the Models. This part of the article will
explain the classes that make it possible to easily create View Models.
The ViewModelBase class is the most important class of all in the MVVM Framework of Catel. Of course, it can't do anything useful without the
other classes, but all the View Models that are created using Catel derive of this class. ViewModelBase is based on the ModelBase class that
ships with Catel. Thanks to the existence of that class, the MVVM framework was set up very quickly (although very quickly is relative). Below is
a class diagram that shows the class tree:

The class diagram above shows how many default interfaces of the .NET Framework are supported in the ModelBase class. Since most of these
interfaces are used by WPF as well, the ViewModelBase class itself can take huge advantage of the implementation of ModelBase.
Because ViewModelBase derives from ModelBase, you can declare properties exactly the same way. Even better, you can simply use ModelBas
e (or the extended SavableModelBase) to create (and save) your Models, and use ViewModelBase as the base for all the View Models.

Creating a view model


To declare a View Model, use the following code snippet:
vm - defines a new view model
When using the vm code snippet, this is the result:

/// <summary>
/// $name$ view model.
/// </summary>
public class $name$ViewModel : ViewModelBase
{
#region Fields
#endregion
#region Constructors
/// <summary>
/// Initializes a new instance of the <see cref="$name$ViewModel"/> class.
/// </summary>
public $name$ViewModel ()
{
}
#endregion
#region Properties
/// <summary>
/// Gets the title of the view model.
/// </summary>
/// <value>The title.</value>
public override string Title { get { return "View model title"; } }
// TODO: Register models with the vmpropmodel codesnippet
// TODO: Register view model properties with the vmprop or vmpropviewmodeltomodel
codesnippets
#endregion
#region Commands
// TODO: Register commands with the vmcommand or vmcommandwithcanexecute
codesnippets
#endregion
#region Methods
#endregion
}

Declaring properties
Note that declaring properties works exactly the same as declaring properties for the ModelBase

There are several code snippets available to create View Model properties:
vmprop - Defines a simple View Model property.
vmpropmodel - Defines a View Model property with ModelAttribute. The property is also made private by default.
vmpropviewmodeltomodel - Defines a View Model property with ViewModelToModelAttribute.
When using the vmprop code snippet, this is the result:

/// <summary>
/// Gets or sets the name.
/// </summary>
public string Name
{
get { return GetValue<string>(NameProperty); }
set { SetValue(NameProperty, value); }
}
/// <summary>
/// Register the Name property so it is known in the class.
/// </summary>
public static readonly PropertyData NameProperty = RegisterProperty("Name",
typeof(string));

In the View, it is now possible to bind to the Name property of the View Model, as long as DataContext is set to an instance of the View Model.

Declaring commands
There are several code snippets available to create View Model commands:
vmcommand - Defines a command that is always executable.
vmcommandwithcanexecute - Defines a command that implements a CanExecute method to determine whether the command can be
invoked on the View Model in its current state.
When using the vmcommandwithcanexecute code snippet, this is the result:

/// <summary>
/// Gets the Add command.
/// </summary>
public Command<object, object> Add { get; private set; }
// TODO: Move code below to constructor
Add = new Command<object, object>(OnAddExecute, OnAddCanExecute);
// TODO: Move code above to constructor
/// <summary>
/// Method to check whether the Add command can be executed.
/// </summary>
/// <param name="parameter">The parameter of the command.</param>
private bool OnAddCanExecute(object parameter)
{
return true;
}
/// <summary>
/// Method to invoke when the Add command is executed.
/// </summary>
/// <param name="parameter">The parameter of the command.</param>
private void OnAddExecute(object parameter)
{
// TODO: Handle command logic here
}

The only thing left to do now is to move the creation of the command to the constructor (as the comments already instructs you to).

In the View, it is now possible to bind any Command property (such as the Command property of a Button) to the Add property of the View Model,
as long as DataContext is set to an instance of the View Model.

Adding validation
Because the ViewModelBase class derives from ModelBase, it provides the same power of validation that the ModelBase class has to offer. Mode
lBase (and thus ViewModelBase) offers the following types of validation:
Field warnings
Business warnings
Field errors
Business errors
ViewModelBase uses smart validation. This means that if the object is already validated, the object is not validated again to make sure that the
View Models don't hit too much on the performance. Only when a property on the View Model changes, validation will be invoked. Of course, if
required, it is still possible to force validation when the View Model must be validated, even when no properties have changed.
To implement field or business rule validation, you only have to override ValidateFields and/or the ValidateBusinessRules method:

/// <summary>
/// Validates the field values of this object. Override this method to enable
/// validation of field values.
/// </summary>
/// <param name="validationResults">The validation results, add additional results to
this list.</param>
protected override void ValidateFields(List<FieldValidationResult> validationResults)
{
if (!string.IsNullOrEmpty(FirstName))
{
validationResults.Add(FieldValidationResult.CreateError(FirstNameProperty,
"First name cannot be empty"));
}
}
/// <summary>
/// Validates the field values of this object. Override this method to enable
/// validation of field values.
/// </summary>
/// <param name="validationResults">The validation results, add additional results to
this list.</param>
protected override void ValidateBusinessRules(List<BusinessRuleValidationResult>
validationResults)
{
if (SomeBusinessErrorOccurs)
{
validationResults.Add(BusinessRuleValidationResult.CreateError("A business
error occurred"));
}
}

Note that it is also possible to re-use validation in a model using ModelToViewModel mappings or even external validation such as Flue
ntValidation
There are also other ways to add validation to a data object:
Validation via data annotations - attributes such as the RequiredAttribute
Validation via IValidator - custom validation such as FluentValidation
The great thing is that Catel will gather all validation results from all different mappings and combine these into the ValidationContext. This context
can be used to query all sorts of validation info about an object.

Interaction with models


One of the most important reasons why a View Model is created is because it serves as the glue between a View and the Model. The
communication between the View and the View Model is fully taken care of by WPF in the form of Bindings. The problem is that most of the time,
a View Model is used to show a subset of a Model (which is, for example, a database entity).
Most MVVM frameworks (actually, I haven't seen anyone not requiring manual updating) require manual updating, which brings us back to the
stone age (remember the WinForms time setting the controls at startup, and reading the values at the end?). Catel solves this issue by providing
convenience attributes that take care of this dumb getting/setting story between the View Model and the Model. Catel fully supports getting/setting
the values from/to the Model, but believe me: you will love the attributes that are described next.

ModelAttribute
To be able to map values from/to a Model, it is important to know the actual Model. So, to let the View Model know what property represents the
Model, ModelAttribute can be used like shown below:

/// <summary>
/// Gets or sets the person.
/// </summary>
[Model]
public Person Person
{
get { return GetValue<Person>(PersonProperty); }
private set { SetValue(PersonProperty, value); }
}
/// <summary>
/// Register the Person property so it is known in the class.
/// </summary>
public static readonly PropertyData PersonProperty = RegisterProperty("Person",
typeof(Person));

A Model setter is normally written as private (you normally don't want a UI to be able to change a Model), but the getter is public because you
might want to read info from it.
Note that you should use the vmpropmodel code snippet to create Model properties

Models in Catel are handled as very, very special objects. This means that as soon as a Model is set, Catel tries to call the IEditableObject.Begin
Edit method. Then, as soon as the Model is changed without being saved, or if the View Model is canceled, the Model is correctly canceled via IE
ditableObject.CancelEdit. If the Model is saved, the active Models will be committed via IEditableObject.EndEdit. I will leave the rest of the magic
out of this article, but if you have any questions about it, don't hesitate to contact us!

ViewModelToModelAttribute
Now that we know how to declare a property has a Model, it is time to learn how we can communicate with it. Normally, you would have to watch
the Model to make sure it is synchronized correctly when the Model is updated. With Catel, this is not necessary any longer. Simply use ViewMod
elToModelAttribute, and you will get the following advantages:
Models are automatically being watched for changes, thus if a mapped property changes, the View Model is updated accordingly;
When a View Model is changed, this property is automatically mapped to the Model;
When the Model changes, the View Model is initialized automatically with the values of the new Model;
When a Model has an error or warning (business or field), the warnings are mapped to the View Model so you can re-use the validation
of the Model inside your View Model.
So, you get all of this for free? No, you will have to decorate your property with ViewModelToModelAttribute, like shown below:

/// <summary>
/// Gets or sets the first name.
/// </summary>
[ViewModelToModel("Person")]
public string FirstName
{
get { return GetValue<string>(FirstNameProperty); }
set { SetValue(FirstNameProperty, value); }
}
/// <summary>
/// Register the FirstName property so it is known in the class.
/// </summary>
public static readonly PropertyData FirstNameProperty = RegisterProperty("FirstName",
typeof(string));

The code example is the easiest usage of the attribute that is available. It only provides the name of the Model property. This is required because
it is possible (but not likely) to have multiple Models. But what if the property on your Model has a different name than your View Model? No
problem, use the overload of the attribute as shown below:

[ViewModelToModel("Person", "RealFirstName")]
public string FirstName
///... (remaining code left out for the sake of simplicity)

The code above will map the FirstName property of the View Model to the RealFirstName property of the Person model.

ExposeAttribute
The ViewModelToModelAttribute is a great way to map properties between the model and the view model. However, sometimes the mappings are
not required for manual coding and should only be exposed from inside the view model to the view. The ExposeAttribute is great way to simplify
this process. The code below is the same as declaring a model property named Person and 3 additional properties using the ViewModelToModel
Attribute:

/// <summary>
/// Gets or sets the person.
/// </summary>
[Model]
[Expose("FirstName")]
[Expose("MiddleName")]
[Expose("LastName")]
private Person Person
{
get { return GetValue<Person>(PersonProperty); }
set { SetValue(PersonProperty, value); }
}

/// <summary>
/// Register the Person property so it is known in the class.
/// </summary>
public static readonly PropertyData PersonProperty = RegisterProperty("Person",
typeof(Person));

This feature is only available in WPF because Silverlight does not provide the ICustomTypeDescriptor or an equivalent feature

Interaction with other view models


Now that we've seen how easy it is to communicate between the View Model and the Model, you want more, right? I know how it is: You let 'em
have one finger, they take your whole hand. No worries, you can have my right hand, as long as I can keep my left one. Anyway, the developers
of Catel are prepared for this. So, let's talk about the interaction with other View Models.
Say, you have a multiple document interface (MDI as it was called in the old days). If you are following MVVM principles, every document (or tab)
has its own View Model. Then, you want to be aware of updates of a single type of View Model. Say, for example, that there is a View Model
representing a family called FamilyViewModel. This View Model is probably interested in changes in the PersonViewModel.

ViewModelManager
Let's start with the basics. As we have learned earlier in this article, all View Models created with the help of Catel derive from the ViewModelBase
class. One of the things that this class does is that it registers itself with the ViewModelManager class when it is being created, and it unregisters
itself again when it is closed. So, simply said, ViewModelManager is a class that holds a reference to all existing View Models at the moment.

InterestedInAttribute
Now that we know about the ViewModelManager class, and know that there is a repository that holds all of the live instances of all View Model
classes, it should be fairly easy to communicate with other View Models. It actually is; you just have to decorate a View Model with InterestedInAtt
ribute, as shown below:

[InterestedIn(typeof(FamilyViewModel))]
public class PersonViewModel : ViewModelBase

A View Model can have multiple InterestedInAttribute instances, so it is possible to subscribe to multiple View Model types at the same time. Once
a View Model is decorated with InterestedInAttribute, the View Model will receive all changes (and of course, the View Model that caused the
change) via the OnViewModelPropertyChanged method, as shown below:

/// <summary>
/// Called when a property has changed for a view model type that the current view
model is interested in. This can
/// be accomplished by decorating the view model with the <see
cref="InterestedInAttribute"/>.
/// </summary>
/// <param name="viewModel">The view model.</param>
/// <param name="propertyName">Name of the property.</param>
protected override void OnViewModelPropertyChanged(IViewModel viewModel, string
propertyName)
{
// You can now do something with the changed property
}

Note that it is also possible to get notified of commands that are being executed on other view models

MessageMediator
Catel also offers a solution to the message mediator pattern in the form of the MessageMediator class. This is all described in the next section
"Message mediator".

Introduction to services
Services are very important in MVVM. They define a way to interact with the user without using fixed controls such as MessageBox or SaveFileDi
alog. The interfaces defined in Catel only define generic functionality of what to expect from a specific service. Using services is a great way to
abstract away all specific functionality from a view model into a service that can be mocked during unit testing and can be used by other view

models as well.

ServiceLocator
The key behind services is the ServiceLocator. The ServiceLocator is the IoC (Inversion of Control) container that Catel provides. This is a
container that contains all registrations and service instances available throughout the application. Retrieving services from the default ServiceLoc
ator in Catel is very simple:

var dependencyResolver = this.GetDependencyResolver();


var messageService = dependencyResolver.Resolve<IMessageService>();

It is also possible to get services injected into the constructor, which is the recommended approach

Dependency injection
A slightly better way to manage dependencies is to use dependency injection. The reason is that to instantiate a class, you always have to
provide all the dependencies. This way, all dependencies are always known to the caller which gives is a bit easier to control than having to know
what services are being used by a component (such as a view model).
Catel fully supports dependency on view models. This means that a view model can have a constructor with several services. Catel will
automatically inject the services via the constructor. An example is below:

public class PersonViewModel : ViewModelBase


{
private readonly IMessageService _messageService;
private readonly IPleaseWaitService _pleaseWaitService;
public PersonViewModel(IMessageService messageService, IPleaseWaitService
pleaseWaitService)
{
_messageService = messageService;
_pleaseWaitService = pleaseWaitService;
}
}

Overview of services
The services below are available in Catel:
Name

Description

IAccelerometerService

Allows a developer to access the accelerometer of a Windows Phone device.

ICameraService

Allows a developer to use the PhotoCamera class in an MVVM manner.

ICompassService

Allows a developer to access the compass of a Windows Phone device.

IGyroscopeService

Allows a developer to access the compass of a Windows Phone device.

ILocationService

Allows a developer to use GPS devices inside a view model.

IMessageService

Allows a developer to show message boxes from a view model.

INavigationService

Allows a developer to navigate to other pages inside an application using view models only.

IOpenFileService

Allows a developer to let the user choose a file from inside a view model.

IPleaseWaitService

Allows a developer to show a please wait message (a.k.a. busy indicator) from a view model.

IProcessService

Allows a developer to run processes from inside a view model.

ISaveFileService

Allows a developer to let the user choose a file from inside a view model.

IUIVisualizerService

Allows a developer to show (modal) windows or dialogs without actually referencing a specific view.

IVibrateService

Allows a developer to start and stop vibration of the device via a service.

Note that this section is not always fully up-to-date, Catel might provide more services than listed here

Introduction to the nested user controls problem


One of the issues most users of MVVM face is that nested user controls problem. The problem is that most (actually all that weve seen) MVVM
Frameworks only support one view model for a window (or if youre lucky, a user control). However, the nested user controls problem raises lots
of questions:
What if the requirements are to build a dynamic UI where the nested user controls are loaded dynamically when they are required?
What about validation in nested user controls?
When should the nested user control view models be saved?
Most MVVM developers just answer: Put all the properties of the nested user controls on the main view model. Say that again? Are you kidding
me? Thats not a real world solution for a real world problem. So, we as developers of Catel offer you a real world solution for the nested user
controls problem in the form of the UserControl.
The real power of the UserControl class lays in the fact that it is able to construct view models dynamically based on its data context. So, the only
thing the developers have to take care of is to set the right data context. Below is a graphical presentation of the nested user controls problem:

As the images above show, the method that Catel uses to solve the problem is much more professional. Below are a few reasons:
Separation of concerns (each control has a view model only containing the information for itself, not for children);
User controls are built so they can be re-used. Without the user controls to be able to have their own view models, how should one
actually use user controls with MVVM?
The idea behind the user control is pretty complex, especially because WPF (and thus Silverlight and WP7) isnt very good at runtime data
context type changing. However, with a few workarounds (very well described in the source code of UserControl), it is possible to dynamically
construct view models. The user control constructs the view model with or without a constructor as described earlier in this article. When the view
model is constructed, the user control tries to find a (logical or visual) parent that implements the IViewModelContainer interface. Thanks to this
interface, a view model can subscribe itself to a parent view model and the validation chain is created as shown below:

As the image above shows, all children in the chain are validated, and when the last child is validated, the view model reports the result of its
children and itself back to its parent. This way, it is still possible to disable a command when one of the nested user control view models has an
error.
Saving a chain of nested view models works exactly the same as the validation. First, the view model saves all children, then itself and finally
reports back its result to the parent.
Now, lets go to some real-life example. I dont want to make it too complex, but not too easy as well, but dont want to put the focus on the
content of the data, but on the user control and view model creation. Therefore, I have chosen for the data model below:

The image shows that we have a house. In that house, we have multiple rooms. In each room, there can be several tables with chairs and beds.
This shows a complex UI tree with lots of different user controls (each object has its own representation and thus user control). Now our goal is
to create user controls that can be used in the window that shows the full house, but also in sub-parts and we want to be fully independent of the
HouseWindowViewModel (which is the only view model that would be created in a regular MVVM Framework).
The example below shows only the Room control and the corresponding view model. The full source code of this article is provided in the source
code repository of Catel, so the whole example is available if you are interested or need a more complete example.
First, we start with a simple model. For the model, we use the ModelBase class. By using the provided code snippets, this model is setup within a
minute:

/// <summary>
/// Bed class which fully supports serialization, property changed notifications,
/// backwards compatibility and error checking.
/// </summary>
[Serializable]
public class Room : ModelBase<Room>
{
#region Constructor & destructor
/// <summary>
/// Initializes a new object from scratch.
/// </summary>
public Room()
: this(NameProperty.GetDefaultValue<string>()) { }

/// <summary>
/// Initializes a new instance of the <see cref="Room"/> class.
/// </summary>
/// <param name="name">The name.</param>
public Room(string name)
{
// Create collections
Tables = new ObservableCollection<Table>();
Beds = new ObservableCollection<Bed>();
// Store values
Name = name;
}
/// <summary>
/// Initializes a new object based on <see cref="SerializationInfo"/>.
/// </summary>
/// <param name="info"><see cref="SerializationInfo"/> that contains the
information.</param>
/// <param name="context"><see cref="StreamingContext"/>.</param>
protected Room(SerializationInfo info, StreamingContext context)
: base(info, context) { }
#endregion

#region Properties
/// <summary>
/// Gets or sets the name.
/// </summary>
public string Name
{
get { return GetValue<string>(NameProperty); }
set { SetValue(NameProperty, value); }
}
/// <summary>
/// Register the Name property so it is known in the class.
/// </summary>
public static readonly PropertyData NameProperty = RegisterProperty("Name",
typeof(string), "Room");
/// <summary>
/// Gets or sets the table collection.
/// </summary>
public ObservableCollection<Table> Tables
{
get { return GetValue<ObservableCollection<Table>>(TablesProperty); }
set { SetValue(TablesProperty, value); }
}
/// <summary>
/// Register the Tables property so it is known in the class.
/// </summary>
public static readonly PropertyData TablesProperty = RegisterProperty("Tables",
typeof(ObservableCollection<Table>));
/// <summary>
/// Gets or sets the bed collection.
/// </summary>
public ObservableCollection<Bed> Beds

{
get { return GetValue<ObservableCollection<Bed>>(BedsProperty); }
set { SetValue(BedsProperty, value); }
}
/// <summary>
/// Register the Beds property so it is known in the class.
/// </summary>
public static readonly PropertyData BedsProperty = RegisterProperty("Beds",

typeof(ObservableCollection<Bed>));
#endregion
}

Next, we are going to create the view model. Again, by the use of code snippets explained earlier in this article, the view model is set up within a
few minutes:

/// <summary>
/// Room view model.
/// </summary>
public class RoomViewModel : ViewModelBase
{
#region Variables
private int _bedIndex = 1;
private int _tableIndex = 1;
#endregion
#region Constructor & destructor
/// <summary>
/// Initializes a new instance of the <see cref="RoomViewModel"/> class.
/// </summary>
public RoomViewModel(Models.Room room)
{
// Store values
Room = room;
// Create commands
AddTable = new Command(OnAddTableExecuted);
AddBed = new Command(OnAddBedExecuted);
}
#endregion
#region Properties
/// <summary>
/// Gets the title of the view model.
/// </summary>
/// <value>The title.</value>
public override string Title { get { return "Room"; } }
#region Models
/// <summary>
/// Gets or sets the room.
/// </summary>
[Model]
public Models.Room Room
{
get { return GetValue<Models.Room>(RoomProperty); }
private set { SetValue(RoomProperty, value); }
}
/// <summary>
/// Register the Room property so it is known in the class.
/// </summary>
public static readonly PropertyData RoomProperty = RegisterProperty("Room",
typeof(Models.Room));
#endregion
#region View model

/// <summary>
/// Gets or sets the name.
/// </summary>
[ViewModelToModel("Room")]
public string Name
{
get { return GetValue<string>(NameProperty); }
set { SetValue(NameProperty, value); }
}
/// <summary>
/// Register the Name property so it is known in the class.
/// </summary>
public static readonly PropertyData NameProperty = RegisterProperty("Name",
typeof(string));
/// <summary>
/// Gets or sets the table collection.
/// </summary>
[ViewModelToModel("Room")]
public ObservableCollection<Models.Table> Tables
{
get { return GetValue<ObservableCollection<Models.Table>>(TablesProperty); }
set { SetValue(TablesProperty, value); }
}
/// <summary>
/// Register the Tables property so it is known in the class.
/// </summary>
public static readonly PropertyData TablesProperty = RegisterProperty("Tables",
typeof(ObservableCollection<Models.Table>));
/// <summary>
/// Gets or sets the bed collection.
/// </summary>
[ViewModelToModel("Room")]
public ObservableCollection<Models.Bed> Beds
{
get { return GetValue<ObservableCollection<Models.Bed>>(BedsProperty); }
set { SetValue(BedsProperty, value); }
}
/// <summary>
/// Register the Beds property so it is known in the class.
/// </summary>
public static readonly PropertyData BedsProperty = RegisterProperty("Beds",
typeof(ObservableCollection<Models.Bed>));
#endregion
#endregion
#region Commands
/// <summary>
/// Gets the AddTable command.
/// </summary>
public Command AddTable { get; private set; }
/// <summary>
/// Method to invoke when the AddTable command is executed.
/// </summary>

private void OnAddTableExecuted()


{
Tables.Add(new Models.Table(string.Format("Table {0}", _tableIndex++)));
}
/// <summary>
/// Gets the AddBed command.
/// </summary>
public Command AddBed { get; private set; }
/// <summary>
/// Method to invoke when the AddBed command is executed.
/// </summary>
private void OnAddBedExecuted()
{
Beds.Add(new Models.Bed(string.Format("Bed {0}", _bedIndex++)));

}
#endregion
}

As you can see, the view model can only be constructed by passing a Room model object. It is very important to be aware of this construction.
The reason that there is no empty constructor is because there is no support for views that do not represent a Room model.
In the view model, the properties of the Room model are mapped by the use of the Model attribute and the ViewModelToModel attribute. Last but
not least, commands are defined to be able to add new tables and beds to the Room model.
Another way to add a new user control is to use the item templates

Now the model and the view model are fully set up, the last thing to do is to create the actual view. To accomplish this, add a new WPF user
control to the project. First thing to do is to implement the code-behind, since that is the easiest to do:

<summary>
/// Interaction logic for Room.xaml
/// </summary>
public partial class Room : UserControl
{
/// <summary>
/// Initializes a new instance of the <see cref="Room"/> class.
/// </summary>
public Room()
{
// Initialize component
InitializeComponent();
}
}

The only thing we changed from the default user control template is that the user control now derives from Catel.Windows.Controls.UserControl c
ontrol instead of the default System.Windows.Controls.UserControl control. This is it for the code-behind, lets move up to the view.
The last thing to do now is the actual xaml view. For the sake of simplicity, the actual content is left out (its just a grid with a textbox and
itemscontrols for the children):

<catel:UserControl
x:Class="Catel.Articles._03___MVVM.Examples.NestedUserControls.Room"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:catel="http://catel.codeplex.com"
xmlns:NestedUserControls="clr-namespace:Catel.Articles._03___MVVM.Examples.NestedUserC
ontrols">
<!-- For the sake of simplicity, the content is left out -->
</catel:UserControl>

A few things are very important to notice in the xaml code shown above. The first thing to notice is that (like the code-behind), the base class is
now catel:UserControl instead of UserControl.
Thats all that can be learned about solving the nested user control problem. We have set up the model, view model and finally the view. Now,
lets take a look at how it looks in a screenshot (and notice the construction time of the view model, they are really constructed on-demand):

The red border is the control that we just created. It shows the name of the room, the view model construction time and the child objects (inside
expanders).

Introduction to unit testing in MVVM


If you are wondering why you should even write unit tests, you should also wonder why you arent still living in a cage and writing stuff on the
walls (don't feel offended, continue reading...). Writing unit tests makes sure that you dont break existing functionality in an application when
making changes. This lowers the cost of QA (since you dont need a technical tester executing regression tests all the time). I dont say that a
tester isnt needed; my opinion is that at least someone else besides the developer should take a human look at the software before it is even
released. If you are still not convinced why you should write unit tests, please go back to your cave and stop reading this article for the sake of
your own pleasure.
This documentation does not cover the basics of unit testing. It assumes that you already know what unit tests are, and how to write them. This
documentation is specifically written to explain how view models of the MVVM pattern can be unit tested, especially with the use of Catel.

Testing commands
Thanks to commands (which implement the ICommand interface), testing view models and UI logic has never been so easy. Now commands can
be invoked programmatically without having to automate the UI; it is very simple to reproduce a button click during a unit test.
When testing commands, it is very important to test the state as well. The command implementation of Catel has a CanExecute and an Execute
method which can be invoked manually. Therefore, it is very easy to test a command. The code below shows a test that checks whether the Rem
ove command can be executed. At first, the command cannot be executed because there is no selected person. After the selected person is set,
the command should be able to execute:

Assert.IsFalse(mainWindowViewModel.Remove.CanExecute(null));
mainWindowViewModel.SelectedPerson = mainWindowViewModel.PersonCollection[0];
Assert.IsTrue(mainWindowViewModel.Remove.CanExecute(null));

To execute a command in code, one should use the following code:

mainWindowViewModel.Remove.Execute(null);

Testing services
For more information about unit testing services, see the unit testing services documentation.

Introduction to MVC
Note that this documentation has to be written

FAQ
Welcome to the FAQ. Please pick a section:
General
MVVM

General
I want to change the bitmap effects, what should I do?
StyleHelper.CreateStyleForwardersForDefaultStyles does not work in Silverlight

I want to change the bitmap effects, what should I do?


1. Download the DirectX SDK
2. Compile the .fx file into a .ps file using the following command: "$(DXSDKDIR)Utilities\Bin\x86\fxc.exe" /T ps2_0 /E main /Fo
"MyEffect.ps" "MyEffect.fx"
3. Now, the fx file is updated and Catel should be recompiled

StyleHelper.CreateStyleForwardersForDefaultStyles does not work in Silverlight


Probably, the application resources are defined like this:

<Application xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
x:Class="MyApp">
<Application.Resources>
<ResourceDictionary Source="/CWP.Shared;component/themes/generic.xaml" />
</Application.Resources>
</Application>

However, Silverlight does not allow to add resources to a ResourceDictionary where the source is set. To be able to use default styles, use this
code:

<Application xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
x:Class="MyApp">
<Application.Resources>
<ResourceDictionary>
<ResourceDictionary.MergedDictionaries>
<ResourceDictionary Source="/MyApp.Shared;component/themes/generic.xaml" />
</ResourceDictionary.MergedDictionaries>
</ResourceDictionary>
</Application.Resources>
</Application>

MVVM
How to support example data with view models?
How to use events with MVVM?
Silverlight throws error about type that cannot be created?
How can I add the MVVM behaviors via code (programmatically)?
How can I inject or manipulate the view model of a UserControl?
How can I prevent validation of required fields?

How to support example data with view models?


To find out how to create design time data, see the designers topic.

How to use events with MVVM?


When writing MVVM, it's "forbidden" (read: not a best practice) to use click handlers (or other UI events) in your view-model. But then should you
react to events?
1. Start with creating a command like you are used to using MVVM. This command will be executed when the event occurs.
2. Add a reference to System.Windows.Interactivity.dll (ships with Catel). If you have used NuGet to add a reference, it is automatically
included for you.
3. Add the following namespace definitions to your view declaration:

xmlns:i="clr-namespace:System.Windows.Interactivity;assembly=System.Windows.Inter
activity"
xmlns:catel="http://catel.codeplex.com"

4. Use the following code to convert an event to a command:

4.

<i:Interaction.Triggers>
<i:EventTrigger EventName="[YourEvent]">
<catel:EventToCommand Command="{Binding [YourCommand]}"
DisableAssociatedObjectOnCannotExecute="False" />
</i:EventTrigger>
</i:Interaction.Triggers>

An example for a ListBox double click:

<ListBox ItemsSource="{Binding PersonCollection}" SelectedItem="{Binding


SelectedPerson}">
<i:Interaction.Triggers>
<i:EventTrigger EventName="MouseDoubleClick">
<catel:EventToCommand Command="{Binding Edit}"
DisableAssociatedObjectOnCannotExecute="False" />
</i:EventTrigger>
</i:Interaction.Triggers>
<ListBox.ItemTemplate>
<DataTemplate>
<StackPanel Orientation="Horizontal">
<Label Content="{Binding FirstName}" />
<Label Content="{Binding MiddleName}" />
<Label Content="{Binding LastName}" />
</StackPanel>
</DataTemplate>
</ListBox.ItemTemplate>
</ListBox>

Silverlight throws error about type that cannot be created?


If you are using type creation via xaml this way:

<i:Interaction.Behaviors>
<catel:WindowBehavior ViewModelType="viewmodels:DemoWindowViewModel"
Save="okButton.Click" Cancel="cancelButton.Click" />
</i:Interaction.Behaviors>

It might be possible that Silverlight throws an exception with these details:

{System.Windows.Markup.XamlParseException: Failed to create a 'System.Type' from the


text 'ViewModels:DemoWindowViewModel'. [Line: 13 Position: 67]
at System.Windows.Application.LoadComponent(Object component, Uri resourceLocator)
at Catel.Examples.AdvancedDemo.Views.LogicInBehavior.DemoWindow.InitializeComponent()
at Catel.Examples.AdvancedDemo.Views.LogicInBehavior.DemoWindow..ctor()}

This happens in Silverlight 4 when the Silverlight 5 (beta) tools are not installed. To resolve this issue, install the Silverlight 5 (beta) tools.

How can I add the MVVM behaviors via code (programmatically)?

Silverlight has a known issue, and sometimes installing the Silverlight 5 (beta) toolkit isn't the right option to solve the issue. Luckily, it is also
possible to add one of the MVVM behaviors via code to any control or window.
Below is the code-behind of a view that adds the UserControlBehavior via code:

public partial class DynamicBehaviorView : UserControl, IViewModelContainer


{
private Catel.Windows.Controls.MVVMProviders.UserControlBehavior _mvvmBehavior;
/// <summary>
/// Initializes a new instance of the <see cref="DynamicBehaviorView"/> class.
/// </summary>
public DynamicBehaviorView()
{
InitializeComponent();
_mvvmBehavior = new Catel.Windows.Controls.MVVMProviders.UserControlBehavior();
_mvvmBehavior.ViewModelType = typeof(ViewModels.MyViewModel);
System.Windows.Interactivity.Interaction.GetBehaviors(this).Add(_mvvmBehavior);
_mvvmBehavior.ViewModelChanged += (sender, e) =>
ViewModelChanged.SafeInvoke(this, e);
_mvvmBehavior.ViewModelPropertyChanged += (sender, e) =>
ViewModelPropertyChanged.SafeInvoke(this, e);
}
/// <summary>
/// Gets the view model that is contained by the container.
/// </summary>
/// <value>The view model.</value>
public IViewModel ViewModel
{
get { return _mvvmBehavior.ViewModel; }
}
/// <summary>
/// Occurs when the <see cref="ViewModel"/> property has changed.
/// </summary>
public event EventHandler<EventArgs> ViewModelChanged;
/// <summary>
/// Occurs when a property on the <see cref="ViewModel"/> has changed.
/// </summary>
public event EventHandler<PropertyChangedEventArgs> ViewModelPropertyChanged;
#if !SILVERLIGHT
/// <summary>
/// Occurs when a property on the container has changed.
/// </summary>
/// <remarks>
/// This event makes it possible to externally subscribe to property changes of a
<see cref="DependencyObject"/>
/// (mostly the container of a view model) because the .NET Framework does not
allows us to.
/// </remarks>
public event EventHandler<PropertyChangedEventArgs> PropertyChanged;
/// <summary>
/// Invoked whenever the effective value of any dependency property on this <see
cref="T:System.Windows.FrameworkElement"/> has been updated. The specific dependency
property that changed is reported in the arguments parameter. Overrides <see

cref="M:System.Windows.DependencyObject.OnPropertyChanged(System.Windows.DependencyPro
pertyChangedEventArgs)"/>.
/// </summary>
/// <param name="e">The event data that describes the property that changed, as
well as old and new values.</param>
protected override void
OnPropertyChanged(System.Windows.DependencyPropertyChangedEventArgs e)
{
base.OnPropertyChanged(e);
PropertyChanged.SafeInvoke(this, new PropertyChangedEventArgs(e.Property.Name));

}
#endif
}

Using this technique, it is even possible to determine the view model of any view dynamically at runtime.

How can I inject or manipulate the view model of a UserControl?


The UserControl is a very powerful control. It allows lazy loaded dynamic view model construction. However, sometimes you just don't want the
user control to dynamically create the view model. Luckily, the user control instantiates a new view model with this logic:
1. The DataContext of the control can be injected into a constructor of the view model
2. The view model has an empty constructor
You can set the DataContext of the control to a view model, and this way "inject" a view model into a control instead of letting it be created first. In
fact, the user control first checks whether the DataContext is already a valid view model for the user control. If so, it keeps it that way.

How can I prevent validation of required fields?


Catel does not validate the properties with data annotations at startup. It will only validate the data annotations when properties change or when
the view model is about to be saved. This is implemented this way to allow a developer to show required fields with an asterisk (*) instead of
errors. If a developer still wants to initially display errors, only a single call has to be made in the constructor:

Validate(true, false);

If the validation is implemented in the models and not in the view model, set the ValidateModelsOnInitialization to false.

Setup, deployment and projects


Getting prerelease (beta) versions via NuGet
Stepping through the code
Compiling from source
Code snippets & templates
Updating to a new version via NuGet
Update guides

Getting prerelease (beta) versions via NuGet


Starting on December 21, 2011, beta versions of Catel are published to NuGet. This way, it is possible to give users that like to live on the edge a
change to update their packages via NuGet.
Installing via package manager
Installing via package manager console

Installing via package manager


Please make sure to select the same settings as in the screenshow below:

Installing via package manager console


This example installs Catel.Extensions.Controls as a package. However, to install other packages simple change the ID (name) of the package.
Installing the latest beta

Install-Package Catel.Extensions.Controls IncludePrerelease

Installing a specific beta

Install-Package Catel.Extensions.Controls IncludePrerelease -version


4.0.0-unstable0532

Updating to the latest beta

Update-Package Catel.Extensions.Controls IncludePrerelease

Updating to a specific beta

Update-Package Catel.Extensions.Controls IncludePrerelease -version


4.0.0-unstable0532

Updating to the latest stable version

Update-Package Catel.Extensions.Controls

Stepping through the code


It is possible to step through the source code of Catel. This will give great insights when debugging applications because you can actually see
what is happening inside Catel.
To enable stepping through the source code, use the following steps:
1. Install any Catel package via NuGet (all have support for stepping through the code)
2. Enable source server support in Visual Studio:

Note that Visual Studio 2012 needs to run elevated in order to download the source server files due to a bug in Visual Studio 2012

Compiling from source


In order to compile, the following 3rd party software is r equired:
Visual Studio 2013 Update 2 (to support Shared Projects)
Silverlight 5 tools
Windows Phone 8 tools
Xamarin (if you want to compile this part)
All other libraries required are located inside the lib folder or are retrieved via NuGet.

Code snippets & templates


The latest code snippets and templates are available on the official website. When downloaded, follow the steps below to install them.

Installing the code snippets

Extract the zip file to the following directory: %MyDocuments%\Visual Studio 2xxx\Code Snippets

Installing the item and project templates


C#
Extract the zip\C#\ItemTemplates to the following directory: %MyDocuments%\Visual Studio 2xxx\Templates\ItemTemplates\Visual C#
Extract the zip\C#\ProjectTemplates to the following directory: %MyDocuments%\Visual Studio 2xxx\Templates\ProjectTemplates\Visual C#

VB.NET
Extract the zip\VB.NET\ItemTemplates to the following directory: %MyDocuments%\Visual Studio 2xxx\Templates\ItemTemplates\Visual Basic
Extract the zip\VB.NET\ProjectTemplates to the following directory: %MyDocuments%\Visual Studio 2xxx\Templates\ProjectTemplates\Visual
Basic

It's possible that you need to restart Visual Studio for it to recognize the templates

Using the code snippets


Using the item templates
Using the project templates

Using the code snippets


This part of the documentation explains all the code snippets.
Code snippet

Explanation

modelobject

Defines a model using the ModelBase class.

modelprop

Defines a new property on a model class.

modelpropchanged

Defines a new property with change notification on a model class.

vm

Defines a new view model.

vmcommand

Defines a new view model command with only an executed action.

vmcommandwithcanexecute

Defines a new view model command with an executed action, but also a canexecute function.

vmprop

Defines a new property on a view model.

vmpropmodel

Defines a new property on a view model and decorates it with the ModelAttribute.

vmpropviewmodeltomodel

Defines a new property on a view model and decorates it with the ViewModelToModelAttribute.

Using the item templates


There are lots of item templates available for Catel so it is really easy to develop new views very fast.

Difference between logic in view base or behavior


As you might have noticed, there are lots of "double" item templates. However, there is a substantial difference between the item templates that
implement the logic in the view base or the logic in a behavior.
Shortly said, a view with the logic in the view base is defined like this:

public class MyView : Catel.Windows.Controls.UserControl


{
// rest of the class definition
}

This means that the logic for MVVM is located in the view base (in this example, the UserControl).
An item template where the logic is located in a behavior uses regular controls and uses one of the available MVVM behaviors to implement the
logic. The behaviors are extremely powerful, but we still recommend the use of logic in the view base since that takes more work out of the hands
from the developer.

View model
The view model is the easiest and smallest item template available. The question is even whether a new view model should be created via an
item template or by using the vm code snippet.

User control
The user control templates create a user control deriving from UserControl. First it is very important to make a decision whether the logic should
be implemented in the view base or a behavior. Then, select the appropriate template:

The item template will assume that a view model with the same name is already created. For example, if a view with the name PersonView is
created, the template assumes that the view model name is PersonViewModel. If you prefer a different naming convention, simply change the
view model type name after the item has been created.
Unfortunately, there is a bug in the item templates system of Visual Studio so it is not possible to also set the namespace of the view
models to [ProjectRootNamespace].ViewModels, so this has to be done manually

Window
The window templates create a window deriving from DataWindow. First it is very important to make a decision whether the logic should be
implemented in the view base or a behavior. Then, select the appropriate template:

The item template will assume that a view model with the same name is already created. For example, if a view with the name PersonView is
created, the template assumes that the view model name is PersonViewModel. If you prefer a different naming convention, simply change the
view model type name after the item has been created.
Unfortunately, there is a bug in the item templates system of Visual Studio so it is not possible to also set the namespace of the view
models to [ProjectRootNamespace].ViewModels, so this has to be done manually

Using the project templates


There are several project templates available for Catel. The easiest way is to follow these steps.

Using the project templates


Create a new project. Make sure that at least .NET Framework 4.0 is selected as target framework. The templates can be found under the Catel
folder as shown in the image below:

As soon as the project is created, the only thing left to do is add references to the Catel libraries. You can either do this manually or use NuGet.

Updating to a new version via NuGet


NuGet makes the life very easy for developers. You can simply add new dependencies to projects via the package manager. However, there are
some pitfalls one has to be aware of. If you are using NuGet to install Catel packages, please use this guide to update Catel to a new version.
The pitfall
How to update without causing problems

The pitfall
Catel ships with many different extensions. This means that each extensions ships in its own NuGet package. This might cause NuGet packages
to be installed with different versions throughout the solution. Assume the solution below:
MyProject.DAL => contains Catel.Core (3.5)
MyProject => contains Catel.Core (3.5), Catel.MVVM (3.5)
When you go to the NuGet package manager, you will notice that updates are available. When you just click update on Catel.MVVM, you will end
up with a version mismatch, which is shown below:
MyProject.DAL => contains Catel.Core (3.5)
MyProject => contains Catel.Core (3.6), Catel.MVVM (3.6)
This is because NuGet will install Catel.MVVM (3.6) which has a dependency on Catel.Core (3.6). Because it notices this dependency, it will
automatically update Catel.Core, but only for the MyProject project, not for all projects. Now there is a mismatch and you won't be able to update
the MyProject.DAL anymore via the NuGet package manager because it already notices that you already installed Catel.Core 3.6 somewhere
else.

How to update without causing problems


To prevent the pitfall described above, below are some simple steps. If you follow these steps, you will never have any issues with version
dependencies that go wrong.

1. Right-click on the solution => manage NuGet packages


2. Go to Updates and search for Catel as you can see in the image below:

3. Make sure to Update in the following order:


1. Catel.Core
2. Catel.MVVM (if used)
3. Any other extensions can now be updated without any issues

Update guides
This section of the documentation describes how to update to a new version of Catel. This guide does only cover direct version transitions (thus
3.9 => 4.0, not 3.6 => 4.0).
Catel 4.0.0
Catel 4.1.0

Catel 4.0.0
This guide describes how to update your code to be fully compatible with Catel 4.0.0.
Renaming classes
Renaming namespaces
Simplied ModelBase external interfacing
Renamed LoadTabItemsBehavior
Add additional members to custom IView implementations
Using FastViewPropertySelector by default for major performance improvement
Manually add interesting properties (recommended)
Register the ViewPropertySelector
Full support for asynchronous (async/await)
IViewModel
Updating Initialize method
Updating Save method
Updating Close method
IMessageService
IUIVisualizerService
Optimizing views (especially 3rd party)
Removed IServiceLocator.RemoveInstance methods

Changed CompositeCommand
Added time to all log calls
Behavior changes

Renaming classes
Some classes in Catel have been renamed.
Catel.Environment => CatelEnvironment
IDependencyPropertySelector => IViewPropertySelector

Renaming namespaces
Some namespaces in Catel have been changed to match the functionality. For example, all services are now in Catel.Service instead of Catel.MV
VM.Services because they can be used without MVVM.
Below is a list of changed namespaces:
Catel.MVVM.Services => Catel.Services
Catel.Windows.Data.Converters => Catel.MVVM.Converters
Catel.Windows.Controls.MVVMProviders.Logic => Catel.MVVM.Providers
Some interfaces were moved (but not all classes in the namespace):
Catel.Windows => Catel.MVVM.Views

Simplied ModelBase external interfacing


The ModelBase class exposed a lot of properties for validation such as HasErrors, HasFieldErrors, HasBusinessRuleErrors, etc. These all these
properties are now explicitly implemented into interfaces to make models using ModelBase cleaner to use for end-developers. Below is a list of
properties that are now implemented as explicit interface implementations:
Member name

Explicit interface implementation

Member type

BusinessRuleErrorCount

IModelValidation.BusinessRuleErrorCount

property

BusinessRuleWarningCount

IModelValidation.BusinessRuleWarningCount

property

Deserialized

IModelSerialization.Deserialized

event

ErrorsChanged

INotifyDataErrorInfo.ErrorsChanged

event

FieldErrorCount

IModelValidation.FieldErrorCount

property

FieldWarningCount

IModelValidation.FieldWarningCount

property

HasErrors

INotifyDataErrorInfo.HasErrors

property

HasWarnings

INotifyDataWarningInfo.HasWarnings

property

ValidationContext

IModelValidation.ValidationContext

property

Validator

IModelValidation.Validator

property

WarningsChanged

INotifyDataWarningInfo.WarningsChanged

event

Renamed LoadTabItemsBehavior
The LoadTabItemsBehavior has been refactored with new names. The old names will be removed in v5, but will error in v4. Below are the
renames:
Single => LazyLoading
SingleUnloadOthers => LazyLoadingUnloadOthers
AllOnStartup => EagerLoading
AllOnFirstUse => EagerLoadingOnFirstUse

Add additional members to custom IView implementations


To support Xamarin, the IView interface has been extended with new members. Make sure to implement the new members.

Using FastViewPropertySelector by default for major performance improvement


When not using the ViewToViewModel attributes, it is not required to subscribe to all dependency properties in the UserControlLogic. Starting
from Catel 4.0, Catel uses the FastViewPropertySelector by default which subscribes to no properties by default. This is a breaking change for
users using the ViewToViewModel attribute.
To get back the behavior, there are 2 ways:

Manually add interesting properties (recommended)


It is best to let Catel only subscribe to the properties that it should (for the best performance). To do so, use the IViewPropertySelector.AddProper
tyToSubscribe method to add properties:

var serviceLocator = ServiceLocator.Default;


var viewPropertySelector = serviceLocator.ResolveType<IViewPropertySelector>();

viewPropertySelector.AddPropertyToSubscribe("MyProperty", typeof(MyView));

In most cases, the only reason to subscribe to property changes is because of the ViewToViewModel attribute. If that is the case, it is best to use
the extension method AutoDetectViewPropertiesToSubscribe in the static constructor of the view:

static MyView()
{
typeof(MyView).AutoDetectViewPropertiesToSubscribe();
}

Register the ViewPropertySelector


The default implementation of the ViewPropertySelector subscribes to all properties by default. By registering it in the ServiceLocator will ensure
Catel subscribes to all dependency properties:

var serviceLocator = ServiceLocator.Default;


serviceLocator.RegisterType<IViewPropertySelector, ViewPropertySelector>();

Full support for asynchronous (async/await)


IViewModel
The IViewModel interface now returns tasks instead of direct values to support async/await.

Updating Initialize method


public override void Initialize()
{
base.Initialize();
}

Must be changed in:

public override async Task Initialize()


{
await base.Initialize();
}

Updating Save method


public override bool Save()
{
return base.Save();
}

Must be changed in:

public override async Task<bool?> Save()


{
return await base.Save();
}

Updating Close method


public override void Close()
{
base.Close();
}

Must be changed in:

public override async Task Close()


{
await base.Close();
}

IMessageService
The use of await or Task.ContinueWith to await the result is now necessary or use the code below:

if (await messageService.ShowInfo("message", other parameters...) ==


MessageBoxResult.Yes)
{
// Handle yes here
}

IUIVisualizerService
The use of await or Task.ContinueWith to await the result is now necessary or use the code below:

await uiVisualizerService.ShowDialog<MyViewModel>();
// Window is closed here thanks to the await keyword

Optimizing views (especially 3rd party)


Catel 4.0 introduces a much simpler way to use Catel on 3rd party controls. This means that the following changes have been applied and might
be breaking:
Removed GetViewModelType() from view base classes. Instead use the IViewModelLocator to ensure Catel can find the view models.
Note that it is possible to manually register a custom view with a view model in case the view / view model don't match any naming
convention.
Removed GetViewModelInstance() from view base classes. Customize the IViewModelFactory instead.
Removed ValidateData, DiscardChanges and ApplyChanges from all views except DataWindow
Merged ViewLoaded and Loaded events on IViewModelContainer and IView interfaces
Renamed ViewLoading and ViewUnloading events on IViewModelContainer to Loading and Unloading
Renamed IViewLoadedManager to IViewLoadManager

Removed IServiceLocator.RemoveInstance methods


The IServiceLocator.Remove[x] methods are removed. Use the RemoveType methods instead.

Changed CompositeCommand
The composite command will always allow execution, even when commands don't allow it. Therefore the AllowPartialExecution is now set to false
by default.
If there is a requirement to allow partial invocation, set this property to true.

Added time to all log calls


The time parameter has been added to all log calls. This is a breaking change for all classes implementing ILogListener.

Behavior changes
To improve multiple platforms support, all parameters of the following methods on BehaviorBase have been removed:

OnAssociatedObjectLoaded(object sender, EventArgs e) => OnAssociatedObjectLoaded()


OnAssociatedObjectUnloaded(object sender, EventArgs e) => OnAssociatedObjectUnloaded()

Catel 4.1.0
This guide describes how to update your code to be fully compatible with Catel 4.1.0.
This guide assumes that you are coming from Catel 4.0.0. If not, please read that guide first.

IUIVisualizerService

IUIVisualizerService
We have reverted the change to force you to use async code on the IUIVisualizerService. There are now 2 options:

1. Synchronous:

var result = uiVisualizerService.ShowDialog<MyViewModel>();


// Window is closed here (synchronous behavior)

2. Asynchronous:

var result = await uiVisualizerService.ShowDialogAsync<MyViewModel>();


// Window is closed here thanks to the await keyword

Getting started
The getting started series focuses on the main features of Catel.
Quick introduction for developers
Getting started with WPF

Quick introduction for developers


This is a quick introduction for developers who don't have a lot of time to read all the docs. This document contains the absolute basics of what a
developer needs to know.
Core
Logging / debugging
Catel properties
MVVM
Handling of viewmodels
Handling hierarchy and parent/child view models
Communication between view models
Resolving views and view models

Core
This pare contains the core functionality of Catel and what you should know when using Catel.

Logging / debugging
If you ever think Catel is behaving strange or does not work as expected, make sure to enable the logging. Below is an example on how to enable
the logging:

#if DEBUG
LogManager.RegisterDebugListener();
#endif

Catel will then log everything to the output window and provide all the information about its internals.
For more information, read about logging.

Catel properties
All properties in classes deriving from ModelBase (thus also ViewModelBase) require a special property definition.

Normally one would write something like this:

private string _firstName;


public string FirstName
{
get { return _firstName; }
set
{
RaisePropertyChanging("FirstName");
_firstName = value;
RaisePropertyChanged("FirstName");
}
}

In Catel one should write this:

public string FirstName


{
get { return GetValue< string>(FirstNameProperty); }
set { SetValue(FirstNameProperty, value); }
}
public static readonly PropertyData FirstNameProperty = RegisterProperty("FirstName",
typeof(string), null);

Catel will automatically take care of change notifications.


Note that you can use the modelprop or vmprop to easily create these properties using code snippets. You can also use Catel.Fody inst
ead

MVVM
This part is especially meant for the MVVM part.

Handling of viewmodels
In other MVVM frameworks, you are obliged to set the data context of a view manually. It will look something like this:

var view = new PersonView();


view.DataContext = new PersonViewModel();

Catel automatically resolves the right view model based on the view. If a view is created, Catel automatically creates the view model:

var view = new PersonView();


// view model is automatically created

It goes even further. Catel can create view models based on the data context. For more information, read nested user controls.

Handling hierarchy and parent/child view models


Note that Catel is already fully aware of parent/child relations of view models so you dont have to do anything

for this yourself. For more information, read nested user controls.
Communication between view models
There are several methods available to communicate between view models. Just make sure that you never directly reference other view model
and keep everything loosely coupled.

Resolving views and view models


Catel resolves views and view models by naming convention. This means that based on the name of a view, the view model can be determined.
This also works the other way around where the view model can be determined based on the view. For more information, read about naming
conventions.

Getting started with WPF


Welcome to the Getting started guide for Catel and WPF. In this guide, a very simple application will be created with the most commonly used
aspects of Catel and WPF.
The application will manage family members and will display the families in separate views.
Note that this guide assumes that the reader has a basic understanding of XAML and WPF since this guide will not cover these basics

Note that this guide will recommend code snippets that can be found here. They are not required, just recommended to speed up
creating Catel classes and properties.
Creating the project
Creating the models
Serializing data from/to disk
Creating the view models
Creating the views (user controls)
Creating the views (windows)
Hooking up everything together
Finalizing the application
Download the final result: WPF.GettingStarted.zip

Creating the project


In this step we will create the project and add the relevant NuGet packages.
Creating the project
Adding the NuGet packages
Running the project
Explanation of the project structure
Up next
This guide uses the on-line templates that are available in the Visual Studio gallery. If you can't find the templates on-line, please
download them here.

Creating the project


To create the project, start Visual Studio and choose File => New Project... Then switch to the on-line template section as you can see in the
screenshot below and search for Catel:

Pick a good name, in our case WPF.GettingStarted and click OK. The template will now be downloaded and the project will be created.

Adding the NuGet packages


As soon as the project is created, the Readme.txt will be opened and instruct your what to do. Right-click on the solution => Manage NuGet
packages... Then search for Catel.Extensions.Controls and click Install.

Running the project


Now the NuGet packages are installed, the project is created and can be built. The basics are created and the application is ready:

Explanation of the project structure


The project template creates the project structure that fits best with Catel. Below is an explanation of the new project structure:

The ViewModels folder contains the MainWindowViewModel, which contains the logic for the interaction with the MainWindow view.
The Views folder contains the MainWindow, which represents the actual view.

Up next
Creating the models

Creating the models

In this step we will create models. Since this application is about families and persons inside those families, we need to create the following
models: Settings, Family and Person.
Creating the model classes
Settings class
Family class
Person class
Adding properties to the models
Settings class
Family class
Person class
Up next

Creating the model classes


The models that will be used in this application will derive from the ModelBase or SavableModelBase class of Catel. These classes enable
support for change notifications, validations and persistence. The SavableModelBase adds additional methods to save and load from/to streams
or files without having to create a serializer first.
To create the model classes, create the following classes in the Models folder.
The model code snippet is available to create models

Settings class
The settings class is the top container that will store all families and other settings (which might be added in the future).

namespace WPF.GettingStarted.Models
{
using Catel.Data;
public class Settings : SavableModelBase<Settings>
{
}
}

Family class

namespace WPF.GettingStarted.Models
{
using Catel.Data;
public class Family : ModelBase
{
}
}

Person class

namespace WPF.GettingStarted.Models
{
using Catel.Data;
public class Person : ModelBase
{
}
}

Adding properties to the models


The next step is to add properties to the models. An important concept to understand is that Catel uses specific "dependency-a-like" properties in
order to provide all the functionality in the ModelBase classes. Below are the properties per model that need to be registered.
At first sight, these properties might look very overwhelming. Let's take a look at how the property system works. The most important thing is the
actual property registration:

public static readonly PropertyData PersonsProperty = RegisterProperty("Persons",


typeof(ObservableCollection<Person>), () => new ObservableCollection<Person>());

This defines a property on the model with the following data:


Name => Persons
Type => ObservableCollection<Person>
DefaultValue => new ObservableCollection<Person>()
This will create a property in the property bag of the model. The next piece of the property is the actual wrapper around the property value which
is managed by the property bag. The Catel properties always need a wrapper to be exposed to the "outside world" of the class.

public ObservableCollection<Person> Persons


{
get { return GetValue<ObservableCollection<Person>>(PersonsProperty); }
set { SetValue(PersonsProperty, value); }
}

The modelprop code snippet is available to create models

Settings class

public class Settings : SavableModelBase<Settings>


{
/// <summary>
/// Gets or sets all the families.
/// </summary>
public ObservableCollection<Family> Families
{
get { return GetValue<ObservableCollection<Family>>(FamiliesProperty); }
set { SetValue(FamiliesProperty, value); }
}
/// <summary>
/// Register the Families property so it is known in the class.
/// </summary>
public static readonly PropertyData FamiliesProperty =
RegisterProperty("Families", typeof(ObservableCollection<Family>), () => new
ObservableCollection<Family>());
}

Family class

public class Family : ModelBase


{
/// <summary>
/// Gets or sets the family name.
/// </summary>
public string FamilyName
{
get { return GetValue<string>(FamilyNameProperty); }
set { SetValue(FamilyNameProperty, value); }
}
/// <summary>
/// Register the FamilyName property so it is known in the class.
/// </summary>
public static readonly PropertyData FamilyNameProperty =
RegisterProperty("FamilyName", typeof(string), null);
/// <summary>
/// Gets or sets the list of persons in this family.
/// </summary>
public ObservableCollection<Person> Persons
{
get { return GetValue<ObservableCollection<Person>>(PersonsProperty); }
set { SetValue(PersonsProperty, value); }
}
/// <summary>
/// Register the Persons property so it is known in the class.
/// </summary>
public static readonly PropertyData PersonsProperty = RegisterProperty("Persons",
typeof(ObservableCollection<Person>), () => new ObservableCollection<Person>());
public override string ToString()
{
return FamilyName;
}
}

Person class

public class Person : ModelBase


{
/// <summary>
/// Gets or sets the first name.
/// </summary>
public string FirstName
{
get { return GetValue<string>(FirstNameProperty); }
set { SetValue(FirstNameProperty, value); }
}
/// <summary>
/// Register the FirstName property so it is known in the class.
/// </summary>
public static readonly PropertyData FirstNameProperty =
RegisterProperty("FirstName", typeof(string), null);
/// <summary>
/// Gets or sets the last name.
/// </summary>
public string LastName
{
get { return GetValue<string>(LastNameProperty); }
set { SetValue(LastNameProperty, value); }
}
/// <summary>
/// Register the LastName property so it is known in the class.
/// </summary>
public static readonly PropertyData LastNameProperty =
RegisterProperty("LastName", typeof(string), null);
public override string ToString()
{
string fullName = string.Empty;
if (!string.IsNullOrEmpty(FirstName))
{
fullName += FirstName;
}
if (!string.IsNullOrEmpty(FirstName) && !string.IsNullOrWhiteSpace(LastName))
{
fullName += " ";
}
if (!string.IsNullOrWhiteSpace(LastName))
{
fullName += LastName;
}
return fullName;
}
}

Up next
Serializing data from/to disk

Serializing data from/to disk

In this step we will create services that will serialize the models from/to disk. Services are a great way to abstract functionality that can be used in
every part of the application. This guide will also register the service in the ServiceLocator so it can be injected in view models.
Creating the service definition
Creating the service implementation
Registering the service in the ServiceLocator
Adding the service usage to the MainWindowViewModel
Injecting the service via dependency injection
Creating the Families property on the MainWindowViewModel
Loading the families at startup
Saving the families at shutdown
Up next

Creating the service definition


The first thing to do is to create the Services folder to group the services. Below is a screenshot of how to solution will look after creating the
folders:

Then add a new interface to the Interfaces folder named IFamilyService. This will manage the families that are avaiable. Below is the interface
defined:

namespace WPF.GettingStarted.Services
{
using WPF.GettingStarted.Models;
public interface IFamilyService
{
IEnumerable<Family> LoadFamilies();
void SaveFamilies(IEnumerable<Family> families);
}
}

Creating the service implementation


Below is the implementation of the service which will actually take care of saving and loading of the families:

namespace
{
using
using
using
using
using

WPF.GettingStarted.Services
System.Collections.Generic;
System.IO;
Catel.Collections;
Catel.Data;
WPF.GettingStarted.Models;

public class FamilyService : IFamilyService


{
private readonly string _path;
public FamilyService()
{
string directory =
Catel.IO.Path.GetApplicationDataDirectory("CatenaLogic", "WPF.GettingStarted");
_path = Path.Combine(directory, "family.xml");
}
public IEnumerable<Family> LoadFamilies()
{
if (!File.Exists(_path))
{
return new Family[] { };
}
using (var fileStream = File.Open(_path, FileMode.Open))
{
var settings = Settings.Load(fileStream, SerializationMode.Xml);
return settings.Families;
}
}
public void SaveFamilies(IEnumerable<Family> families)
{
var settings = new Settings();
settings.Families.ReplaceRange(families);
settings.Save(_path, SerializationMode.Xml);
}
}
}

Registering the service in the ServiceLocator


Now we have created the service, it is time to register it in the ServiceLocator. In the App.xaml.cs, add the following code:

var serviceLocator = ServiceLocator.Default;


serviceLocator.RegisterType<IFamilyService, FamilyService>();

Adding the service usage to the MainWindowViewModel


Now the service is registered, it can be used anywhere in the application. A great place to load and save the families is in the MainWindowViewM

odel which contains all the logic of the main application window.

Injecting the service via dependency injection


To get an instance of the service in the view model, change the constructor to the following definition.

private readonly IFamilyService _familyService;


/// <summary>
/// Initializes a new instance of the <see cref="MainWindowViewModel"/> class.
/// </summary>
public MainWindowViewModel(IFamilyService familyService)
{
Argument.IsNotNull(() => familyService);
_familyService = familyService;
}

As you can see in the code above, a new field is created to store the dependency IFamilyService. Then the constructor ensures that the argument
is not null and stores it in the field.

Creating the Families property on the MainWindowViewModel


The next thing we need is a Families property on the MainWindowViewModel to store the families in we load from disk. Below is the property
definition for that:

/// <summary>
/// Gets the families.
/// </summary>
public ObservableCollection<Family> Families
{
get { return GetValue<ObservableCollection<Family>>(FamiliesProperty); }
private set { SetValue(FamiliesProperty, value); }
}
/// <summary>
/// Register the Families property so it is known in the class.
/// </summary>
public static readonly PropertyData FamiliesProperty = RegisterProperty("Families",
typeof(ObservableCollection<Family>), null);

Loading the families at startup


Now we have the IFamilyService and the Families property, it is time to combine these two. To do this, we need to override the Initialize method
on the view model which is automatically called as soon as the view is loaded by Catel:

protected override async Task Initialize()


{
var families = _familyService.LoadFamilies();
Families = new ObservableCollection<Family>(families);
}

Saving the families at shutdown

To save the families at shutdown, override the Close method on the view model which is automatically called as soon as the view is closed by
Catel:

protected override async Task Close()


{
_familyService.SaveFamilies(Families);
}

After running the application once, a new file will be stored in the following directory:
C:\Users\[yourusername]\AppData\Roaming\CatenaLogic\WPF.GettingStarted

Up next
Creating the view models

Creating the view models


In this step we will create the view models. Since this is a very simple application, just a few view models are required. A view model in essence is
nothing more than a class that derives from the ViewModelBase class
Creating the PersonViewModel
Enabling model injection
Exposing properties of a model
Creating the FamilyViewModel
Up next
The vm code snippet is available to create view models. There is also an on-line item template available for Catel view models

Creating the PersonViewModel


Below is the class definition of the PersonViewModel. This view model will be used to show the details of a Person model.

namespace WPF.GettingStarted.ViewModels
{
using Catel.MVVM;
public class PersonViewModel : ViewModelBase
{
}
}

Enabling model injection


In hierarchy views, it is important to manage the state of views and view models based on the actual context where the view (thus view model) is
located. Catel does this by allowing model injection. The view models will only be created when the model is available within the context of the
view.

public class PersonViewModel : ViewModelBase


{
public PersonViewModel(Person person)
{
Argument.IsNotNull(() => person);
Person = person;
}
/// <summary>
/// Gets or sets the person.
/// </summary>
[Model]
public Person Person
{
get { return GetValue<Person>(PersonProperty); }
set { SetValue(PersonProperty, value); }
}
/// <summary>
/// Register the Person property so it is known in the class.
/// </summary>
public static readonly PropertyData PersonProperty = RegisterProperty("Person",
typeof(Person), null);
}

Note that the Person property is decorated with the Model attribute. This automatically makes sure that if a view model is saved, the IEd
itableObject.EndEdit is called. When the view model is canceled, the IEditableObject.CancelEdit is called and all changes on the model
will be reverted.

Exposing properties of a model


One very powerful feature of Catel is that it can automatically map properties from a model to a view model. This way the user does not have to
write repetitive code to map the properties from the model to the view model at startup and map the properties from view model to model when
the view model is closed. Catel will take care of this all automatically.

/// <summary>
/// Gets or sets the first name.
/// </summary>
[ViewModelToModel("Person")]
public string FirstName
{
get { return GetValue<string>(FirstNameProperty); }
set { SetValue(FirstNameProperty, value); }
}
/// <summary>
/// Register the FirstName property so it is known in the class.
/// </summary>
public static readonly PropertyData FirstNameProperty = RegisterProperty("FirstName",
typeof(string), null);
/// <summary>
/// Gets or sets the last name.
/// </summary>
[ViewModelToModel("Person")]
public string LastName
{
get { return GetValue<string>(LastNameProperty); }
set { SetValue(LastNameProperty, value); }
}
/// <summary>
/// Register the LastName property so it is known in the class.
/// </summary>
public static readonly PropertyData LastNameProperty = RegisterProperty("LastName",
typeof(string), null);

Note that the properties are decorated with the ViewModelToModel attribute which enables the automatic mappings feature in Catel.

Creating the FamilyViewModel


The FamilyViewModel must be set up the same way as the PersonViewModel above.

namespace
{
using
using
using
using
using

WPF.GettingStarted.ViewModels
System.Collections.ObjectModel;
Catel;
Catel.Data;
Catel.MVVM;
WPF.GettingStarted.Models;

public class FamilyViewModel : ViewModelBase


{
public FamilyViewModel(Family family)
{
Argument.IsNotNull(() => family);
Family = family;
}

/// <summary>
/// Gets the family.
/// </summary>
[Model]
public Family Family
{
get { return GetValue<Family>(FamilyProperty);
private set { SetValue(FamilyProperty, value);
}
/// <summary>
/// Register the Family property so it is known in
/// </summary>
public static readonly PropertyData FamilyProperty
RegisterProperty("Family", typeof(Family), null);

}
}

the class.
=

/// <summary>
/// Gets the family members.
/// </summary>
[ViewModelToModel("Family")]
public ObservableCollection<Person> Persons
{
get { return GetValue<ObservableCollection<Person>>(PersonsProperty); }
private set { SetValue(PersonsProperty, value); }
}
/// <summary>
/// Register the Persons property so it is known in the class.
/// </summary>
public static readonly PropertyData PersonsProperty =
RegisterProperty("Persons", typeof(ObservableCollection<Person>), null);
/// <summary>
/// Gets or sets the family name.
/// </summary>
[ViewModelToModel("Family")]
public string FamilyName
{
get { return GetValue<string>(FamilyNameProperty); }
set { SetValue(FamilyNameProperty, value); }
}
/// <summary>
/// Register the FamilyName property so it is known in the class.
/// </summary>
public static readonly PropertyData FamilyNameProperty =

RegisterProperty("FamilyName", typeof(string));
}
}

Up next
Creating the views (user controls)

Creating the views (user controls)


In this step we will create the views for the application. There are several views that will be created and both user controls and windows will be
handled in this part of the guide. Catel makes it very easy to create views as user controls with their own view models. In the previous step we
already created the view models.
Person view
Family view
Up next

Person view
To create a new view, right-click the Views folder in the solution => Add => New item... => On-line => and search for Catel as you can see in the
screen below:

Give the new view the name PersonView. The view will be added to the Views folder.
Catel will automatically link the PersonViewModel and PersonView together by naming convention

Now we only need to modify the view itself, the code-behind can stay untouched. Since xaml isn't very interesting for this guide, simply copy/paste
the xaml below and set it as content of the view:

<catel:StackGrid>
<catel:StackGrid.RowDefinitions>
<RowDefinition Height="Auto" />
<RowDefinition Height="Auto" />
</catel:StackGrid.RowDefinitions>
<catel:StackGrid.ColumnDefinitions>
<ColumnDefinition Width="Auto" />
<ColumnDefinition Width="*" />
</catel:StackGrid.ColumnDefinitions>
<Label Content="First name" />
<Label Content="{Binding FirstName}" />
<Label Content="Last name" />
<Label Content="{Binding LastName}" />
</catel:StackGrid>

Family view
The FamilyView must be created exactly the same way as the PersonView. Use the following xaml as content:

<catel:StackGrid>
<catel:StackGrid.RowDefinitions>
<RowDefinition Height="Auto" />
<RowDefinition Height="Auto" />
<RowDefinition Height="Auto" />
</catel:StackGrid.RowDefinitions>
<catel:StackGrid.ColumnDefinitions>
<ColumnDefinition Width="Auto" />
<ColumnDefinition Width="*" />
</catel:StackGrid.ColumnDefinitions>
<Label Content="Family name" />
<Label Content="{Binding FamilyName}" />
<Label Grid.ColumnSpan="2" Content="Persons" />
<ItemsControl Grid.ColumnSpan="2" ItemsSource="{Binding Persons}">
<ItemsControl.ItemTemplate>
<DataTemplate>
<views:PersonView DataContext="{Binding}" />
</DataTemplate>
</ItemsControl.ItemTemplate>
</ItemsControl>
</catel:StackGrid>

Since this view uses the PersonView, it must be defined as a namespace at the top of the file:

xmlns:views="clr-namespace:WPF.GettingStarted.Views"

The thing that is important to notice in the FamilyView is how it uses the PersonView and injects the Person models into the PersonView data

context.

Up next
Creating the views (windows)

Creating the views (windows)


In this step we will create the windows for the application. In the previous step we already created the user controls. Windows are a great way to
show in an edit-context. Catel provides great edit-windows in the form of the DataWindow. This is a window that automatically adds OK and Canc
el buttons (but of course allows customization of the buttons and behavior).
Person window
Family window
Creating the FamilyWindowViewModel
Creating the FamilyWindow
Up next

Person window
It is very important that the window derives from one of the Catel windows. This is required to make the binding system work (same as
UserControl). Make sure that the window definition in the xaml is either catel:Window or catel:DataWindow
To add a new DataWindow, right-click the Views folder in the solution => Add => New item... => On-line => and search for Catel as you can see
in the screen below:

Give the new view the name PersonWindow. The view will be added to the Views folder.
Note that we can use the PersonViewModel for both the PersonView (user control) and PersonWindow. Both views represent the same
models and view models, just a different context. To make sure that the IUIVisualizerService knows what view to pick first, register the

PersonWindow in the IUIVisualizerService at application startup:

var uiVisualizerService = serviceLocator.ResolveType<IUIVisualizerService>();


uiVisualizerService.Register(typeof(PersonViewModel), typeof(PersonWindow));

The template will also create a constructor to inject a view model into the window. Please make sure that the constructor takes a view model of
the type PersonViewModel instead of the generated PersonWindowModel. Then replace the content of the view with the xaml below:

<catel:StackGrid>
<catel:StackGrid.RowDefinitions>
<RowDefinition Height="Auto" />
<RowDefinition Height="Auto" />
</catel:StackGrid.RowDefinitions>
<catel:StackGrid.ColumnDefinitions>
<ColumnDefinition Width="Auto" />
<ColumnDefinition Width="*" />
</catel:StackGrid.ColumnDefinitions>
<Label Content="First name" />
<TextBox Text="{Binding FirstName, ValidatesOnDataErrors=True,
NotifyOnValidationError=True}" />
<Label Content="Last name" />
<TextBox Text="{Binding LastName, ValidatesOnDataErrors=True,
NotifyOnValidationError=True}" />
</catel:StackGrid>

Family window
The FamilyWindow is a bit different because we want additional logic in this window. We want to create add / edit / remove buttons for the family
members. Therefore we need to create a separate view model which contains this logic.

Creating the FamilyWindowViewModel


Since the FamilyWindowViewModel will look a lot like the FamilyViewModel, just copy/paste the FamilyViewModel and rename the copy to Family
WindowViewModel.
Note that the FamilyWindowViewModel needs additional logic, but that will be handled in the next part of this getting started guide

Creating the FamilyWindow


Once the FamilyWindowViewModel is created, the FamilyWindow must be created exactly the same way as the PersonWindow. Again make sure
to use the right view model (FamilyWindowViewModel) in the constructor of the window in the code-behind. Then use the following xaml:

<catel:StackGrid>
<catel:StackGrid.RowDefinitions>
<RowDefinition Height="Auto" />
<RowDefinition Height="Auto" />
<RowDefinition Height="*" />
</catel:StackGrid.RowDefinitions>
<catel:StackGrid.ColumnDefinitions>
<ColumnDefinition Width="Auto" />
<ColumnDefinition Width="*" />
</catel:StackGrid.ColumnDefinitions>
<Label Content="Family name" />
<TextBox Text="{Binding FamilyName, NotifyOnValidationError=True,
ValidatesOnDataErrors=True}" />
<Label Grid.ColumnSpan="2" Content="Persons" />
<catel:StackGrid Grid.ColumnSpan="2">
<catel:StackGrid.ColumnDefinitions>
<ColumnDefinition Width="*" />
<ColumnDefinition Width="Auto" />
</catel:StackGrid.ColumnDefinitions>
<ListBox ItemsSource="{Binding Persons}" SelectedItem="{Binding
SelectedPerson}">
<ListBox.ItemTemplate>
<DataTemplate>
<views:PersonView DataContext="{Binding}" />
</DataTemplate>
</ListBox.ItemTemplate>
</ListBox>
<StackPanel>
<Button Command="{Binding AddPerson}" Content="Add..." />
<Button Command="{Binding EditPerson}" Content="Edit..." />
<Button Command="{Binding RemovePerson}" Content="Remove" />
</StackPanel>
</catel:StackGrid>
</catel:StackGrid>

Up next
Hooking up everything together

Hooking up everything together


In this step we will hook everything together and add additional logic to the remaining view models.
Hooking up the view models
Adding additional logic to FamilyWindowViewModel
Adding additional dependencies being injected
Adding the properties
Adding the commands
Adding additional logic to the MainWindowViewModel
Adding additional dependencies being injected
Adding the properties
Adding the commands
Hooking up the views
Up next

Hooking up the view models


We now have most of the application ready. However we need some logic in the view models to hook up everything together.

Adding additional logic to FamilyWindowViewModel


The first thing we are going to do is to finalize the FamilyWindowViewModel we created in the previous step. To do this, we are going to add a few
properties and commands to the view model.

Adding additional dependencies being injected


Since we will be using additional services inside the FamilyWindowViewModel, it is important to add them as dependency via the constructor. The
updated constructor will look like this:

public FamilyWindowViewModel(Family family, IUIVisualizerService uiVisualizerService,


IMessageService messageService)
{
Argument.IsNotNull(() => family);
Argument.IsNotNull(() => uiVisualizerService);
Argument.IsNotNull(() => messageService);
Family = family;
_uiVisualizerService = uiVisualizerService;
_messageService = messageService;
}

Don't forget to create the right backing fields _uiVisualizerService and _messageService

Adding the properties


We need a property representing the currently selected person in edit mode of a family. Below is the property definition which needs to be added
to the view model:

/// <summary>
/// Gets or sets the selected person.
/// </summary>
public Person SelectedPerson
{
get { return GetValue<Person>(SelectedPersonProperty); }
set { SetValue(SelectedPersonProperty, value); }
}
/// <summary>
/// Register the SelectedPerson property so it is known in the class.
/// </summary>
public static readonly PropertyData SelectedPersonProperty =
RegisterProperty("SelectedPerson", typeof(Person), null);

Adding the commands


Note that we recommend that you use the vmcommand and vmcommandwithcanexecute code snippets available here

Below is the code which comes in two parts.

1. Add this code to the constructor:

AddPerson = new Command(OnAddPersonExecute);


EditPerson = new Command(OnEditPersonExecute, OnEditPersonCanExecute);
RemovePerson = new Command(OnRemovePersonExecute, OnRemovePersonCanExecute);

2. You must import Catel.IoC namespace since it contains ViewModelBase's GetTypeFactory() extension method used below.

using Catel.IoC;

3. Add this code to the view model itself:

/// <summary>
/// Gets the AddPerson command.
/// </summary>
public Command AddPerson { get; private set; }
/// <summary>
/// Method to invoke when the AddPerson command is executed.
/// </summary>
private async void OnAddPersonExecute()
{
var person = new Person();
person.LastName = FamilyName;
// Note that we use the type factory here because it will automatically take care
of any dependencies
// that the PersonViewModel will add in the future
var typeFactory = this.GetTypeFactory();
var personViewModel =
typeFactory.CreateInstanceWithParametersAndAutoCompletion<PersonViewModel>(person);
if (await _uiVisualizerService.ShowDialogAsync(personViewModel) ?? false)
{
Persons.Add(person);
}
}
/// <summary>
/// Gets the EditPerson command.
/// </summary>
public Command EditPerson { get; private set; }
/// <summary>
/// Method to check whether the EditPerson command can be executed.
/// </summary>
/// <returns><c>true</c> if the command can be executed; otherwise
<c>false</c></returns>
private bool OnEditPersonCanExecute()
{
return SelectedPerson != null;
}
/// <summary>
/// Method to invoke when the EditPerson command is executed.
/// </summary>
private async void OnEditPersonExecute()

{
// Note that we use the type factory here because it will automatically take care
of any dependencies
// that the PersonViewModel will add in the future
var typeFactory = this.GetTypeFactory();
var personViewModel =
typeFactory.CreateInstanceWithParametersAndAutoCompletion<PersonViewModel>(SelectedPer
son);
await _uiVisualizerService.ShowDialogAsync(personViewModel);
}
/// <summary>
/// Gets the RemovePerson command.
/// </summary>
public Command RemovePerson { get; private set; }
/// <summary>
/// Method to check whether the RemovePerson command can be executed.
/// </summary>
/// <returns><c>true</c> if the command can be executed; otherwise
<c>false</c></returns>
private bool OnRemovePersonCanExecute()
{
return SelectedPerson != null;
}
/// <summary>
/// Method to invoke when the RemovePerson command is executed.
/// </summary>
private async void OnRemovePersonExecute()
{
if (await _messageService.Show(string.Format("Are you sure you want to delete the
person '{0}'?", SelectedPerson),
"Are you sure?", MessageButton.YesNo, MessageImage.Question) ==
MessageResult.Yes)
{
Persons.Remove(SelectedPerson);

SelectedPerson = null;
}
}

Adding additional logic to the MainWindowViewModel


The same edit functionality we added to the FamilyWindowViewModel must be added to the MainWindowViewModel. The difference is that
instead of adding / editing / removing persons, the MainWindowViewModel will do this for families.

Adding additional dependencies being injected


We will again need additional dependencies. Below is the updated constructor for the MainWindowViewModel:

public MainWindowViewModel(IFamilyService familyService, IUIVisualizerService


uiVisualizerService, IMessageService messageService)
{
Argument.IsNotNull(() => familyService);
Argument.IsNotNull(() => uiVisualizerService);
Argument.IsNotNull(() => messageService);
_familyService = familyService;
_uiVisualizerService = uiVisualizerService;
_messageService = messageService;
}

Adding the properties


We will again need a property to handle the selected family:

/// <summary>
/// Gets or sets the selected family.
/// </summary>
public Family SelectedFamily
{
get { return GetValue<Family>(SelectedFamilyProperty); }
set { SetValue(SelectedFamilyProperty, value); }
}
/// <summary>
/// Register the SelectedFamily property so it is known in the class.
/// </summary>
public static readonly PropertyData SelectedFamilyProperty =
RegisterProperty("SelectedFamily", typeof(Family), null);

Adding the commands


Last but not least, we will also add the commands to the MainWindowViewModel to handle the logic.
1. Add this code to the constructor:

AddFamily = new Command(OnAddFamilyExecute);


EditFamily = new Command(OnEditFamilyExecute, OnEditFamilyCanExecute);
RemoveFamily = new Command(OnRemoveFamilyExecute, OnRemoveFamilyCanExecute);

2. Add this code to the view model itself:

/// <summary>
/// Gets the AddFamily command.
/// </summary>
public Command AddFamily { get; private set; }
/// <summary>
/// Method to invoke when the AddFamily command is executed.
/// </summary>
private async void OnAddFamilyExecute()
{
var family = new Family();
// Note that we use the type factory here because it will automatically take care
of any dependencies
// that the FamilyWindowViewModel will add in the future
var typeFactory = this.GetTypeFactory();
var familyWindowViewModel =
typeFactory.CreateInstanceWithParametersAndAutoCompletion<FamilyWindowViewModel>(famil
y);
if (await _uiVisualizerService.ShowDialog(familyWindowViewModel) ?? false)
{
Families.Add(family);
}
}
/// <summary>
/// Gets the EditFamily command.
/// </summary>
public Command EditFamily { get; private set; }
/// <summary>
/// Method to check whether the EditFamily command can be executed.
/// </summary>
/// <returns><c>true</c> if the command can be executed; otherwise
<c>false</c></returns>
private bool OnEditFamilyCanExecute()
{
return SelectedFamily != null;
}
/// <summary>
/// Method to invoke when the EditFamily command is executed.
/// </summary>
private async void OnEditFamilyExecute()
{
// Note that we use the type factory here because it will automatically take care
of any dependencies
// that the PersonViewModel will add in the future
var typeFactory = this.GetTypeFactory();
var familyWindowViewModel =
typeFactory.CreateInstanceWithParametersAndAutoCompletion<FamilyWindowViewModel>(Selec
tedFamily);
await _uiVisualizerService.ShowDialogAsync(familyWindowViewModel);
}
/// <summary>
/// Gets the RemoveFamily command.

/// </summary>
public Command RemoveFamily { get; private set; }
/// <summary>
/// Method to check whether the RemoveFamily command can be executed.
/// </summary>
/// <returns><c>true</c> if the command can be executed; otherwise
<c>false</c></returns>
private bool OnRemoveFamilyCanExecute()
{
return SelectedFamily != null;
}
/// <summary>
/// Method to invoke when the RemoveFamily command is executed.
/// </summary>
private async void OnRemoveFamilyExecute()
{
if (await _messageService.Show(string.Format("Are you sure you want to delete the
family '{0}'?", SelectedFamily),
"Are you sure?", MessageButton.YesNo, MessageImage.Question) ==
MessageResult.Yes)
{
Families.Remove(SelectedFamily);

SelectedFamily = null;
}
}

Hooking up the views


We now have all the views ready, but we don't see anything yet. The reason for this is that we haven't modified the MainWindow view yet. To do
so, replace the xaml content with the xaml below:

<catel:StackGrid>
<catel:StackGrid.ColumnDefinitions>
<ColumnDefinition Width="*" />
<ColumnDefinition Width="100" />
</catel:StackGrid.ColumnDefinitions>
<ListBox ItemsSource="{Binding Families}" SelectedItem="{Binding SelectedFamily}">
<ListBox.ItemTemplate>
<DataTemplate>
<views:FamilyView DataContext="{Binding}" />
</DataTemplate>
</ListBox.ItemTemplate>
</ListBox>
<StackPanel>
<Button Command="{Binding AddFamily}" Content="Add..." />
<Button Command="{Binding EditFamily}" Content="Edit..." />
<Button Command="{Binding RemoveFamily}" Content="Remove" />
</StackPanel>
</catel:StackGrid>

Now run the application and you should see your fully functional family management application.

Up next
Finalizing the application

Finalizing the application


The application we have created so far is fully functional, but misses a bit of the "magic". Below are some additional steps that might make your
application more appealing and more user friendly. Of course you can go as far as you want by creating custom animations and such, but this
guide focuses purely on making the basics more appealing.
Adding validation
Adding behaviors to enable double-click on the list boxes
Adding search functionality to the main window
Adding additional properties to the view model
Adding the search functionality to the view

Adding validation
Adding validation with Catel is extremely easy. There are two flavors to pick from, but they work exactly the same (since both the models and view
models internally derive from ModelBase). To add validation to the Person model, use this code:

protected override void ValidateFields(List<IFieldValidationResult> validationResults)


{
if (string.IsNullOrWhiteSpace(FirstName))
{
validationResults.Add(FieldValidationResult.CreateError(FirstNameProperty,
"The first name is required"));
}
if (string.IsNullOrWhiteSpace(LastName))
{
validationResults.Add(FieldValidationResult.CreateError(LastNameProperty, "The
last name is required"));
}
}

The validation for the Family model is very easy as well:

protected override void ValidateFields(List<IFieldValidationResult> validationResults)


{
if (string.IsNullOrWhiteSpace(FamilyName))
{
validationResults.Add(FieldValidationResult.CreateError(FamilyNameProperty,
"The family name is required"));
}
}

Note that this validation code can be used in both the model and/or the view models

Adding behaviors to enable double-click on the list boxes


The user must manually click the Edit buttons in the editable views to edit a specific model. To make it easier for the user, we can enable double
click to command behaviors. To do so, navigate to the MainWindow and add this to the ListBox definition:

<ListBox x:Name="listBox" ItemsSource="{Binding Families}" SelectedItem="{Binding


SelectedFamily}">
<ListBox.ItemTemplate>
<DataTemplate>
<Grid>
<i:Interaction.Behaviors>
<catel:DoubleClickToCommand Command="{Binding ElementName=listBox,
Path=DataContext.EditFamily}" />
</i:Interaction.Behaviors>
<views:FamilyView DataContext="{Binding}" />
</Grid>
</DataTemplate>
</ListBox.ItemTemplate>
</ListBox>

The same goes for the FamilyWindow:

<ListBox x:Name="listBox" ItemsSource="{Binding Persons}" SelectedItem="{Binding


SelectedPerson}">
<ListBox.ItemTemplate>
<DataTemplate>
<Grid>
<i:Interaction.Behaviors>
<catel:DoubleClickToCommand Command="{Binding ElementName=listBox,
Path=DataContext.EditPerson}" />
</i:Interaction.Behaviors>
<views:PersonView DataContext="{Binding}" />
</Grid>
</DataTemplate>
</ListBox.ItemTemplate>
</ListBox>

Note that the xmlns:i="http://schemas.microsoft.com/expression/2010/interactivity" must be added in order for the code above to
compile

Adding search functionality to the main window


A functionality that is needed in a lot of applications is search functionality. To implement this we will need to modify the MainWindowViewModel.
Below are the steps required to implement search functionality.

Adding additional properties to the view model


Lets start by adding the additional properties required to implement searching in the MainWindowViewModel:

/// <summary>
/// Gets the filtered families.
/// </summary>
public ObservableCollection<Family> FilteredFamilies
{
get { return GetValue<ObservableCollection<Family>>(FilteredFamiliesProperty); }
private set { SetValue(FilteredFamiliesProperty, value); }
}
/// <summary>
/// Register the FilteredFamilies property so it is known in the class.
/// </summary>
public static readonly PropertyData FilteredFamiliesProperty =
RegisterProperty("FilteredFamilies", typeof(ObservableCollection<Family>));
/// <summary>
/// Gets or sets the search filter.
/// </summary>
public string SearchFilter
{
get { return GetValue<string>(SearchFilterProperty); }
set { SetValue(SearchFilterProperty, value); }
}
/// <summary>
/// Register the SearchFilter property so it is known in the class.
/// </summary>
public static readonly PropertyData SearchFilterProperty =
RegisterProperty("SearchFilter", typeof(string), null, (sender, e) =>
((MainWindowViewModel)sender).UpdateSearchFilter());

Note that this property contains an additional change callback function which will be called when the property has changed.

Add the following import to the view model. You will needed because native ObservableCollection class does not support ReplaceRange()

using Catel.Collections;

Add this method to the view model:

/// <summary>
/// Updates the filtered items.
/// </summary>
private void UpdateSearchFilter()
{
if (FilteredFamilies == null)
{
FilteredFamilies = new ObservableCollection<Family>();
}
if (string.IsNullOrWhiteSpace(SearchFilter))
{
FilteredFamilies.ReplaceRange(Families);
}
else
{
var lowerSearchFilter = SearchFilter.ToLower();
FilteredFamilies.ReplaceRange(from family in Families
where
!string.IsNullOrWhiteSpace(family.FamilyName) &&
family.FamilyName.ToLower().Contains(lowerSearchFilter)
select family);
}
}

Then, add this code to the OnAddFamilyExecute function:

private async void OnAddFamilyExecute()


{
var family = new Family();
// Note that we use the type factory here because it will automatically take care
of any dependencies
// that the FamilyWindowViewModel will add in the future
var typeFactory = this.GetTypeFactory();
var familyWindowViewModel =
typeFactory.CreateInstanceWithParametersAndAutoCompletion<FamilyWindowViewModel>(famil
y);
if (await _uiVisualizerService.ShowDialog(familyWindowViewModel) ?? false)
{
Families.Add(family);
UpdateSearchFilter();
}
}

Last but not least, add this to the Initialize method after the Families is set from the IFamilyService

protected override async Task Initialize()


{
var families = _familyService.LoadFamilies();
Families = new ObservableCollection<Family>(families);
UpdateSearchFilter();
}

Adding the search functionality to the view


Replace the xaml of the main window by the following content:

<catel:StackGrid>
<catel:StackGrid.RowDefinitions>
<RowDefinition Height="Auto" />
<RowDefinition Height="*" />
</catel:StackGrid.RowDefinitions>
<catel:StackGrid.ColumnDefinitions>
<ColumnDefinition Width="*" />
<ColumnDefinition Width="100" />
</catel:StackGrid.ColumnDefinitions>
<catel:StackGrid Grid.ColumnSpan="2">
<catel:StackGrid.ColumnDefinitions>
<ColumnDefinition Width="Auto" />
<ColumnDefinition Width="*" />
</catel:StackGrid.ColumnDefinitions>
<Label Content="Filter:" />
<TextBox Text="{Binding SearchFilter}">
<i:Interaction.Behaviors>
<catel:UpdateBindingOnTextChanged UpdateDelay="500" />
</i:Interaction.Behaviors>
</TextBox>
</catel:StackGrid>
<ListBox x:Name="listBox" ItemsSource="{Binding FilteredFamilies}"
SelectedItem="{Binding SelectedFamily}">
<ListBox.ItemTemplate>
<DataTemplate>
<Grid>
<i:Interaction.Behaviors>
<catel:DoubleClickToCommand Command="{Binding
ElementName=listBox, Path=DataContext.EditFamily}" />
</i:Interaction.Behaviors>
<views:FamilyView DataContext="{Binding}" />
</Grid>
</DataTemplate>
</ListBox.ItemTemplate>
</ListBox>
<StackPanel>
<Button Command="{Binding AddFamily}" Content="Add..." />
<Button Command="{Binding EditFamily}" Content="Edit..." />
<Button Command="{Binding RemoveFamily}" Content="Remove" />
</StackPanel>
</catel:StackGrid>

Examples
There are lots of examples written for Catel. Most of the examples are located in the Catel Examples repository, but there are some examples
which can are listed below:
MyMediaStuff - WPF demo application that uses media display, nested user controls and timers

If you have an example application that you want to share, let us know!

WPF Examples
Advanced WPF example
Authentication example
Browser application example
Master/detail example
Multilingual example
MVVM communication styles
Person application WPF example
Validation example
Viewmodel lifetime example
Silverlight examples
Advanced Silverlight example
Navigation example
Nested user controls example
Person application Silverlight example
Windows Phone examples
Bing maps example
Sensors example
Shopping list example
Open source using Catel

WPF Examples
Advanced WPF example
Authentication example
Browser application example
Master/detail example
Multilingual example
MVVM communication styles
Person application WPF example
Validation example
Viewmodel lifetime example

Advanced WPF example


This example shows advanced functionality such as MEF, Unity, Nested User Controls and MVVM behaviors.
The first groupbox at the left shows how to instantiate a Window both where the MVVM logic is implemented in the view base ( DataWindow) and
a behavior (WindowBehavior).
The second groupbox shows how to instantiate the UserControl both where the MVVM logic is implemented in the view base (UserControl) and a
behavior (UserControlBehavior).
The third groupbox shows the usage of the IPleaseWaitService (both in determinate and indeterminate mode) using the ServiceLocator, MEF and
Unity.

Screenshots

Authentication example
This example shows how to use authentication for views. You can either choose to run the window as read-only user or as administrator. When
running as read-only user, you will notice that the controls are disabled, hidden and collapsed. When running as administrator, the controls will all
be available.

Screenshots

Browser application example


This example shows how to run a browser application in WPF by using the INavigationService.

Screenshots

Master/detail example
This example shows how to create a master/detail with a UserControl as detail which automatically responds to changes in the master.

Screenshots

Multilingual example
This example show how to use the multiple languages in Catel. This example is also used to test new languages that are translated for Catel.

Screenshots

MVVM communication styles


There are several ways to implement communication between view models. This example shows the different communication styles:
Services
InterestedIn
MessageMediator

Services
The best way to communicate between view models are services. These are implementations registered in the ServiceLocator that can
automatically be injected into view models. Using services has several advantages:
1.
2.
3.
4.

The service can be shared among any view models that require the logic
Easy to mock because you can inject mock implementations of the services during unit tests
Easy to change the logic since it only needs to be changed in a single location
No need for view models to be aware of each other (separation of concerns)

A service is a custom implementation of any logic. A good example is the IMessageService in Catel. It is a service that allows a view model to
show a message. If you want to change the way messages are shown to the users, you only have to register a new implementation in the Service
Locator and all will be fixed.

InterestedIn
The InterestedIn method in Catel is the easiest way to communicate between view models. This can be done by simply adding the InterestedInAtt
ribute on top of a view model and override the OnViewModelPropertyChanged and OnViewModelCommandExecuted methods.

MessageMediator
Thought more flexible, the MessageMediator technique requires more work because the developer is responsible for defining custom messages,
registering and unregistering specific messages and sending the messages via the MessageMediator.

Screenshots

Person application WPF example


This example is a small application that allows adding persons via a model popup window. Is shows how to add validation, modal dialogs (via
MVVM) and view model to model mappings.

Screenshots

Validation example
This example shows all the different validation techniques available in Catel. The following validation techniques are shown:
Validation via validate methods
Validation via data annotations
Validation in model
Validation in IValidator
Validation via FluentValidation Extension

Screenshots

Viewmodel lifetime example


This example shows how to manually control the lifetime of view models. When adding new tabs, you can either choose the default behavior
(close view model when a control is unloaded) or to keep the view model alive. When a tab is unselected, the view model will be closed because
the view is unloaded from the visual tree. When the control should keep the view model alive, you will note that the total number of view models
will not decrease when switching from tabs.
All view models are explicitly closed when the close button on the tab is clicked. In that case, you will see the total number of alive view models
decrease.

Screenshots

Silverlight examples
Advanced Silverlight example
Navigation example
Nested user controls example
Person application Silverlight example

Advanced Silverlight example


This example shows advanced functionality such as MEF, Unity, Nested User Controls and MVVM behaviors.
The first groupbox at the left shows how to instantiate a Window both where the MVVM logic is implemented in the view base (DataWindow) and
a behavior (WindowBehavior).
The second groupbox shows how to instantiate the UserControl both where the MVVM logic is implemented in the view base (UserControl) and a
behavior (UserControlBehavior).
The third groupbox shows the usage of the IPleaseWaitService (both in determinate and indeterminate mode) using the ServiceLocator, MEF and
Unity.

Screenshots

Navigation example
This example shows how to create a page navigation application using Silverlight. It uses the INavigationService to implement navigation.

Screenshots

Nested user controls example


This example shows how to use nested user controls without instantiating all the view models of the nested user controls first. As you can see by
the view model creation time, the view models are actually created on-demand (we also call this lazy loading of view models).

Screenshots

Person application Silverlight example


This example is a small application that allows adding persons via a model popup window. Is shows how to add validation, modal dialogs (via
MVVM) and view model to model mappings.

Screenshots

Windows Phone examples


Bing maps example
Sensors example
Shopping list example

Bing maps example


This example shows how to access the current location in MVVM in Windows Phone and show it using Bing maps.

Screenshots

Sensors example
This example shows how to access all Windows Phone sensors and how to emulate them (for example, during unit tests or in the emulator).

Screenshots

Shopping list example


This example shows a shopping list application with navigation via arguments and several views and how to store data in the isolated storage.

Screenshots

Open source using Catel


There are a lot of open source components using Catel. Below are a few examples on how to use Catel in open source.
Orc.FilterBuilder
FilterBuilder is WPF component which can help you extract key insights from your data, by adding complex filtering functionalities to your
application.

Want to be listed here? Contact us!

Problem solving
As with every framework or toolkit, developers run into problems. This can be bugs or abuse of the API. Catel has several ways for developers to
solve the problems themselves before contacting the team with the possible issue.
Enabling the log
Enabling stepping through the code
ApiCop

Enabling the log


We take logging very serious in Catel. This means that a lot of information about the internals can be be seen in the output window. To enable
logging in Catel, use the following code in your application startup code:

#if DEBUG
Catel.Logging.LogManager.AddDebugListener();
#endif

Now you can see all the log messages in the output window.

Enabling stepping through the code


It's possible to step through the Catel code to see what is happening in the internals of Catel. This gives you great insights in Catel and can help
you solve the problems you are encountering. See the stepping through the code documentation.

ApiCop
Catel provides a feature called ApiCop. This will give you information about the most cases where the API of Catel is abused or not used in the
right way. The ApiCop feature will create an advisory report at the end of an application with tips on how to improve the feature usage in Catel.
Below is an example report:

****************************************************************
ApiCop (r) results of 'DataWindowTest.WPF' v1.0.0.0
recorded on 2014-02-19 10:06
To ignore rules, call ApiCopManager.IgnoredRules.Add([rulename]);
For more information about ApiCop, visit the website:
https://catelproject.atlassian.net/wiki/display/CTL/ApiCop
****************************************************************
================================================================
DATAWINDOWTEST.VIEWS.AVIEW
================================================================
Cop TargetType: Catel.Windows.Controls.MVVMProviders.Logic.UserControlLogic
Rule: UserControlLogic.InfoBarMessageControl (Error)
For more information about this rule, visit
https://catelproject.atlassian.net/wiki/display/CTL/Performance+considerat
ions

[DataWindowTest.Views.AView] Feature used '0' of '2' times, consider


turning it off by default
---------------------------------------------------------------Cop TargetType: Catel.Windows.Controls.MVVMProviders.Logic.UserControlLogic
Rule: UserControlLogic.CreateWarningAndErrorValidator (Error)
For more information about this rule, visit
https://catelproject.atlassian.net/wiki/display/CTL/Performance+considerat
ions
[DataWindowTest.Views.AView] Feature used '0' of '2' times, consider
turning it off by default
---------------------------------------------------------------================================================================
DATAWINDOWTEST.VIEWS.BVIEW
================================================================
Cop TargetType: Catel.Windows.Controls.MVVMProviders.Logic.UserControlLogic
Rule: UserControlLogic.InfoBarMessageControl (Error)
For more information about this rule, visit
https://catelproject.atlassian.net/wiki/display/CTL/Performance+considerat
ions
[DataWindowTest.Views.BView] Feature used '0' of '2' times, consider
turning it off by default
---------------------------------------------------------------Cop TargetType: Catel.Windows.Controls.MVVMProviders.Logic.UserControlLogic
Rule: UserControlLogic.CreateWarningAndErrorValidator (Error)
For more information about this rule, visit
https://catelproject.atlassian.net/wiki/display/CTL/Performance+considerat
ions
[DataWindowTest.Views.BView] Feature used '0' of '2' times, consider
turning it off by default
----------------------------------------------------------------

****************************************************************
End of ApiCop (r) results, generation took '00:00:00.137'
****************************************************************

For more information, see the ApiCop documentation.

Performance considerations
While developer software, it is very important to keep an eye on the performance. Catel itself does perform very well, but there are some caveats
that you should be aware of. If you have the feeling the the application is laggy or slow, or if you want to make sure to squeeze the best
performance out of Catel, the checklist below is very important.
Use the ApiCop feature to get a detailed advisory report on your software

General
Disable the call to LogManager.AddDebugListener
Disable event subscriptions of child values for ModelBase
Disabling validation during activities where validation is not required
Use LeanAndMeanModel property on ModelBase
Preloading assemblies into the AppDomain
Warming up the serializers
MVVM
Set SkipSearchingForInfoBarMessageControl on UserControl to true
Use the FastObservableCollection
Specify throttling on the ViewModelBase

General
Disable the call to LogManager.AddDebugListener
The DebugListener is a very useful class while developing an application. It throws all the logging of Catel to the output window of Visual Studio
which allows you to view exactly what happens behind the scenes. However, writing all these logs to the output window is very expensive and
might cause an application to perform badly.
Therefore, it is important to disable any call to LogManager.AddDebugListener when releasing an application or while performance testing.

Disable event subscriptions of child values for ModelBase


To be able to (re)validate when a child object changes, the ModelBase subscribes to all change notifications (of all childs) by default. This can be
disabled by using the following code:

ModelBase.DefaultDisableEventSubscriptionsOfChildValuesValue = false;

Disabling validation during activities where validation is not required


Validation inside Catel is very powerful, but sometimes it is not needed. To disable all validation inside Catel, use the following code:

ModelBase.SuspendValidationForAllModels = true;

Use LeanAndMeanModel property on ModelBase

When loading lots of models, it is not required to get support for validation and change notifications. Notifications and validation can be suspended
per model (using the LeanAndMeanModel property) or globally using the GlobalLeanAndMeanModel property.

Preloading assemblies into the AppDomain


Preloading assemblies might result in a slower startup time, but will not cause slow downs for reflection or assembly loading during the actual
application execution. To preload assemblies using Catel, simply call this extension method:

WPF application
In App.xaml.cs, add the following code

var directory = typeof(MainWindow).Assembly.GetDirectory();


AppDomain.CurrentDomain.PreloadAssemblies(directory);

ASP.NET application
In global.asax, add the following code:

var directory = Server.MapPath("~/bin");


AppDomain.Current.PreloadAssemblies(directory);

Warming up the serializers


To improve performance for serialization, warm up the serializers.

MVVM
Set SkipSearchingForInfoBarMessageControl on UserControl to true
By default, Catel assumes that an InfoBarMessageControl is located on any window. However, it might be that this control is not located on a
window that contains an instance of the UserControl class. This might decrease the performance, especially when lots of user controls are used in
a hierarchical way. The cause is that the UserControlLogic searches for an InfoBarMessageControl to register the view model to.
If no InfoBarMessageControl is located on a container, make sure to set SkipSearchingForInfoBarMessageControl to true.

// Use when not using styles and transitions


Catel.Windows.Controls.UserControl.DefaultTransferStylesAndTransitionsToViewModelGridV
alue = false;
// Use when not using any validation controls
Catel.Windows.Controls.UserControl.DefaultSkipSearchingForInfoBarMessageControlValue =
true;
Catel.Windows.Controls.UserControl.DefaultCreateWarningAndErrorValidatorForViewModelVa
lue = false;
// Use when not using *any* validation
Catel.Data.ModelBase.SuspendValidationForAllModels = true;

Use the FastObservableCollection

The FastObservableCollection does not raise events for every item, but only invokes events for the complete range of items added to or removed
from the collection.
When modifying a large collection of items, it is not required to raise change events for each added / removed value. Therefore the FastObservabl
eCollection will disable change notifications until the full collection modification is done and then raise the change events just once.

Specify throttling on the ViewModelBase


The ViewModelBase allows the specify the throttling of the property change notifications. In normal situations it is best to directly raise property
change notifications. However, when a lot of properties change a lot within a very short timeframe, it might be interesting to enable throttling. By
using throttling, the change notifications are not directly sent to the UI but instead added to a dictionary. Then each time the ThottlingRate is
reached, the change notifications are sent in batches to the view. If the same property has changed several times in a specific time frame, it will
only be raised once which might give a performance boost in very specific situations.
By default, throttling is disabled but can be enabled by setting the ThrottlingRate property:

ThrottlingRate = new TimeSpan(0, 0, 0, 0, 200);

The AdvancedDemo example contains a demo that shows the impact of throttling

Catel.Core
ApiCop
Argument checking
Caching
Configuration
Data handling
Exception handling
IoC (ServiceLocator and TypeFactory)
Logging
Messaging
Multilingual
Parallel invocation and tasks
Preventing memory leaks
Reflection
Scoping
Serialization
Thread safe code
Validation

ApiCop
Introduction
Usage for end-users (developers)
Architecture
For more information, see:
Cops
Rules
Listeners

Introduction
ApiCop is a unique feature in Catel that helps developers make sure the users are using the Api of frameworks the right way. This functionality
has been evolved from experience that users want logical advice including links to documentation when and why they are not using an Api in its
full potential.
The advantage of ApiCop is that it will only execute any code to trace the application when a debugger is attached. If no debugger is attached, the
feature will be fully disabled to prevent an impact of performance when running the software without debuggers.

Usage for end-users (developers)


As an end-user (developers that use a framework that supports ApiCop), the usage is really simply. Whenever you need a report (for example,
when closing an application when the debugger is attached), use the ApiCopManager to write the results. Below is an example of a WPF
application in the App.xaml.cs:

protected override void OnExit(ExitEventArgs e)


{
#if DEBUG
var apiCopListener = new ConsoleApiCopListener();
ApiCopManager.AddListener(apiCopListener);
ApiCopManager.WriteResults();
#endif
base.OnExit(e);
}

The code above writes the results of the ApiCop feature to the console, which will look like this:

****************************************************************
ApiCop (r) results of 'DataWindowTest.WPF' v1.0.0.0
recorded on 2014-02-19 10:06
To ignore rules, call ApiCopManager.IgnoredRules.Add([rulename]);
For more information about ApiCop, visit the website:
https://catelproject.atlassian.net/wiki/display/CTL/ApiCop
****************************************************************
================================================================
DATAWINDOWTEST.VIEWS.AVIEW
================================================================
Cop TargetType: Catel.Windows.Controls.MVVMProviders.Logic.UserControlLogic
Rule: UserControlLogic.InfoBarMessageControl (Error)
For more information about this rule, visit
https://catelproject.atlassian.net/wiki/display/CTL/Performance+considerat
ions
[DataWindowTest.Views.AView] Feature used '0' of '2' times, consider
turning it off by default
---------------------------------------------------------------Cop TargetType: Catel.Windows.Controls.MVVMProviders.Logic.UserControlLogic
Rule: UserControlLogic.CreateWarningAndErrorValidator (Error)
For more information about this rule, visit
https://catelproject.atlassian.net/wiki/display/CTL/Performance+considerat
ions
[DataWindowTest.Views.AView] Feature used '0' of '2' times, consider
turning it off by default

---------------------------------------------------------------================================================================
DATAWINDOWTEST.VIEWS.BVIEW
================================================================
Cop TargetType: Catel.Windows.Controls.MVVMProviders.Logic.UserControlLogic
Rule: UserControlLogic.InfoBarMessageControl (Error)
For more information about this rule, visit
https://catelproject.atlassian.net/wiki/display/CTL/Performance+considerat
ions
[DataWindowTest.Views.BView] Feature used '0' of '2' times, consider
turning it off by default
---------------------------------------------------------------Cop TargetType: Catel.Windows.Controls.MVVMProviders.Logic.UserControlLogic
Rule: UserControlLogic.CreateWarningAndErrorValidator (Error)
For more information about this rule, visit
https://catelproject.atlassian.net/wiki/display/CTL/Performance+considerat
ions
[DataWindowTest.Views.BView] Feature used '0' of '2' times, consider
turning it off by default
----------------------------------------------------------------

****************************************************************
End of ApiCop (r) results, generation took '00:00:00.137'
****************************************************************

Architecture
ApiCop provides a set of components that help developers of frameworks to aid developers during the usage of their frameworks. Below is a
graphical presentation of the components.

The green parts are the only components that end-users will use. The blue parts are components for Api developers.

Cops
The IApiCop is responsible for containing all the rules that are used inside a class. A class should contain only one IApiCop and one or more
rules.
Retrieving an IApiCop for a class

Retrieving an IApiCop for a class


To retrieve an IApiCop for a class, use the following code:

private static readonly IApiCop = ApiCopManager.GetCurrentClassApiCop();

Rules
Rules always belong to an IApiCop instance. Rules are registered once and then updated when needed, based on the requirement of the rule.
Rules are normally custom-made, but Catel does provide a few base implementations.
Registering rules
Updating rules

Available rules
UnusedFeatureApiCopRule
Usage

Registering rules
To register a rule in the IApiCop, use the following code:

ApiCop.RegisterRule(new
UnusedFeatureApiCopRule("UserControlLogic.InfoBarMessageControl", "The
InfoBarMessageControl is not found in the visual tree. This will have
a negative impact on performance. Consider setting the
SkipSearchingForInfoBarMessageControl or
DefaultSkipSearchingForInfoBarMessageControlValue to true.",
ApiCopRuleLevel.Error,
"https://catelproject.atlassian.net/wiki/display/CTL/Performance+considerations"));

The first argument is the name of the rule. This is a unique identifier and allows users to ignore rules by this name. The next parameter is a good
extension which will explain to the end-developer what is wrong and why the rule is created in the first place. In this case it is about the InfoBarMe
ssageControl which might have a negative impact on performance.
It is good practice to use the ClassName.FeatureName for the rule names

Updating rules
Once a rule is registered, it must be updated to actually provide any useful information. How a rule must be updated depends on the rule
implementation, but the code below shows how the feature can be used. This specific rule is implemented to check if the InfoBarMessageControl i
s actually used by the software. If it is, the counter is increased as "feature being used", otherwise "feature not being used".

_infoBarMessageControl = FindParentByPredicate(TargetControl, o => o is


InfoBarMessageControl) as InfoBarMessageControl;
ApiCop.UpdateRule<UnusedFeatureApiCopRule>("UserControlLogic.InfoBarMessageControl",
rule => rule.IncreaseCount(_infoBarMessageControl != null,
TargetControlType.FullName));

This code shows the regular code executed by the framework (the search in the visual tree) and the update of the rule. Note that the update
method only requires the following things: the name, a callback method and a tag. The reason a callback method is being used is that the callback
will only be executed when a debugger is attached to minimize the impact on performance in production scenarios.
It is good practice to use the final class name as as tag (especially when the rule is registered in a base class)

Available rules
Catel provides the following rules out of the box.

UnusedFeatureApiCopRule
This rule contains several counters. Each time code is executed, one must call the IncreaseCount method and specify if the feature is being used.

Usage

ApiCop.UpdateRule<UnusedFeatureApiCopRule>("ruleName",
rule => rule.IncreaseCount(isFeatureBeingUsed));

Listeners
Listeners are a way to get information about the cops and their rules in the framework. The ApiCopManager will take care of all the retrieval of the
results and the registration of the cops. The registered listeners are used by the ApiCopManager.WriteResults method to write the output to. To
add a listener and be able to see the output of the ApiCop feature, use the following code:

var apiCopListener = new ConsoleApiCopListener();


ApiCopManager.AddListener(apiCopListener);

After the listeners are added, one can call ApiCopManager.WriteResults:

ApiCopManager.WriteResults();

Customizing grouping
Creating custom listeners

Customizing grouping
It is possible to group the listeners. To specify the grouping, use the following code:

var apiCopListener = new ConsoleApiCopListener();


apiCopListener.Grouping = ApiCopListenerGrouping.Rule;

The following grouping options are available:


Grouping name

Description

Cop

Sort by the name of the class in which the cop is registered.

Rule

Sort by the rule name.

Tag

Sort by tag, which is dependent on the rule implementation. It is recommended though to use the final class name as tag.

Creating custom listeners


Catel provides several listeners out of the box. To create custom listeners, the only requirement is to implement the IApiCopListener. To make it
easier to create custom listeners (such as an HTML listener), Catel provides the following base classes which can also be used as a base for
custom listeners:
ApiCopListenerBase
Gives most flexibility, but is also more work to implement
TextApiCopListenerBase
Is fully prepared for all text-based listeners (such as console, text file, etc), and only requires the implementation of the WriteLine method

Argument checking
It is best practice to always check if the input to a method is correct. If not, an exception should be thrown. Most people do not check for
exceptions correctly and lots of null reference exceptions inside a deep stacktrace are hard to solve.
Catel does check the input on every method. Normally, a check would look like this:

public void CheckForException(object obj)


{
if (obj == null)
{
throw new ArgumentNullException("obj");
}
}

However, Catel extensively logs all behavior, thus all the checks started to look like this:

public void CheckForException(object obj)


{
if (obj == null)
{
Log.Debug("Argument 'obj' is null in CheckForException");
throw new ArgumentNullException("obj");
}
}

Handling input correctly in such a case takes a lot of space and repetitive code. Therefore the Argument class is developed. This way, it is very
simple to check for arguments:

public void CheckForException(object obj)


{
Argument.IsNotNull("obj", obj);
}

Or, if a range should be checked:

public void CheckForException(int myInt)


{
Argument.IsNotOutOfRange("myInt", myInt, 0, 10);
}

A final example is to check whether a type implements a specific interface:

public void CheckForException(object obj)


{
Argument.ImplementsInterface("obj", obj, typeof(INotifyPropertyChanged));
}

Caching
Caching is about improve applications performance. The most expensive performance costs of the applications are related with the data
retrieving, typically when this data requires to be moved a cross the network or loaded from disk. But some data have an slow changing behavior
(a.k.a non-volatile) and doesn't requires to be re-read with the same frequency of the volatile data.
So, to improve your application performance and handling this "nonvolatile" data from a pretty clean approach, Catel comes with a CacheStorage
<TKey, TValue> class. Notice that the first generic parameter is the type of the key and the second the type of the value the will be store, just like
a Dictionary<TKey, TValue> but CacheStorage isn't it just a Dictionary. This class allows you to retrieve data and storing it into the cache with
single statement and also helps you to handle expiration policy if you need it.

Initializing a cache storage


To initialize a cache storage field into your class use the follow code:

private readonly CacheStorage<string, Person> _personCache = new CacheStorage<string,


Person>(storeNullValues: true);

Retrieve data and storing into cache with single statement


To retrieve data and storing into a cache with a single statement use the follow code:

var person = _personCache.GetFromCacheOrFetch(Id, () => service.FindPersonById(Id));

When this statement is executed more than once times with the with the same key, the value will be retrieved from the cache storage instead from
the service call. The service call will be executed just the first time or if the item is removed from the cache manually or automatically due by the
expiration policy.

Using cache expiration policies


The cache expiration policies adds a removal behavior to the cache storage items. A policy signals that an item is expired to makes that cache
storage removes the item automatically.
A default cache expiration policy initialization code can be specified during cache storage initialization constructor:

CacheStorage<string, Person> _personCache = new CacheStorage<string, Person>(() =>


ExpirationPolicy.Duration(TimeSpan.FromMinutes(5)), true);

You can specify an specific expiration policy for an item when it's storing:

_personCache.GetFromCacheOrFetch(id, () => service.GetPersonById(id),


ExpirationPolicy.Duration(TimeSpan.FromMinutes(10)));

The default cache policy specified at cache storage initialization will be used if during item storing the expiration policy is not specified.

Build-in expiration policies


Catel comes with build-in expiration policies. They are listed in the follow table:
Expiration policy

Type

Description

AbsoluteExpirationPolicy

Time-base

The cache item


will expire on
the absolute
expiration
DateTime

DurationExpirationPolicy

Time-base

The cache item


will expire
using the
duration
TimeSpan to
calculate the
absolute
expiration from
DateTime.Now

Initialization code sample

ExpirationPolicy.Absolute(new DateTime(21, 12, 2012))

ExpirationPolicy.Duration(TimeSpan.FromMinutes(5))

SlidingExpirationPolicy

CustomExpirationPolicy

CompositeExpirationPolicy

Time-base

Custom

Custom

The cache item


will expire
using the
duration
TimeSpan to
calculate the
absolute
expiration from
DateTime.Now,
but everytime
the item is
requested, it is
expanded
again with the
specified
TimeSpan
The cache item
will expire
using the
expire function
and execute
the reset action
if is specified.
The example
shows how
create an
sliding
expiration
policy with a
custom
expiration
policy.
Combines
several
expiration
policy into a
single one. It
can be
configured to
expires when
any policy
expires or
when all
policies
expires.

ExpirationPolicy.Sliding(TimeSpan.FromMinutes(5))

var startDateTime = DateTime.Now;


var duration = TimeSpan.FromMinutes(5);
ExpirationPolicy.Custom(() => DateTime.Now >
startDateTime.Add(duration), () => startDateTime =
DateTime.Now);

new CompositeExpirationPolicy().Add(ExpirationPolicy.Sliding(
TimeSpan.FromMinutes(5))).Add(ExpirationPolicy.Custom(()=>...))

Implementing your own expiration cache policy


If the CustomExpirationPolicy is not enough, you can implement you own expiration policy to makes that cache item expires triggered from a
custom event. You are also able to add some code to reset the expiration policy if the item is read from the cache before it expires (just like Slidin
gExpirationPolicy does).
To implement an expiration cache policy use the follow code template:

public class MyExpirationPolicy : ExpirationPolicy


{
public MyExpirationPolicy():base(true)
{
}
public override bool IsExpired
{
get
{
// Add your custom expiration code to detect if the item expires
}
}
public override void OnReset()
{
// Add your custom code to reset the policy if the item is read.
}
}

The base constructor has a parameter to indicate if the policy can be reset. Therefore, if you call the base constructor with false then
the OnReset method will never called.

Configuration
Catel makes it very easy to use configurations on all supported platforms.
Getting values from the configuration
Setting values to the configuration
Customizing the way values are stored
Below is a table to explain what technology is used per platform to retrieve and store configuration values.
Platform

Technology

.NET

ConfigurationManager.AppSettings

Silverlight

IsolatedStorageSettings.ApplicationSettings

Windows Phone

IsolatedStorageSettings.ApplicationSettings

WinRT

ApplicationData.Current.LocalSettings

PCL

Not supported

Getting values from the configuration


To retrieve values from the configuration, use the following code:

var configurationService = new ConfigurationService();


var mySetting = configurationService.GetValue<int>("mySetting", 42);

The code above will retrieve the values from the configuration. If the configuration value does not exist, it will return 42 as default value.
It's best to retrieve the service from the dependency resolver or let it be injected into the classes using it

Setting values to the configuration


To store values in the configuration, use the following code:

var configurationService = new ConfigurationService();


configurationService.SetValue("mySetting", 42);

It's best to retrieve the service from the dependency resolver or let it be injected into the classes using it

Customizing the way values are stored


The ConfigurationService is written with extensibility in mind. Though it defaults to the .NET local storage system, it is very easy to create a
customized configuration service. Below is an example on how to customize the service so it reads and writes values from/to a database.

public class DbConfigurationService : ConfigurationService


{
protected override bool ValueExists(string key)
{
using (var context = new ConfigurationContext())
{
return (from config in context.Configurations
where config.Key == key
select config).Any();
}
}
protected override string GetValueFromStore(string key)
{
using (var context = new ConfigurationContext())
{
return (from config in context.Configurations
where config.Key == key
select config.Value).First();
}
}
protected override void SetValueToStore(string key, string value)
{
using (var context = new ConfigurationContext())
{
var configuration (from config in context.Configurations
where config.Key == key
select config).FirstOrDefault();
if (configuration == null)
{
configuration = context.CreateObject<Configuration>();
configuration.Key = key;
}
configuration.Value = value;
context.SaveChanges();
}
}
}

Don't forget to register the customized ConfigurationService in the ServiceLocator

Data handling
This part of the documentation is all about data handling the way it should that is available via Catel. Some parts are based on the article on Code
Project, but this documentation is more up-to-date.
The first thing that is important is that lots of developers lose way too much time writing custom serializable objects. Serialization is a field of
expertise, and only a handful of developers I know really master the serialization of objects (think of version changes of the assembly, class
changes (new or removed properties), etc.). Most developers think they master serialization by creating a BinaryFormatter object like the code
belows show:

var serializer = new BinaryFormatter();


var myObject = (MyObject)serializer.Deserialize(stream);

Most developers dont know that reflection breaks when:


You change the version number of your assembly;
You add or remove a property or field;
You add or remove an event.
And even if you know, it takes a lot of knowledge and courage to start beating the beast of burden. Like every developer, I also encountered this
and was writing backwards compatibility code until I had enough of it and decided to master the field of serialization. The result is the ModelBase
class, which can be used as a base class for all data objects that need to be held in memory and maybe serialized to disk (or a stream, or XML, or
...).
ObservableObject
DispatcherObservableObject
ModelBase
Using ModelBase as base for entities
Advanced property change notifications
WCF services

ObservableObject
The ObservableObject is a very lightweight class that only implements the INotifyPropertyChanging and INotifyPropertyChanged interfaces. This
class is ideal for simple objects that only need property notification. Below is an example:

public class Person : ObservableObject


{
private string _firstName;
private string _middleName;
private string _lastName;
public Person(string firstName, string middleName, string lastName)
{
FirstName = firstName;
MiddleName = middleName;
LastName = lastName;
}
public string FirstName
{
get { return _firstName; }
set
{
RaisePropertyChanging(() => FirstName);
var oldValue = _firstName;
_firstName = value;
RaisePropertyChanged(() => FirstName, oldValue, value);
}
}
public string MiddleName
{
get { return _middleName; }
set
{
RaisePropertyChanging(() => MiddleName);
var oldValue = _middleName;
_middleName = value;
RaisePropertyChanged(() => MiddleName, oldValue, value);
}
}
public string LastName
{
get { return _lastName; }
set
{
RaisePropertyChanging(() => LastName);
var oldValue = _lastName;
_lastName = value;
RaisePropertyChanged(() => LastName, oldValue, value);
}
}
}

DispatcherObservableObject
Note that the DispatcherObservableObject is located in Catel.MVVM because it uses the IDispatcherService

The DispatcherObservableObject is a class that derives from the ObservableObject class. The only difference is that the DispatcherObservableO
bject will dispatch all property change notifications to the UI thread. Below is a class that uses the DispatcherObservableObject and is thread-safe
for the change notifications.

public class Person : DispatcherObservableObject


{
private string _firstName;
private string _middleName;
private string _lastName;
public Person(string firstName, string middleName, string lastName)
{
FirstName = firstName;
MiddleName = middleName;
LastName = lastName;
}
public string FirstName
{
get { return _firstName; }
set
{
RaisePropertyChanging(() => FirstName);
var oldValue = _firstName;
_firstName = value;
RaisePropertyChanged(() => FirstName, oldValue, value);
}
}
public string MiddleName
{
get { return _middleName; }
set
{
RaisePropertyChanging(() => MiddleName);
var oldValue = _middleName;
_middleName = value;
RaisePropertyChanged(() => MiddleName, oldValue, value);
}
}
public string LastName
{
get { return _lastName; }
set
{
RaisePropertyChanging(() => LastName);
var oldValue = _lastName;
_lastName = value;
RaisePropertyChanged(() => LastName, oldValue, value);
}
}
}

ModelBase
Using the class

Defining properties
Default values for reference types
Functionality provided out of the box
The ModelBase (previously known as the DataObjectBase) class is a generic base class that can be used for all your data classes.
Fully serializable
It is now really easy to store objects on disk or serialize them into memory, either binary or in XML. The data object supports this out of
the box, and automatically handles the (de)serialization.
Support property changed notifications
The class supports the INotifyPropertyChanging and INotifyPropertyChanged interfaces so this class can easily be used in WPF,
Silverlight and applications to reflect changes to the user.
Backwards compatibility
When serializing your objects to binary, it is hard to maintain the right versions. When you add a new property to a binary class, or
change a namespace, the object cannot be loaded any longer. The data object base takes care of this issue and supports backwards
compatibility.
Validation
The class implements the IDataErrorInfo interface so it is possible to validate the data object and check the errors. This way, no custom
validation code needs to be written outside the data class.
Backup & revert
The class implements the IEditableObject interface which makes it possible to create a state of the object. Then all properties can be
edited, and finally, the changes can be applied or cancelled.

Using the class


Using the class is extremely simple. Just declare a new class that derives from ModelBase and you are ready to go:

/// <summary>
/// MyObject class which fully supports serialization,
/// property changed notifications, backwards compatibility and error checking.
/// </summary>
#if !SILVERLIGHT
[Serializable]
#endif
public class MyObject : ModelBase<MyObject>
{
/// <summary>
/// Initializes a new object from scratch.
/// </summary>
public MyObject() { }
#if !SILVERLIGHT
/// <summary>
/// Initializes a new object based on <see cref="SerializationInfo"/>.
/// </summary>
/// <param name="info"><see cref="SerializationInfo"/>
//
that contains the information.</param>
/// <param name="context"><see cref="StreamingContext"/>.</param>
protected MyObject(SerializationInfo info, StreamingContext context)
: base(info, context) { }
#endif
}

As you can see in the code above, the MyObject class derives from ModelBase and provides an empty constructor, but also a constructor that is
used for binary deserialization. The code above might look complex, but it is created using the model code snippet, and you only have to type the
name of the class.

Defining properties
Defining properties for the class is very easy, and works the same like dependency properties. The advantages of this way of defining properties
are:

Properties defined like this are automatically included during serialization; no need to specify complex data contracts;
You can specify a default value for a property which will be used when the class is constructed or the property is not found during
deserialization (in case this property is added to an existing class);
The PropertyData object can be used to retrieve property values so the compiler checks for errors;
You can directly subscribe to change notifications, and all properties automatically support INotifyPropertyChanged out of the box.
Below is the code that defines a new property Name of type string:

/// <summary>
/// Gets or sets the name.
/// </summary>
public string Name
{
get { return GetValue<string>(NameProperty); }
set { SetValue(NameProperty, value); }
}
/// <summary>
/// Register the Name property so it is known in the class.
/// </summary>
public static readonly PropertyData NameProperty = RegisterProperty("Name",
typeof(string), string.Empty);

A registered property can be excluded from serialization if wanted. When the object is deserialized, the default value will be used for the property
in that case.

Default values for reference types


In lots of cases, a default value for reference types is required in the property definitions. However, and you might have noticed this behavior in for
example dependency properties, using an instance as default value can result in unexpected behavior.
Below is an example of a "regular" property registration using a default value for a collection property:

public static readonly PropertyData NameProperty =


RegisterProperty("PersonCollection", typeof(Collection<Person>), new
Collection<Person>());

However, instead of creating a new collection for each new object with this property, only one collection will be created that will be used by all
classes that have this property registered. One solution is to pass null as default value and create the collection in the constructor. A better
solution is to use the override of RegisterProperty with the callback parameters:

public static readonly PropertyData NameProperty =


RegisterProperty("PersonCollection", typeof(Collection<Person>), () => new
Collection<Person>());

This way, every time a new value is needed, the callback will be invoked to create the default value and you will have a true default value for
reference types.

Functionality provided out of the box


The ModelBase provides a lot of functionality out of the box. A few points I want to mention are:
INotifyPropertyChanged
All properties registered using the RegisterProperty method automatically take care of change notifications.
IDataErrorInfo
It is very easy to set field and business errors using the SetFieldError and SetBusinessError methods that can be used in the overridable Validate

Fields and ValidateBusinessRules methods.


IEditableObject
The data object can automatically create an internal backup and restore it, if required, using the IEditableObject interface.
Serialization
As told many times before, using the SavableModelBase, you can simply save your file to a stream (file on disk, stream in memory, etc.).
Keep in mind that this class is not suitable for database communication, there are much better ways to handle this (ORM mappers such as Entity
Framework, NHibernate, LLBLGen Pro, etc.).

Using ModelBase as base for entities


It is possible to use the ModelBase as base class when using EF or any other OR mapper.
Setting up ModelBase as base class
Ignoring default Catel properties in models

Setting up ModelBase as base class


There are a few caveats when using the ModelBase as base class for your entities. One of them is that IsDirty is always true because the
properties from the persistence store are set after the constructor. This guide will explain how to work past that problem.
1. Create a class named EntityBase with the following code:

public class EntityBase : ModelBase


{
protected EntityBase() { }
protected EntityBase(SerializationInfo info, StreamingContext context)
: base(info, context) { }
internal void ClearDirtyFlag()
{
IsDirty = false;
}
}

2. Derive from EntityBase instead of ModelBase so the layer that loads the data can clear the IsDirty flag.
3. When loading the data from the database and setting the initial values, use this code:

var company = new DTO.Company()


{
Address = domainEntity.Address,
City = domainEntity.City,
CompanyID = domainEntity.CompanyID,
CompanyName = domainEntity.CompanyName,
PostalCode = domainEntity.PostalCode,
PostalCodeAndCity = domainEntity.PostalCodeAndCity
};
company.ClearDirtyFlag();
return company;

Note the ClearDirtyFlag call, which is very important to make the IsDirty property behave correctly.
4. Check the IsDirty of the model, not the view model when checking whether the model is dirty inside a view model.

Ignoring default Catel properties in models

It is possible to ignore the default Catel properties in the models for EF code-first. To accomplish this, use the following code:

protected override void OnModelCreating(DbModelBuilder modelBuilder)


{
modelBuilder.Types().Configure(c => c.Ignore("IsDirty"));
modelBuilder.Types().Configure(c => c.Ignore("Mode"));
modelBuilder.Types().Configure(c => c.Ignore("IsReadOnly"));
base.OnModelCreating(modelBuilder);
}

Or, if you only want to do this for classes inheriting Modelbase, use the following code:

protected override void OnModelCreating(DbModelBuilder modelBuilder)


{
modelBuilder.Types().Where(t => t.IsSubclassOf(typeof(ModelBase))).Configure(c =>
c.Ignore("IsDirty"));
modelBuilder.Types().Where(t => t.IsSubclassOf(typeof(ModelBase))).Configure(c =>
c.Ignore("Mode"));
modelBuilder.Types().Where(t => t.IsSubclassOf(typeof(ModelBase))).Configure(c =>
c.Ignore("IsReadOnly"));
base.OnModelCreating(modelBuilder);
}

Advanced property change notifications


Sometimes the old value is needed in case of property change event. However, the INotifyPropertyChanged interface does not provide any of
this. To support this behavior, a new version of the PropertyChangedEventArgs is created called AdvancedPropertyChangedEventArgs. This
class derives from PropertyChangedEventArgs so the interfaces are not broken, but it does add additional functionality to the software system.
Getting old value automatically
Getting more information from the inside
Getting mode information from the outside
Providing old value manually
Some sidenotes

Getting old value automatically


When using the ModelBase or ViewModelBase classes, the old and new value of a property are automatically provided on a property change.
There are two ways to get more information about a property change event.

Getting more information from the inside


The easiest way to get more information on the inside is to override the OnPropertyChanged method. It automatically provides an instance of the
AdvancedPropertyChangedEventArgs:

protected override void OnPropertyChanged(AdvancedPropertyChangedEventArgs e)


{
}

Getting mode information from the outside


Getting the information from outside the objects is a bit more work. This is because the PropertyChanged event still provides a value of the Proper

tyChangedEventArgs class. Therefore, it is required to cast the value:

private void OnObjectPropertyChanged(PropertyChangedEventArgs e)


{
var advancedArgs = e as AdvancedPropertyChangedEventArgs;
if (advancedArgs != null)
{
// a value of AdvancedPropertyChangedEventArgs is now available
}
}

Providing old value manually


When using the dependency property a-like property registration, the old and new value are automatically provided by the classes. However,
when using the ObservableObject, the old and new value are not automatically provided. Therefore, it is possible to provide these values
manually:

private string _firstName;


public string FirstName
{
get { return _firstName; }
set
{
var oldValue = _firstName;
_firstName = value;
RaisePropertyChanged(() => FirstName, oldValue, value);
}
}

When the values are not provided, the old and new value are set to null.

Some sidenotes
As you might have noticed, the AdvancedPropertyChangedEventArgs also provide the IsOldValueMeaningful and the IsNewValueMeaningful. Th
ese are introduced because it is not always possible to determine the old or new value (for example, when the property name is string.Empty,
there is no old value or new value). Therefore, the OldValue and NewValue properties are null, but doesn't mean that those are the actual old and
new values.
It is always required to check whether the values are meaningful before actually handing them:

protected override void OnPropertyChanged(AdvancedPropertyChangedEventArgs e)


{
if (e.IsOldValueMeaningful)
{
// Handle old value
}
if (e.IsNewValueMeaningful)
{
// Handle new value
}
}

WCF services
Starting with version 2.3, both the windows and Silverlight (Silverlight and WP7) libraries use the DataContractSerializer to (de)serialize xml by
default for the ModelBase. The xml serialization technique supports complex nested object graphs. This means that classes deriving from ModelB
ase can be used to transfer data using WCF services.

With the help of the Catel.Fody plugin, it is possible to dynamically weave custom GetXmlSchema methods so no custom code is
required to support WCF and DataContracts

There is no need to decorated the classes with DataMember or DataContract attributes with one single exception: when a class contains
properties that are defined using a base class, the descending (or inherited) classes must be known. Catel could, in theory, reflect the whole App
Domain to gather these classes, but that would be a major hit on performance. Therefore the inherited classes must be defined manually using
the KnownType attribute.

[Serializable, KnownType(Manager), KnownType(Employee)]


public class Job : ModelBase<Job>
{
// abstract Person class which can be Manager or Employee
public Person Person { get; set; }
}

When adding the service reference, make sure to check the "Reuse types in all referenced assemblies" like shown in the image below:

Exception handling
With exception handling in Catel, it is possible to create an exception handling policy and execute code in a safe way without have to check all the
exception types manually. Catel exposes this technique via the IExceptionService.
Setting up the IExceptionService
Executing code using the IExceptionService
Executing an action
Executing a function
Use the retry capabilities
Retry Immediately
Retry defined
Process with retry
Subscribe to the retry events
Handling exceptions manually
Unregistering exceptions
Buffering
Define the way to buffer
Subscribe to the buffering events
Determine if an exception type are registered for handling
Get a specific exception handler

Setting up the IExceptionService


It is important to register an exception in the service and let Catel know how it should be handled. The service handles exceptions in the way they
are added to the IExceptionService.
The example below registers several exceptions and how they should be handled. When a FileNotFoundException occurs, it will show a message
to the user. For any other exception, it will log the exception and show a message that the user should contact the developers.

var dependencyResolver = this.GetDependencyResolver();


var exceptionService = dependencyResolver .Resolve<IExceptionService>();
exceptionService.Register<FileNotFoundException>(exception =>
dependencyResolver.Resolve<IMessageService>().Show(exception.Message));
exceptionService.Register<Exception>(exception =>
{
Log.Error(exception);
dependencyResolver.Resolve<IMessageService>().Show("An unknown exception occurred,
please contact the developers");
});

The IExceptionService checks for type hierarchy. For example, when an exception as type Exception is registered, this handler will
handle all exceptions

Executing code using the IExceptionService


The Process method is responsible to keep track of all exceptions which might occur and will handle them if they are registered. If one of your
registered exceptions is thrown by the code, the Process method will handle it and perform the action defined while the registration operation (for
example, by showing a message box).
The Process method comes in two flavors: as action and as function.

Executing an action
var dependencyResolver = this.GetDependencyResolver();
var exceptionService = dependencyResolver.Resolve<IExceptionService>();
exceptionService.Process(() => { throw new ArgumentOutOfRangeException(); });

Executing a function
var dependencyResolver = this.GetDependencyResolver();
var exceptionService = dependencyResolver.Resolve<IExceptionService>();
var result = exceptionService.Process<int>(() => 1 + 1);

You can process yours actions asynchronously by using the ProcessAsync method.

Use the retry capabilities


In some cases, you can want to have possibility to retry an action a certain number of times before finally handle your exception. Let see how the I
ExceptionService allows us to handle this kind of cases.

Firstly, you need to define how the IExceptionService will retry your action in case of error, two possibilities are provided for that.

Retry Immediately
When you setting up your exceptions on IExceptionService, you have to additionnally use the OnErrorRetryImmediately method like shown below
:

var dependencyResolver = this.GetDependencyResolver();


var exceptionService = dependencyResolver.Resolve<IExceptionService>();
exceptionService.Register<ArgumentNullException>(exception => { /* Do something */ })
.OnErrorRetryImmediately();

This method will say to the IExceptionService to retry the action each times this one throw an exception until it succeed and without to wait before
the next retry.
You can also specify the number of times you want the IExceptionService to retry immediately like this for example : OnErrorRetryImme
diately(5)

Retry defined
You have also the possibility to define more deeply the way you want your actions to be retried by using the OnErrorRetry method like shown
below.

var dependencyResolver = this.GetDependencyResolver();


var exceptionService = dependencyResolver.Resolve<IExceptionService>();
exceptionService.Register<ArgumentNullException>(exception => { /* Do something */ })
.OnErrorRetry(5, TimeSpan.FromMinutes(2));

Where 5 represents the nombre of times the action will be retried and TimeSpan.FromMinutes(2) the interval between the retries.

Process with retry


If you have provided a retry policy, you can use the ProcessWithRetry method to expect have your policy applied on error. Below an example :

var dependencyResolver = this.GetDependencyResolver();


var exceptionService = dependencyResolver.Resolve<IExceptionService>();
exceptionService.ProcessWithRetry(() =>
{
/* Do something */
});

Subscribe to the retry events


Can you subscribe to the events which are thown each time an action is retried like this :

var dependencyResolver = this.GetDependencyResolver();


var exceptionService = dependencyResolver.Resolve<IExceptionService>();
exceptionService.RetryingAction +=
(sender, eventArgs) =>
Console.WriteLine("The '{0}' have caused retrying action for the
'{1}' times.",
eventArgs.LastException, eventArgs.CurrentRetryCount);

Handling exceptions manually


It is possible to manually handle exceptions using the service. This is useful when you don't want to wrap code in the Process method, but still
want to be able to create a generic exception handling policy.

var dependencyResolver = this.GetDependencyResolver();


var exceptionService = dependencyResolver.Resolve<IExceptionService>();
try
{
var value = 150/0;
}
catch (DivideByZeroException exception)
{
exceptionService.HandleException(exception);
}

If the exception can be handled, the registered action will be executed, but your code can safely continue. If the exception (in this case DivideByZ
eroException) is not registered, the HandleException method will rethrow the exception.

Unregistering exceptions
Although it will probably hardly used, it is possible to unregister exceptions again using the code below:

var exceptionService = dependencyResolver.Resolve<IExceptionService>();


exceptionService.Unregister<ArgumentException>();

Buffering
Define the way to buffer
You can want to throttle down the number of exceptions you receive when a production process goes awry for example. You can do it through the
UsingTolerance extension method as shown below :

var dependencyResolver = this.GetDependencyResolver();


var exceptionService = dependencyResolver.Resolve<IExceptionService>();
exceptionService.Register<DivideByZeroException>(exception => { })
.UsingTolerance(9, TimeSpan.FromSeconds(10.0));

Here, the idea is to only receive the 10th exception message.

Subscribe to the buffering events


Can you subscribe to the events which are thown each time an exception is buffered like this :

var dependencyResolver = this.GetDependencyResolver();


var exceptionService = dependencyResolver.Resolve<IExceptionService>();
exceptionService.ExceptionBuffered +=
(sender, eventArgs) =>
Console.WriteLine("The '{0}' is buffered for at '{1}'.",
eventArgs.BufferedException, eventArgs.DateTime);

Determine if an exception type are registered for handling


If you want to know if an exception type have its policy registered on the IExceptionService, you can do this by using the IsExceptionRegistered m
ethod like shown below :

var dependencyResolver = this.GetDependencyResolver();


var exceptionService = dependencyResolver.Resolve<IExceptionService>();
if (exceptionService.IsExceptionRegistered<ArgumentNullException>())
{
//Do something
}

Get a specific exception handler


If you want to retrieve the registered exception handler for an exception type, you have to use the GetHandler method like shown below :

var dependencyResolver = this.GetDependencyResolver();


var exceptionService = dependencyResolver.Resolve<IExceptionService>();
var exceptionHandler = exceptionService.GetHandler<ArgumentException>();

IoC (ServiceLocator and TypeFactory)


Before Catel 2.0, the IoC container used internally was Unity. However, this forced all users to use and configure Unity as the IoC container in
their apps and required the shipping of the libraries as well. Since Catel 2.0, a different technique is used which allows the end-developer to use
the IoC container technique of their choice.
Different components in IoC
Getting components for any object
Also see:
Dependency injection
Introductions to IoC components
Automatic type registration
Setting up the ServiceLocator using configuration
Replacing the default components

Different components in IoC


There are several different components that are very important for the IoC in Catel:
ServiceLocator
Component that is responsible for the registrations of all types. This is the actual IoC container.
TypeFactory

Component that is responsible to create types. This uses the IServiceLocator to retrieve the types which are required to instantiate a
type.
DependencyResolver
Light-weight implementation of the IServiceLocator which does not expose any register methods, but only allows to resolve types.

Getting components for any object


In every object, it is possible to use the Default properties to retrieve the instances of each component. This will cause problems when different
scoping is used. To always be sure to get the right component for the object you are working with, it is recommended to use the following
extension methods:

using Catel.IoC; // Contains ObjectExtensions which allow use of below extension


methods
public class MyService
{
public void SomeMethod()
{
// If you need to create a type with the current scope type factory
var typeFactory = this.GetTypeFactory();
// If you need to register a type with the current scope service locator
var serviceLocator = this.GetServiceLocator();
// If you need to resolve a type with the current scope and the type is not
injected via dependency injection
var dependencyResolver = this.GetDependencyResolver();
}
}

Dependency injection
The ServiceLocator in Catel supports dependency injection.
Introduction to dependency injection
Using dependency injection in Catel
Constructor injection
Manually defining the constructor to use for dependency injection
Advanced dependency injection
Property injection
Type is automatically determined based on property type
Type is manually defined
Using tags
Disabling dependency injection

Introduction to dependency injection


Some people make dependency injection hard to understand, or maybe they don't understand it themselves. Dependency injection simply means
that instead of hard referencing or instantiating other classes (dependendies), the dependencies are injected into the class via the constructor.
Example 1: bad, instantiates the dependencies itself

public class MyClass


{
private IFirstDependency _firstDependency;
private ISecondDependency _secondDependency;
public MyClass()
{
_firstDependency = new FirstDependency();
_secondDependency = new SecondDependency();
}
}

Example 2: good, retrieves the dependencies via the service locator

public class MyClass


{
private IFirstDependency _firstDependency;
private ISecondDependency _secondDependency;
public MyClass()
{
_firstDependency = ServiceLocator.Instance.ResolveType<IFirstDependency>();
_secondDependency = ServiceLocator.Instance.ResolveType<ISecondDependency>();
}
}

Example 3: good, gets the dependencies injected

public class MyClass


{
private IFirstDependency _firstDependency;
private ISecondDependency _secondDependency;
public MyClass(IFirstDependency firstDependency, ISecondDependency
secondDepdenceny)
{
Argument.IsNotNull("firstDependency", firstDependency);
Argument.IsNotNull("secondDependency", secondDependency);
_firstDependency = firstDependency;
_secondDependency = secondDependency;
}
}

There are other ways of using dependency injection, for example via attributes. This documentation will focus on dependency injection
via the constructor only

Using dependency injection in Catel

Constructor injection
Dependency injection via the ServiceLocator in Catel is enabled by default. This means that when a type is resolved from the container, it will
automatically use dependency injection to construct the type if it is not registered as instance.
It will first search for all available constructors on the type that will be instantiated. Then, for each constructor, starting with the one with the most
parameters, it will try to retrieve all values. If one fails, it will go to the next. If all fail, it will try to use the default constructor without parameters. If
that fails as well, then the type cannot be constructed and an exception will be thrown.
To get a better understanding of what happens, see the class below:

public class MyClass


{
private IFirstDependency _firstDependency;
private ISecondDependency _secondDependency;
public MyClass()
: this(null) { }
public MyClass(IFirstDependency firstDependency)
: this(firstDependency, null) { }
public MyClass(IFirstDependency firstDependency, ISecondDependency
secondDependency)
{
_firstDependency = firstDependency;
_secondDependency = secondDependency;
}
}

When the MyClass will be retrieved from the ServiceLocator, this will happen:
1. Find constructor with most parameters (the one with both firstDependency and secondDependency). If both IFirstDependency and
ISecondDependency can be resolved from the ServiceLocator, the type will be constructed with the constructor. Otherwise it will proceed
with step 2.
2. Find next constructor with most parameters (the one with only firstDependency). If IFirstDependency can be resolved from the
ServiceLocator, the type will be constructed with the constructor. Otherwise it will proceed with step 3.
3. At this point, no constructor could be used. In this case, the ServiceLocator will try to use the default constructor (the one without
parameters) as last resort to instantiate the type.

Manually defining the constructor to use for dependency injection


Catel first sorts the constructors based on the number of parameters. Then it will "sub-sort" the same number of parameters and puts parameters
with Object and DynamicObject as last so it will first try all constructors with the best possible matches
If Catel is still unable to pick the right constructor in a class, this behavior can be overridden by decorating the constructor with the DependencyInj
ectionConstructor attribute:

public MyClass(IPerson person)


{
}
[InjectionConstructor]
public MyClass(Person person)
{
// Catel will now first try to use this constructor, no matter the order or number
of parameters
}

Advanced dependency injection


Starting with Catel 3.7, a new type of dependency injection is supported. It allows a developer to instantiate types that combine custom
constructor injection with dependency injection. The class belows shows an interesting combination of custom values that need to be injected and
dependencies that can be retrieved from the IoC container. Before Catel 3.7, one had to manually retrieve the dependencies from the IoC
container when it also required other dependencies to be injected that were not registered in the IoC container:

public class PersonViewModel : ViewModelBase


{
private readonly IMessageService _messageService;
private readonly IProcessService _processService;
public PersonViewModel(IPerson person)
{
Argument.IsNotNull(() => person);
Person = person;
_messageService = ServiceLocator.Default.ResolveType<IMessageService>();
_processService = ServiceLocator.Default.ResolveType<IProcessService>();
}
...
}

With the new technology, such a constructor can be rewritten to truly support dependency injection:

public class PersonViewModel : ViewModelBase


{
private readonly IMessageService _messageService;
private readonly IProcessService _processService;
public PersonViewModel(IPerson person, IMessageService messageService,
IProcessService processService)
{
Argument.IsNotNull(() => person);
Argument.IsNotNull(() => messageService);
Argument.IsNotNull(() => processService);
Person = person;
_messageService = messageService;
_processService = processService
}
...
}

This feature is initially written to support dependency injection in combination with nested user controls

The advanced dependency injection can be used by using the TypeFactory class. Below is an example on how to create a new type using
advanced dependency injection:

var personViewModel =
TypeFactory.Default.CreateInstanceWithParametersAndAutoCompletion<PersonViewModel>(new
Person());

As you can see it is only required to pass in the objects that are not registered in the IoC container. All other dependencies will be automatically
resolved from the ServiceLocator.
Note that the order of the parameters must be the same as the constructor, otherwise the TypeFactory cannot determine the right
constructor to use

Property injection
Starting with Catel 3.8, it is also possible to use property injection. The difference with constructor injection is that the TypeFactory will
automatically set up all properties that required dependency injection.
Note that the Catel team recommends using constructor injection over property injection. Property injection looks like a silver bullet, but
is very tricky because:
1) It does not allow you to check for null values and store dependencies in private fields (when)?
2) Dependency Injection is just a technique. When using a constructor, you can force a user to provide the value and check the input.
With property injection, you can only hope that the user will set them for you, there is no way to check this (unless that is some after
constructor and dependency injection initialization routine. This is never the case if a user manually creates a type though.
To use property injection, simply decorate the properties of a class with the Inject attribute. Below are several options:

Type is automatically determined based on property type


public class MyClass
{
[Inject]
public IMyDependency MyDependency { get; set; }
}

Type is manually defined


public class MyClass
{
[Inject(typeof(IMySubclassedDependency))]
public IMyDependency MyDependency { get; set; }
}

Using tags
It is also possible to determine the tag of a registered dependency:

public class MyClass


{
[Inject(Tag = "myTag")]
public IMyDependency MyDependency { get; set; }
}

Disabling dependency injection


Maybe you don't want dependency injection because it does not give you what you need or you want a very, very small improvement in
performance. In that case, the dependency injection can be disabled using the code below:

ServiceLocator.Default.SupportedDependencyInjection = false

Introductions to IoC components


This section contains the introductions.
Introduction to the ServiceLocator
Introduction to the TypeFactory
Introduction to DependencyResolver and DependencyResolverManager
Ensuring integrity of the ServiceLocator

Introduction to the ServiceLocator


The ServiceLocator services as the container inside Catel.
Internally it uses the TypeFactory as instantiator for the services.
Catel uses it's own ServiceLocator implementing the IServiceLocator to gather all services required by Catel. For example, default services are
the IPleaseWaitService and the IUIVisualizerService. By default, when the first view model is instantiated, Catel registers all default out of the box
services to the ServiceLocator. However, it only does this when the specific services are not already registered. This allows an end-developer to
register his/her own implementations of the services before any view model is instantiated (for example, at application startup).
The ServiceLocator can be instantiated, but Catel instantiates one instance that can be used and shared amongst all objects inside the same App
Domain. The ServiceLocator can be retrieved by using ServiceLocator.Default.
For more information how types are instantiated and dependency injection, take a look at the TypeFactory documentation

Registering a type
Use the following code to register a specific type in the ServiceLocator:

ServiceLocator.Default.RegisterType<IPleaseWaitService, PleaseWaitService>();

Registering a late-bound type


Use the following code to register a late-bound type in the ServiceLocator:

ServiceLocator.Default.RegisterType<IPleaseWaitService>(x => new PleaseWaitService());

Registering an instance of a type


Catel uses the TypeFactory or Activator.CreateInstance to create the interface implementations when the object is first resolved. However,
sometimes a service constructor requires parameters or takes a long time to construct. In such cases, it is recommended to create the type
manually and register the instance of the type:

var pleaseWaitService = new PleaseWaitService();


ServiceLocator.Default.RegisterInstance<IPleaseWaitService>(pleaseWaitService);

Registering a type via MissingType event


The ServiceLocator gives the end-developer a last-resort chance to register a type when it is not registered in the ServiceLocator or any of the
external containers. This event is very useful for logging (then the developer in the log knows exactly what type is missing from the IoC container)
or it can be used to determine at runtime in a very late stage what implementation of the service must be used. To register a type via the event,
subscribe to the event and then use the following code:

private void OnMissingType(object sender, MissingTypeEventArgs e)


{
if (e.InterfaceType == typeof(IPleaseWaitService))
{
// Register an instance
e.ImplementingInstance = new PleaseWaitService();
// Or a type
e.ImplementingType = typeof(PleaseWaitService);
}
}

If both the ImplementingInstance and ImplementingType are filled, the ImplementingIntance will be used.

Resolving a type
To retrieve the implementation of a service, use the following code:

var pleaseWaitService = ServiceLocator.Default.ResolveType<IPleaseWaitService>();

Introduction to the TypeFactory


Dependency injection
Introduction to dependency injection
Using dependency injection in Catel
Disabling dependency injection
Custom initialization
The TypeFactory is responsible for actually creating types inside Catel. It uses the following mechanism:
1. List all the constructors, order them from most parameters to least parameters
2. While (constructors available)
try to construct type using injection
3. If all constructors fail, the TypeFactory will fallback to Activator.CreateInstance()

Dependency injection
The ServiceLocator in Catel supports dependency injection.

Introduction to dependency injection


Some people make dependency injection hard to understand, or maybe they don't understand it themselves. Dependency injection simply means
that instead of hard referencing or instantiating other classes (dependendies), the dependencies are injected into the class via the constructor.
Example 1: bad, instantiates the dependencies itself

public class MyClass


{
private IFirstDependency _firstDependency;
private ISecondDependency _secondDependency;
public MyClass()
{
_firstDependency = new FirstDependency();
_secondDependency = new SecondDependency();
}
}

Example 2: good, retrieves the dependencies via the service locator

public class MyClass


{
private IFirstDependency _firstDependency;
private ISecondDependency _secondDependency;
public MyClass()
{
_firstDependency = ServiceLocator.Instance.ResolveType<IFirstDependency>();
_secondDependency = ServiceLocator.Instance.ResolveType<ISecondDependency>();
}
}

Example 3: good, gets the dependencies injected

public class MyClass


{
private IFirstDependency _firstDependency;
private ISecondDependency _secondDependency;
public MyClass(IFirstDependency firstDependency, ISecondDependency
secondDepdenceny)
{
Argument.IsNotNull("firstDependency", firstDependency);
Argument.IsNotNull("secondDependency", secondDependency);
_firstDependency = firstDependency;
_secondDependency = secondDependency;
}
}

There are other ways of using dependency injection, for example via attributes. This documentation will focus on dependency injection
via the constructor only

Using dependency injection in Catel


Dependency injection via the ServiceLocator in Catel is enabled by default. This means that when a type is resolved from the container, it will

automatically use dependency injection to construct the type if it is not registered as instance.
It will first search for all available constructors on the type that will be instantiated. Then, for each constructor, starting with the one with the most
parameters, it will try to retrieve all values. If one fails, it will go to the next. If all fail, it will try to use the default constructor without parameters. If
that fails as well, then the type cannot be constructed and an exception will be thrown.
To get a better understanding of what happens, see the class below:

public class MyClass


{
private IFirstDependency _firstDependency;
private ISecondDependency _secondDependency;
public MyClass()
: this(null) { }
public MyClass(IFirstDependency firstDependency)
: this(firstDependency, null) { }
public MyClass(IFirstDependency firstDependency, ISecondDependency
secondDepdenceny)
{
_firstDependency = firstDependency;
_secondDependency = secondDependency;
}
}

When the MyClass will be retrieved from the ServiceLocator, this will happen:
1. Find constructor with most parameters (the one with both firstDependency and secondDependency). If both IFirstDependency and
ISecondDependency can be resolved from the ServiceLocator, the type will be constructed with the constructor. Otherwise it will proceed
with step 2.
2. Find next constructor with most parameters (the one with only firstDependency). If IFirstDependency can be resolved from the
ServiceLocator, the type will be constructed with the constructor. Otherwise it will proceed with step 3.
3. At this point, no constructor could be used. In this case, the ServiceLocator will try to use the default constructor (the one without
parameters) as last resort to instantiate the type.

Disabling dependency injection


Maybe you don't want dependency injection because it does not give you what you need or you want a very, very small improvement in
performance. In that case, the dependency injection can be disabled using the code below:

ServiceLocator.Default.SupportedDependencyInjection = false

Custom initialization
All types created with the TypeFactory can be initialized with custom code. This can be done by implementing the INeedCustomInitialization interf
ace. As soon as a type is created, the TypeFactory will check whether it implements the INeedCustomInitialization interface. If so, it will call the Ini
tialize method of the interface.
To prevent misuse of the Initialize method, it is best to implement the interface explicitly

Introduction to DependencyResolver and DependencyResolverManager


Why the need for a DependencyResolver
Managing the dependency resolvers per instance
Registering a dependency resolver for an instance
Retrieving a dependency resolver for an instance
Managing the dependency resolvers per type

Registering a dependency resolver for a type


Retrieving a dependency resolver for a type
Customizing the default DependencyResolver
Customizing the DependencyResolverManager
Managing different scoping of service locators and dependency injection can be hard. To aid developers with this, the IDependencyResolver and
DependencyResolverManager are introduced.

Why the need for a DependencyResolver


That's a good question. Catel already provides the IServiceLocator which allows to resolve types. The downside is that if you want to customize
the way dependencies are resolved in Catel, you will have to implement a custom version of the ServiceLocator. To make it simple to customize
this behavior, the DependencyResolver is introduced.
The main strategy will be to use the DependencyResolver instead of ServiceLocator to resolve the types in Catel, starting with version
3.8
Though in simple situations, Catel will resolve and inject all types automatically, there are a few exceptions to the rule. One of these exceptions
are extension methods. These are static classes which can be used to add functionality to an object. The downside is that you cannot use
dependency injection in static classes, and each object that is extended can have their own scoping of dependency resolvers. To solve this issue,
Catel introduces the DependencyResolverManager. This is a manager that keeps track of all types and objects and the DependencyResolver that
were used to create the object. This way it is still possible to retrieve additional dependencies in extensions methods in the same dependency
resolver the type was created with.
To illustrate this issue, take a look at the view model below:

// Set up a different scoping with a custom service locator


var serviceLocator = new ServiceLocator();
// ... register custom services here
var typeFactory = serviceLocator.ResolveType<ITypeFactory>();
var vm = typeFactory.CreateInstance<MyViewModel>();

In this example, a view model is created with a custom dependency scope. When writing an extension method for the view models, it is
impossible to get to this custom scope:

public static class MyViewModelExtensions


{
public static void DoSomething(this MyViewModel myViewModel)
{
// You can use ServiceLocator.Default here, but that is a *different and
wrong* scope
var additionalDependency =
ServiceLocator.Default.ResolveType<IAdditionalDependency>();
}
}

One option to solve this is to create a property on the view model called DependencyResolver or ServiceLocator. However, it is not the
responsibility of the view model to store this property. In fact, the view model does not know which scoping was used to create itself. The only way
to solve this is to inject the IServiceLocator into the view model, but that's not a good practice.
Below is a rewritten version of the extensions class which uses the DependencyResolverManager:

public static class MyViewModelExtensions


{
public static void DoSomething(this MyViewModel myViewModel)
{
// Get the *right* scope
var dependencyResolverManager = DependencyResolverManager.Default;
var dependencyResolver =
dependencyResolverManager.GetDependencyResolverForInstance(myViewModel);
var additionalDependency =
dependencyResolver.Resolve<IAdditionalDependency>();
}
}

Now you have the actual IDependencyResolver that was use to create the view model and can easily provide the right logic with the right scoping.
Note that there will only be a single instance of a DependencyResolverManager. It is possible to customize the default instance, but
there is no need for different scoping of DependencyResolverManager instances so it is valid to use the static instance

Managing the dependency resolvers per instance


The DependencyResolverManager can manage dependency resolvers per instance. This way it is possible to retrieve the actual dependency
resolver for a specific object instance.

Registering a dependency resolver for an instance


To register a dependency resolver for an instance, use this code:

var serviceLocator = new ServiceLocator();


var dependencyResolver = new CatelDependencyResolver(serviceLocator);
var myObject = new MySpecialObject();
var dependencyResolverManager = DependencyResolverManager.Default;
dependencyResolverManager.RegisterDependencyResolverForInstance(myObject,
dependencyResolver);

Note that it is not required to register a DependencyResolver for instances created with the TypeFactory. The TypeFactory automaticall
y registers the DependencyResolver used in the DependencyResolverManager.

Retrieving a dependency resolver for an instance


To retrieve the dependency resolver for a specific instance, use this code:

var dependencyResolverManager = DependencyResolverManager.Default;


var dependencyResolver =
dependencyResolverManager.GetDependencyResolverForInstance(myObject);

Below is a graph that shows how the dependency resolver of an instance is determined:

Managing the dependency resolvers per type


The DependencyResolverManager can manage dependency resolvers per type. This way it is possible to retrieve the actual dependency resolver
for a specific type.

Registering a dependency resolver for a type


To register a dependency resolver for a type, use this code:

var serviceLocator = new ServiceLocator();


var dependencyResolver = new CatelDependencyResolver(serviceLocator);
var dependencyResolverManager = DependencyResolverManager.Default;
dependencyResolverManager.RegisterDependencyResolverForType(typeof(MyClass),
dependencyResolver);

Note that these registrations are type-specific. You cannot register an interface and all classes deriving from that interface will return the
same DependencyResolver. All actual types must be registered separately.

Retrieving a dependency resolver for a type


To retrieve the dependency resolver for a specific instance, use this code:

var dependencyResolverManager = DependencyResolverManager.Default;


var dependencyResolver =
dependencyResolverManager.GetDependencyResolverForType(typeof(MyClass));

Customizing the default DependencyResolver


By default, the DependencyResolverManager creates a CatelDependencyResolver that wraps the ServiceLocator.Default instance. In simple
applications this is sufficient to get everything working. However sometimes it might be needed to customize the default DependencyResolver. To
change the default one, use the code below:

var dependencyResolverManager = DependencyResolverManager.Default;


dependencyResolverManager.DefaultDependencyResolver = new
MyCustomDependencyResolver();

Customizing the DependencyResolverManager


Customizing the DependencyResolverManager is not recommended. If you still want to do this for whatever reason, create a class implementing
the IDependencyResolverManager or derive from the DependencyResolverManager:

public class CustomizedDependencyResolverManager : DependencyResolverManager


{
public override IDependencyResolver GetDependencyResolverForType(Type type)
{
if (type == typeof(MySpecialClass))
{
return new MySpecialDependencyResolver();
}
return base.GetDependencyResolverForType(type);
}
}

Note that there is no use to override the DependencyResolverManager as the example, but this keeps it easy to understand

Then set the DependencyResolverManager.Default static property:

DependencyResolverManager.Default = new CustomizedDependencyResolverManager();

Ensuring integrity of the ServiceLocator


Starting with Catel 3.6, a very useful feature has been added to the ServiceLocator and TypeFactory. This features is called "integrity checker"
and will ensure you with useful information about type registration paths. This protection mechanism is very useful in complex applications. When
people start building services, sometimes they accidentally inject other services that via injection to other services cause a stack overflow.
Debugging and determining which type is causing the issue can be very time-consuming. To make the example a bit more simple, below are a
few classes which demonstrate a common issue in enterprises.

public class X
{
public X(Y y) { }
}
public class Y
{
public Y(Z z) { }
}
public class Z
{
public Z(X x) { }
}

Note how a round-trip of dependencies is created which will result in a StackOverflowException somewhere in your code. Below is a graphical
example what happens. Note that the dotted line is showing the circular dependency causing the StackOverflowException.

TypeRequestInfo
The first step for the integrity checker is to make sure that it knows what types are being requested from the ServiceLocator (which will be
instantiated by the TypeFactory if required). This class contains all the information about a type being created by the TypeFactory:
Type
Tag (optional, can be used to differentiate different instances of the same type registration)

TypeRequestPath
Now we have detailed information about the types being constructed, it is very important to keep track of the types which are being created by the
TypeFactory. During the construction of a type, the TypeFactory will request the ServiceLocator for a type, which will ask the TypeFactory to
construct the type again. Each time the TypeFactory starts constructing a type (and currently has a TypeRequestPath), it will create a new
instance of the TypeRequestInfo and add it to the TypeRequestPath. The diagram below shows how the TypeRequestPath will evolve.

Once the TypeRequestPath will contain a duplicate instance of a TypeRequestInfo, it will become invalid (which means there is a circular type
dependency).
Note that this is a very simple example, but normally a type will have several services injected which can have dependencies on their
own as well which can cause a very complex type request path

Checking the integrity of the type request


To resolve and construct a type, a lot of communication will happen between the TypeFactory and the ServiceLocator. This flow is show in the

diagram below.

As you can see, there is a lot of communication between the ServiceLocator and TypeFactory. In the TypeRequestPath example we already saw
how the path will become invalid when it contains a duplicate instance of the TypeRequestInfo. The TypeRequestPath will then throw a CircularD
ependencyException with all the necessary information to solve the issue:

Now you will find the issue in no-time and save yourself a lot of your valuable time!

Automatic type registration


This section contains all the information about automatic type registration.
Automatically registering types using attributes
Automatically registering types using conventions

Automatically registering types using attributes


The ServiceLocator in Catel can be set up to discover attribute based registration.

Declaring a registration since the type definition


There is a way to automatically register types into a service locator. Using ServiceLocatorRegistrationAttribute it is possible to register types into
the service locator in a declarative way. The following code shows how use this attribute:

[ServiceLocatorRegistration(typeof(IMyClass))]
public class MyClass : IMyClass
{
}

All registration options are available in attribute based registration, such as registration type and tag, as ServiceLocatorRegistrationAttribute const
ructor arguments. The following code shows how use such options (it registers the MyClass using the IMyClass interface in a transient way (new
type every time it is resolved) using the tag MyTag:

[ServiceLocatorRegistration(typeof(IMyClass), RegistrationType.Transient, "MyTag")]


public class MyClass : IMyClass
{
}

Activating service locator to scan for automatically registration


By default the service locator doesn't scan for automatic registration. In order to activate this you should set AutoRegisterTypesViaAttributes to tru
e.

var serviceLocator = ServiceLocator.Default;


serviceLocator.AutoRegisterTypesViaAttributes = true;

Automatically registering types using conventions


The ServiceLocator in Catel can be set up to automatically register types based on the conventions.
Register using Naming Convention
Register using FirstInterface Convention
Filter types to register
Exclude all types of the namespace containing the specified type
Exclude a specific type
Exclude types using predicate
The convention based registration should to be run first than the others registration methods to be sure to have all your types registered
correctly.
Some conventions are provided by default to allow us to register types.

Register using Naming Convention


You can want to register all types which match with the default naming convention, means when I have a IService interface, I expect the
convention to find and register the Service class as implementation.
To discover types for naming convention registration, we have to simply do :

var serviceLocator = new ServiceLocator();


serviceLocator.RegisterTypesUsingDefaultNamingConvention();

Register using FirstInterface Convention


You can want to register all types which match with the default first interface convention, means when I have a Service class which implements
more than one interface, I expect the convention to find the first interface and use it as service registration.

To discover types for first interface convention registration, we have to simply do :

var serviceLocator = new ServiceLocator();


serviceLocator.RegisterTypesUsingDefaultFirstInterfaceConvention();

Filter types to register


You have the ability to apply filtering on the registration process to exclude for example or include some types.

Exclude all types of the namespace containing the specified type


If you want to exclude all types of the namespace which belong to a particular type, just do that:

var serviceLocator = new ServiceLocator();


serviceLocator.RegisterTypesUsingDefaultNamingConvention()
.ExcludeAllTypesOfNamespaceContaining<IFooService>();

Here, we say to the ServiceLocator to ignore all types included into the namespace which belong to the IFooService type.
You can manually specify the namespace of the types to exclude using the ExcludeAllTypesOfNamespace method like this: ExcludeAll
TypesOfNamespace("MyNamespace")

Exclude a specific type


If you want to exclude a specific type, you can do that by using the ExcludeType method like shown below:

var serviceLocator = new ServiceLocator();


serviceLocator.RegisterTypesUsingDefaultNamingConvention()
.ExcludeType<IFooService>();

The IFooService will be exclude on the registration process.

Exclude types using predicate


You also have the possibility to filter types by using a predicate, below an example :

var serviceLocator = new ServiceLocator();


serviceLocator.RegisterTypesUsingDefaultNamingConvention()
.ExcludeTypesWhere(type => type == typeof(IFooService));

All Exclude methods have an Include version

Setting up the ServiceLocator using configuration


The ServiceLocator in Catel can be set up from configuration file.

Importing IoC configuration section


Configuring a service locator from the default configuration
Configuring a service locator from a named configuration

Importing IoC configuration section


The first step to setup the service locator from the configuration file is import the custom section type Catel.IoC.IoCConfigurationSection from Cat
el.Core. The following example shows how to import this configuration section and make it available for the configuration file as ioc:

<configuration>
<configSections>
<sectionGroup name="catel">
<section name="ioc" type="Catel.IoC.IoCConfigurationSection, Catel.Core" />
</sectionGroup>
</configSections>
...
</configuration>

In the example above we also create a section group named catel to group all Catel related configuration sections.

Configuring a service locator from the default configuration


It's possible add more than one service locator configuration to the configuration file but you must specify an unique name. If a name of a service
locator configuration is not specified then the name default is assigned. By default such configuration supports dependency injection.

<configuration>
<configSections>
<sectionGroup name="catel">
<section name="ioc" type="Catel.IoC.IoCConfigurationSection, Catel.Core" />
</sectionGroup>
</configSections>
<catel>
<ioc>
<serviceLocatorConfigurations>
<serviceLocatorConfiguration [name="default"]>
<register interfaceType="Catel.MVVM.Services.IUIVisualizerService"
implementationType="Catel.MVVM.Services.UIVisualizerService" />
<register interfaceType="Catel.MVVM.Services.IProcessService"
implementationType="Catel.MVVM.Services.ProcessService" />
</serviceLocatorConfiguration>
</serviceLocatorConfigurations>
</ioc>
</catel>
</configuration>

To configure a service locator from the default service locator configuration use the following code:

var serviceLocator = ServiceLocator.Default;


Configuration configuration =
ConfigurationManager.OpenExeConfiguration(ConfigurationUserLevel.None);
var ioc = configuration.GetSection<IoCConfigurationSection>("ioc", "catel");
ioc.DefaultServiceLocatorConfiguration.Configure(serviceLocator);

Configuring a service locator from a named configuration


The following configuration file is a full example on how write more than one service locator configuration:

<configuration>
<configSections>
<sectionGroup name="catel">
<section name="ioc" type="Catel.IoC.IoCConfigurationSection, Catel.Core" />
</sectionGroup>
</configSections>
<catel>
<ioc>
<serviceLocatorConfigurations>
<serviceLocatorConfiguration>
<register interfaceType="Catel.MVVM.Services.IUIVisualizerService"
implementationType="Catel.MVVM.Services.UIVisualizerService" />
<register interfaceType="Catel.MVVM.Services.IProcessService"
implementationType="Catel.MVVM.Services.ProcessService" />
</serviceLocatorConfiguration>
<serviceLocatorConfiguration name="test"
supportDependencyInjection="false">
<register interfaceType="Catel.MVVM.Services.IUIVisualizerService"
implementationType="Catel.MVVM.Services.Test.UIVisualizerService"
registrationType="Transient"/>
<register interfaceType="Catel.MVVM.Services.IProcessService"
implementationType="Catel.MVVM.Services.Test.ProcessService" tag="test"/>
</serviceLocatorConfiguration>
</serviceLocatorConfigurations>
</ioc>
</catel>
</configuration>

To configure a service locator from a named configuration use the following code:
var serviceLocator = ServiceLocator.Default;
Configuration configuration =
ConfigurationManager.OpenExeConfiguration(ConfigurationUserLevel.None);
var ioc = configuration.GetSection<IoCConfigurationSection>("ioc", "catel");
ioc.GetServiceLocatorConfiguration("test").Configure(serviceLocator);

You should also note the options setup if the container in order to support dependency injection and the

registration type (a.k.a instantiation style) and the tag for each registration.
Replacing the default components
By default, Catel provides very fast and functional implementations of the component interfaces. It is possible though that one needs to use a
different container than the specified ones.
Replacing default components
Creating IoC components in code
Note that when any component is replaced, it must be registered with the other instances that are already running. Catel cannot do this
automatically because it is not aware how other (customized) components interact or require registration.

Replacing default components


Starting with Catel 3.9, it is very easy to customize the components. This can be achieved by customizing the factory methods that are available
on the IoCConfiguration class.
Note that the customization of the IoCConfiguration is the first thing that must be done at application start up

To replace any component, first create a custom implementation of the specific component, for example the IServiceLocator. Then update the
factory and call UpdateDefaultComponents:

Catel.IoC.IoCFactory.CreateServiceLocatorFunc = () => new MyCustomServiceLocator();


Catel.IoC.IoCFactory.CreateTypeFactoryFunc = () => new MyCustomTypeFactory();
Catel.IoC.IoCConfiguration.UpdateDefaultComponents();

At this moment, Catel will fully replace the components (in this case the IServiceLocator and ITypeFactory), but will keep using the default
implementation of the IDependencyResolver.

Creating IoC components in code


It is best to respect the customization of the IoC components in the code. Therefore it is wise to always use the IoCFactory to create a ServiceLoc
ator when a new instance is needed:

var serviceLocator = IoCFactory.CreateServiceLocator();

Catel will automatically create the right IDependencyResolver and ITypeFactory and register them in the newly created IServiceLocator.

Logging
Starting with version 2.2, Catel uses a custom internal logging system. This way, the reference to log4net could be removed. The idea behind this
move is not to force the user to use log4net. Also, log4net seems deprecated (no new releases for a long time), and other logging systems such
as NLog seem to grow in popularity.
The new logging system only allows very basic logging. This way, the logging is kept very simple and the real logging can be implemented by the
end-developer if he/she feels the need for it.
Table of contents
Log and ILog
LogManager
Logging in code
Logging in code with additional data
Logging to the output window or console
Overriding global log level flags
Other info
Log listeners

Customizing listeners
Creating log listeners via configuration
Integration with external loggers
Anotar.Catel.Fody

Log and ILog


All logging is available via the ILog interface. This interface is registered automatically on all objects in Catel as Log field. This way, every object
can log any information by calling methods on the Log field.
In Catel, there is only one implementation of the ILog interface, which is the Log class. This class makes sure that the log messages are formatted
correctly and the LogMessage event is invoked when a message is written to the log.
Catel internally creates a separate log per type. This way, there will be lots of logs and it should be easy to filter the information the end-developer
is really interested in.

LogManager
The LogManager is the class where it all comes together. This class is responsible for creating new logs for types, but also keeps track of all logs
and log listeners. To retrieve the log for a specific class, use the following code:

private static readonly ILog Log = LogManager.GetCurrentClassLogger();

Logging in code
To log in code, the ILog interface implements some basic methods to log information with an option for extra data. There are however lots of
extension methods available to log exceptions, string formats and more. Below is an example of logging in code:

Log.Warning("Customer '{0}' does not exist", customerId);

Or, if an exception is available, this can written to the log as well.

Log.Error(ex, "Failed to delete file '{0}'", fileName);

Logging in code with additional data


Sometimes additional data is required (for example, the thread id, or anything else like this). The logging is extensible and contains on the the
bare minimum required for logging. To pass in additional information, use the [Level]WithData methods (such as DebugWithData):

Log.Debug("This is a message from a specific thread", new LogData


{
{ "ThreadId", threadId }
});

Then the log data will be available in the LogData of the LogEntry:

var logData = logEntry.LogData;


var threadId = logData["ThreadId"];

Logging to the output window or console


By default, Catel does not add any listeners. However, it contains a ready-to-use implementation that writes all logs to the output window or
console, which is the DebugLogListener. To register this listener, call this at any time:

#if DEBUG
LogManager.AddDebugListener();
#endif

Prior to Catel 3.8, one should use LogManager.RegisterDebugListener() instead

Overriding global log level flags


Start with Catel 3.8, it is possible to override the global log level flags for all listeners. To do this, set the corresponding flag on the LogManager to
a value. For example, to force debug logging on all log listeners, use the code below:

LogManager.IsDebugEnabled = true;

To reset the override, set the value back to null:

LogManager.IsDebugEnabled = null;

Log listeners
Catel provides several log listeners out of the box.
Batch log listeners
ConsoleLogListener
DebugLogListener
EventLogListener
Event Tracing for Windows (ETW)
FileLogListener
RollingInMemoryLogListener
SeqLogListener

Batch log listeners


Flushing all listeners
Implementing a custom IBatchLogListener
A batch log listener is a class implementing the IBatchLogListener interface (and most probably deriving from BatchLogListenerBase). This
interface adds a Flush method which allows a listener to be flushed. The advantage is that when a log listener writes to a slower persistence
store, it will not have to access this expensive resource for every log event, but by batches.

Flushing all listeners


When using batch log listeners, it is very important to flush the log listeners at important events such as application unhandled exceptions or when
the application exits. The reason is that otherwise important log events that are currently in the batch that hasn't been written to the persistence
store are lost.
To flush all flushable listeners, use the following method:

LogManager.FlushAll();

Implementing a custom IBatchLogListener


When implementing a custom batch log listener, it is very wise to derive from the BatchLogListenerBase class. This brings the following
advantages:
1. The BatchLogListenerBase is thread-safe
2. The BatchLogListenerBase automatically flushes the listener every 5 seconds
3. You only need to implement the WriteBatch which actually writes the entries to the persistence store
Below is an example batch log listener:

public class FileLogListener : BatchLogListenerBase


{
private readonly string _filePath;
private readonly int _maxSizeInKiloBytes;
public FileLogListener(string filePath, int maxSizeInKiloBytes)
{
Argument.IsNotNullOrWhitespace(() => filePath);
_filePath = filePath;
_maxSizeInKiloBytes = maxSizeInKiloBytes;
}
protected override void WriteBatch(System.Collections.Generic.List<LogBatchEntry>
batchEntries)
{
try
{
var fileInfo = new FileInfo(_filePath);
if (fileInfo.Exists && (fileInfo.Length / 1024 >= _maxSizeInKiloBytes))
{
CreateCopyOfCurrentLogFile(_filePath);
}
using (var fileStream = new FileStream(_filePath, FileMode.Append,
FileAccess.Write, FileShare.Read))
{
using (var writer = new StreamWriter(fileStream))
{
foreach (var batchEntry in batchEntries)
{
var message = FormatLogEvent(batchEntry.Log, batchEntry.Message,
batchEntry.LogEvent, batchEntry.ExtraData);
writer.WriteLine(message);
}
}
}
}
catch (Exception)
{
// Swallow
}
}
private void CreateCopyOfCurrentLogFile(string filePath)
{
for (int i = 1; i < 999; i++)
{
var possibleFilePath = string.Format("{0}.{1:000}", filePath, i);
if (!File.Exists(possibleFilePath))
{
File.Move(filePath, possibleFilePath);
}
}
}
}

ConsoleLogListener
The ConsoleLogListener writes messages to the console with automatic colors:

To add it, use the code below:

var logListener = new ConsoleLogListener();


logListener.IgnoreCatelLogging = true;
// TODO: Customize options
LogManager.AddListener(logListener);

DebugLogListener
The DebugLogListener is the best debugging tool there is during development. It shows you insight in your application in the output window of
Visual Studio, even from messages generated by Catel. To use it, use this:

#if DEBUG
LogManager.AddDebugListener();
#endif

EventLogListener
The EventLogListener allow to write log data to the system event log.

To add it, use the code below:

var logListener = new EventLogListener();


logListener.IgnoreCatelLogging = true;
// TODO: Customize options
LogManager.AddListener(logListener);

This log listener is currently available only for .NET 4.0 and .NET 4.5

Event Tracing for Windows (ETW)


Starting with version 4.0.0, Catel supports Event Tracking for Windows (ETW) out of the box. To add a log listener, use the code below:

var logListener = new EtwLogListener();


logListener.IgnoreCatelLogging = true;
// TODO: Customize options
LogManager.AddListener(logListener);

FileLogListener
Specifying the path
Creating a custom listener
Registering the listener
Catel also supports very lightweight listeners to allow external logging libraries to hook on. To create a listener, first create a new class that
implements the ILogListener interface. Next, register it in the LogManager using the LogManager.AddListener method.
The ILogListener has a separate method for each LogEvent, but also has a shared method that is called for each log event. For example, if a
debug message is written to the log, both the Write and Debug methods are invoked on the ILogListener.
For an example which writes to disk in batches, see the batch log event listeners

Note that Catel already contains a FileLogListener and there is no need to reproduce this class. It only acts as an example that is easy
to understand

Specifying the path


The default FileLogListener that ships with Catel allows the customization of the file name and the size of the log file. If no size is specified, the
max log file size will default to 10 MB.
There are several constants inside the file name that can be used:
Constant

Description

{AppData}

The application data directory based on the entry assembly. For example %AppData%\[company]\[product]\

{AppDir}

The directory of the current application (AppDomain.CurrentDomain.BaseDirectory)

{Date}

The date as yyyy-MM-dd

{Time}

The time as HHmmss

{ProcessId}

The process id

{AssemblyName}

The assembly name

{AutoLogFileName}

Creates a log file with the following format: {AssemblyName}_{Date}_{Time}_{ProcessId}

A good example would be:

var fileLogListener = new FileLogListener();


fileLogListener.FilePath = "{AppDir}\{AutoLogFileName}";
LogManager.AddListener(fileLogListener);

Note that the default path of the FileLogListener is {AppData}\{AutoLogFileName}

Creating a custom listener


A listener can be created by creating a new class deriving from LogListenerBase.

public class FileLogListener : LogListenerBase


{
private readonly TextWriter _textWriter;
public FileLogListener(string fileName)
{
Argument.IsNotNullOrWhitespace("fileName", fileName);
FileName = fileName;
_textWriter = new StreamWriter(fileName, true);
}
public string FileName { get; private set; }
public override void Write(ILog log, string message, LogEvent logEvent)
{
_textWriter.WriteLine(message);
}
}

Registering the listener


Last but not least, it is important to register the listener:

LogManager.AddListener(new FileLogListener("<log_file_path>"));

RollingInMemoryLogListener
Enabling the feature
Querying log messages
Customizing number of items to keep in memory

In memory logging can be very useful to be able to query the latest log messages. Catel provides this via the RollingInMemoryLogListener and Ro
llingInMemoryLogService. The RollingInMemoryLogService is a wrapper around the RollingInMemoryLogListener to provide a simple way to use
the listener.

Enabling the feature


By default, the feature is disabled to not eat any CPU ticks when not being used. To use the feature, the only thing required is to resolve the type
from the ServiceLocator:

var rollingInMemoryLogService =
ServiceLocator.Default.ResolveType<IRollingInMemoryLogService>();

Querying log messages


To query the latest log messages, use one of the following methods:
GetLogEntries
GetWarningLogEntries
GetErrorLogEntries

Customizing number of items to keep in memory


To customize the number of items being kept in memory, use one of the following properties:
MaximumNumberOfLogEntries
MaximumNumberOfWarningLogEntries
MaximumNumberOfErrorLogEntries

SeqLogListener
Seq is a structured logs server for .NET Apps. It act like a logs repository, allow to diagnostic by query your logs using a natural syntax, react on
notifying you through email or instant messages and so on ...

To use the Seq log listener, use the following code:

var logListener = new SeqLogListener();


logListener.IgnoreCatelLogging = true;
// TODO: Customize options
LogManager.AddListener(logListener);

This one can also be used on configuration file:

<catel>
<logging>
<listeners>
<listener type="Catel.Logging.SeqLogListener"
ServerUrl="http://localhost:5341" IgnoreCatelLogging="true" IsDebugEnabled="false"
IsInfoEnabled="true" IsWarningEnabled="true" IsErrorEnabled="true" />
</listeners>
</logging>
</catel>

This log listener is currently available only for .NET 4.0 and .NET 4.5

Customizing listeners
Each listener can be customized to only receive the logs that the listener is interested in. This way, the listener does not receive events it is not
interested in. For example, to only receive errors, create a new listener and use the following customization:

var listener = new MyLogListener();


listener.IsDebugEnabled = false;
listener.IsInfoEnabled = false;
listener.IsWarningEnabled = false;
listener.IsErrorEnabled = true;

By default, all types of logging are enabled on a log listener.

Creating log listeners via configuration


Starting with Catel 3.8, it is possible to instantiate LogListener classes from the configuration. Below is an example on how to customize the
listeners:

<configSections>
<sectionGroup name="catel">
<section name="logging" type="Catel.Logging.LoggingConfigurationSection, Catel.Core"
/>
</sectionGroup>
</configSections>
<catel>
<logging>
<listeners>
<listener type="Catel.Logging.FileLogListener"
FilePath="{AppData}\CatelLogging.txt" IgnoreCatelLogging="true"
IsDebugEnabled="false" IsInfoEnabled="true" IsWarningEnabled="true"
IsErrorEnabled="true"/>
</listeners>
</logging>
</catel>

It is important to register the logging section as shown in the example above. Then the logging section in the bottom can contain an unlimited
number of listeners. Each listener has to provide at least the type property which contains the type and namespace of the ILogListener which
must be added:

<listener type="Catel.Logging.FileLogListener" />

The other properties are fully customizable and can be defined on the fly. This means that the configuration is fully customizable for every listener
that needs to be added. Below is an example to register the FileLogListener via configuration:

<listener type="Catel.Logging.FileLogListener" FilePath="CatelLogging.txt"


IgnoreCatelLogging="true"
IsDebugEnabled="false" IsInfoEnabled="true" IsWarningEnabled="true"
IsErrorEnabled="true"/>

The ILogListener properties (IsDebugEnabled, IsInfoEnabled, IsWarningEnabled and IsErrorEnabled) are available to all listeners. All other
properties depend on the the actual listener being registered. This allows major flexibility at runtime.

Integration with external loggers


The logging in Catel does not write any output by default. This gives a developer freedom to use any final logging mechanism in the way he or
she intended. For example, Catel can easily be integrated with log4net or NLog. Basically, the following steps are required to implement an
external log solution:
1. Create a custom ILogListener by creating your own or using the LogListenerBase implementation
2. Register it in the LogManager using the LogManager.AddListener
Log4net
NLog

Log4net
The example below provides an ILogListener for NLog, but any external logging library can be used.

Creating the listener


A listener can be created by creating a new class deriving from LogListenerBase.

public class Log4netListener : LogListenerBase


{
protected override void Debug(ILog log, string message, object extraData)
{
var finalLog = log4net.LogManager.GetLogger(log.TargetType);
finalLog.Debug(message);
}
protected override void Info(ILog log, string message, object extraData)
{
var finalLog = log4net.LogManager.GetLogger(log.TargetType);
finalLog.Info(message);
}
protected override void Warning(ILog log, string message, object extraData)
{
var finalLog = log4net.LogManager.GetLogger(log.TargetType);
finalLog.Warn(message);
}
protected override void Error(ILog log, string message, object extraData)
{
var finalLog = log4net.LogManager.GetLogger(log.TargetType);
finalLog.Error(message);
}
}

Registering the listener


Last but not least, it is important to register the listener:

LogManager.AddListener(new Log4netListener());

Configuring log4net
Note that this is just a sample configuration. Please use the log4net documentation for all options

1. Add reference to log4net


2. Add [assembly: log4net.Config.XmlConfigurator(Watch = true)] to AssemblyInfo.cs
3. Configure log4net in your app.config to configure the actual data

NLog
The example below provides an ILogListener for NLog, but any external logging library can be used.

Creating the listener


A listener can be created by creating a new class deriving from LogListenerBase.

public class NLogListener : LogListenerBase


{
protected override void Debug(ILog log, string message, object extraData)
{
var finalLog = NLog.LogManager.GetLogger(log.TargetType.ToString());
finalLog.Debug(message);
}
protected override void Info(ILog log, string message, object extraData)
{
var finalLog = NLog.LogManager.GetLogger(log.TargetType.ToString());
finalLog.Info(message);
}
protected override void Warning(ILog log, string message, object extraData)
{
var finalLog = NLog.LogManager.GetLogger(log.TargetType.ToString());
finalLog.Warn(message);
}
protected override void Error(ILog log, string message, object extraData)
{
var finalLog = NLog.LogManager.GetLogger(log.TargetType.ToString());
finalLog.Error(message);
}
}

Registering the listener


Last but not least, it is important to register the listener:

LogManager.AddListener(new NLogListener());

Anotar.Catel.Fody
Logging is a very important part of an application. It provides detailed information about the application workflow, even when an application is
already deployed to several clients. Thats the reason that logging is a first class citizen in the Catel framework.
In general, logging works by defining an ILog instance on a class:

private static readonly ILog Log = LogManager.GetCurrentClassLogger();

Then in any method, logging can be added like this:

Log.Info(This is a logging with a format {0}, test);

Writing the Log definition can be boring and repetitive. Luckily Simon Cropp came up with a solution for that, namely Anotar.Catel.Fody. With the
Anotar implementation, a reference will be added to the solution. Then after compilation the assembly will be removed and all calls to the LogTo cl
ass will be replaced by actual calls to the Catel logging classes.

How to use Anotar

Using Anotar is really easy, just call the static methods on the LogTo class as you can see below:

LogTo.Info("This is a logging with a format {0}", test);

Note that it is no longer required to define the Log field, it will be added automatically by Anotar.
Besides that it is really easy to use, another benefit is a very small performance improvement. The GetCurrentClassLogger uses reflection to
determine the current class. This is a very slight hit on performance the first time a class is used (only once, the field is static). Anotar directly
replaces the call by an implementation like this:

private static readonly ILog Log = LogManager.GetLogger(typeof(MyClass));

Additional options
Disabling method names and line numbers
By default Anotar also logs the method and line number:

03:58:11:858 => [DEBUG] [AnotarDemo.Program] Method: 'Void Main(String[])'. Line: ~19.


this is a test

If you don't want such output, add this attribute on assembly level:

[assembly: LogMinimalMessage]

Then the output will look like this:

03:59:36:344 => [DEBUG] [AnotarDemo1.Program] this is a test

Logging exceptions automatically


It is possible to automatically log exceptions inside a method. To accomplish this, decorate the method with the LogTo[LogLevel]OnException attri
bute:

[LogToDebugOnException]
public static void ExceptionalMethod()
{
throw new Exception("This will be logged automatically");
}

Then the output will be as follows:

04:01:48:331 => [DEBUG] [AnotarDemo.Program] Exception occurred in 'Void


ExceptionalMethod()'. | [Exception] System.Exception: This will be logged
automatically
at AnotarDemo.Program.ExceptionalMethod() in
c:\Source\AnotarDemo\AnotarDemo\Program.cs:line 27

Messaging
MessageBase
Message mediator
Messaging via attributes

MessageBase
The MessageMediator is a very powerful class to send messages to other objects inside an application. However, it can sometimes by
cumbersome to register and create messages. Therefore the MessageBase class is a very nice convenience class to create messages and allow
easier registration.
The MessageBase provides the following additional functionality out of the box:
Send messages with data without instantiating a message
Register message handlers
Unregister message handlers

Creating messages based on the MessageBase


It is very easy to create a new message. The message below is a message that contains a string and this little class provides lots of capabilities.

public class DemoMessage : MessageBase<DemoMessage, string>


{
public DemoMessage() { }
public DemoMessage(string content)
: base(content) { }
}

Note that the message needs an empty constructor

Sending messages
A user can send a message by using the following code:

DemoMessage.SendWith("hello world");

Registering to messages
A class that is interested in message can register to a message using the Register method:

DemoMessage.Register(this, OnDemoMessage);

Unregistering from messages


DemoMessage.Unregister(this, OnDemoMessage);

Instantiating a message with data


The MessageBase class can also instantiate messages by using the With method:

var message = DemoMessage.With("hello world");

Message mediator
Catel allows sending messages to unknown targets by implementing the mediator pattern. The mediator is assured memory leak free, and can be
used safely in any .NET environment (even ASP.NET). Below are a few usage examples of the MessageMediator class.

Registering to a message
To register a handler for a specific message type, in this case a string, use the following code:

var mediator = ServiceLocator.Default.ResolveType<IMessageMediator>();


mediator.Register<string>(this, OnMessage);

Sending out a message


To send a message to all recipients, use the following code:

var mediator = ServiceLocator.Default.ResolveType<IMessageMediator>();


mediator.SendMessage<string>("message");

Sending out a message with a tag


Sometimes, you want to send messages only based on a tag. For example, you want to let other view models know that you just added a person.
All recipients that registered to the string message type with the Person tag will receive the message:

var mediator = ServiceLocator.Default.ResolveType<IMessageMediator>();


mediator.SendMessage<string>("Person added", "Person");

Messaging via attributes


The message mediator is a great way to communicate between instances in an application. It does however require to manually subscribe to and
unsubscribe from classes. This issue can be bypassed using the attribute based approach. This is an alternative for registering a method in the
message mediator and not be obliged to use Register<T> method.

Subscribing and unsubscribing


When attributes are using inside a class, it is required to call the MessageMediatorHelper.SubscripeRecipient. To unsubscribe an object, it is
required to call MessageMediatorHelper.UnsubscribeRecipient.
Note that the ViewModelBase class already handles the subscriptions using attributes out of the box

There are two options to decorate methods with the attribute. Either with or without tag.

Subscribing without a tag


In this case, the mediator will send the message to all the methods that has subscribe using the attribute to receive the message and not one
especially. The code below broadcasts a message without any tag. This is just regular behavior of the message mediator.

/// <summary>
/// Method to invoke when the command is executed.
/// </summary>
private void OnCmdExecute()
{
var dependencyResolver = this.GetDependencyResolver();
var mediator = dependencyResolver.Resolve<IMessageMediator>();
mediator.SendMessage("Test Value");
}

If a class, for example a view model, is interested in these messages, the only thing that needs to be done is to decorate a method with the
MessageRecipient attribute as shown below:

/// <summary>
/// Shows the message.
/// </summary>
/// <param name="value">The value.</param>
[MessageRecipient]
private void ShowMessage(string value)
{
var dependencyResolver = this.GetDependencyResolver();
var messageService = dependencyResolver.Resolve<IMessageService>();
messageService.Show(value);
}

Subscribing with a tag


A tag can be used to specify some sort of grouping for messages. The MessageRecipient attribute also supports this as shown in the code
below. First lets take a look how to send a message and specify a tag.

/// <summary>
/// Method to invoke when the command is executed.
/// </summary>
private void OnCmdExecute()
{
var dependencyResolver = this.GetDependencyResolver();
var mediator = dependencyResolver.Resolve<IMessageMediator>();
mediator.SendMessage("Test Value", "myTag");
}

The message is now sent with the tag. The attribute has to be used as shown below:

/// <summary>
/// Shows the message.
/// </summary>
/// <param name="value">The value.</param>
[MessageRecipient(Tag = "myTag")]
private void ShowMessage(string value)
{
var dependencyResolver = this.GetDependencyResolver();
var messageService = dependencyResolver.Resolve<IMessageService>();
messageService.Show(value);
}

Multilingual
Making an application multilingual is a very common feature request nowadays. Therefore Catel provides the resources in several languages and
provides the LanguageService to give the developers full control over the translation process in their applications.
Setting up the LanguageService
Setting cultures
Registering custom language sources
Using the LanguageService
Using the LanguageService in XAML
Using the LanguageBinding in WPF and Silverlight
Using the LanguageBinding in Windows Phone
Implementing custom LanguageService (from database)
Creating a custom ILanguageSource implementation
Creating a custom DbLanguageService
Enabling the custom DbLanguageService

Setting up the LanguageService


Setting cultures
By default the LanguageService will use the current UI culture to retrieve the right language values. These can easily be customized:

var dependencyResolver = this.GetDependencyResolver();


var languageService = dependencyResolver.Resolve<ILanguageService>();
languageService.PreferredCulture = new CultureInfo("nl-NL");
languageService.FallbackCulture = new CultureInfo("en-US");

Registering custom language sources


In order to customize the language sources, custom language sources can be registered via the RegisterLanguageSource method.
The code below shows how to add a new LanguageResourceSource which represents a resource file in a specific assembly:

var dependencyResolver = this.GetDependencyResolver();


var languageService = dependencyResolver.Resolve<ILanguageService>();
// Create source for assembly MyApplication where the Resources.resx is located in the
Properties folder
var resourcesSource = new LanguageResourceSource("MyApplication",
"MyApplication.Properties", "Resources");
languageService.RegisterLanguageSource(resourcesSource );
// Create source for assembly MyApplication where the Exceptions.resx is located in
the Properties folder
var exceptionsSource = new LanguageResourceSource("MyApplication",
"MyApplication.Properties", "Exceptions");
languageService.RegisterLanguageSource(exceptionsSource );

The LanguageService will now automatically query these sources for the translations.

Using the LanguageService


To use the LanguageService, retrieve it via the DependencyResolver (or let it be injected) and use the provided methods. The example below
retrieves the WarningTitle resource string in the PreferredCulture. If the resource cannot be found in the PreferredCulture, it will be retrieved for
the FallbackCulture. If that cannot be found, it will return null.

var dependencyResolver = this.GetDependencyResolver();


var languageService = dependencyResolver.Resolve<ILanguageService>();
var warningTitle = languageService.GetString("WarningTitle");

Using the LanguageService in XAML


To use the LanguageService in XAML, Catel provides the markup extensions.

Using the LanguageBinding in WPF and Silverlight


To use the LanguageBinding markup extension in WPF and Silverlight, use the following code:

<TextBlock Text="{LanguageBinding WarningTitle}" />

Using the LanguageBinding in Windows Phone


Since Windows Phone does not support markup extensions, a custom MarkupExtension implementation is used in Catel. This requires a little
difference in the usage of the markup extension:

<TextBlock Text="{markup:LanguageBinding ResourceName=WarningTitle}" />

Implementing custom LanguageService (from database)


Implementing a custom LanguageService consists of several steps which are described below.

Note that this implementation queries the database for each translation. It is best to read all translations into memory at once to improve
performance

Creating a custom ILanguageSource implementation


First of all, we need to implement a customized language source to allow the custom service to know what source to read for translations:

public class DbLanguageSource : ILanguageSource


{
public DbLanguageSource(string connectionString)
{
Argument.IsNotNullOrWhitespace(() => connectionString);
ConnectionString = connectionString;
}
public string ConnectionString { get; private set; }
public string GetSource()
{
return ConnectionString;
}
}

Creating a custom DbLanguageService


Below is a custom implementation of the LanguageService. Note that we only have to derive a single method to fully customize the
implementation:

public class DbLanguageService : LanguageService


{
protected override string GetString(ILanguageSource languageSource, string
resourceName, CultureInfo cultureInfo)
{
var connectionString = languageSource.GetSource();
using (var dbConnection = new SqlConnection(connectionString))
{
dbConnection.Open();
var sqlCommand = dbConnection.CreateCommand();
sqlCommand.CommandType = CommandType.Text;
sqlCommand.CommandText = @"SELECT [Name] FROM [Translations] WHERE
[ResourceName] = @ResourceName AND [CultureName] = @CultureName";
sqlCommand.Parameters.Add(new SqlParameter("ResourceName", resourceName));
sqlCommand.Parameters.Add(new SqlParameter("CultureName",
cultureInfo.ThreeLetterISOLanguageName));
var translation = sqlCommand.ExecuteScalar() as string;
if (!string.IsNullOrWhiteSpace(translation))
{
return translation;
}
}
// Resource not found, fall back to base if you like, or simply return null
return base.GetString(languageSource, resourceName, cultureInfo);
}
}

Enabling the custom DbLanguageService


To enable the custom DbLanguageService, it must be registered in the ServiceLocator:

var serviceLocator = ServiceLocator.Default;


var dbLanguageService = new DbLanguageService();
var dbLanguageSource = new DbLanguageSource("myConnectionString");
dbLanguageService.RegisterLanguageSource(dbLanguageSource);
serviceLocator.RegisterInstance<ILanguageService>(dbLanguageService);

Parallel invocation and tasks


This page contains helper classes in Catel to invoke specific actions on very large collections in parallel.
Running batches on large sets in parallel

Running batches on large sets in parallel


When handling a lot of items and invoking a method per item, it might be a viable option to execute the actions in batches. This normally requires
quite some code to split up the large collection into batches and execute the method for each item. To make this process much easier, Catel
introduces the ParallelHelper class.

To invoke an Initialize method on all types currently loaded by Catel, in batches of 2500 types per batch, use the following code:

var allTypes = new List<Type>(TypeCache.GetTypes());


ParallelHelper.ExecuteInParallel(allTypes, type =>
{
SomeInitializeTypeMethod(type);
}, 2500, "Initialize types");

It is really easy to tweak the number of items per batch to find the optimal performance of items per batch.

Preventing memory leaks


Memory leaks are a very stubborn issue inside the .NET world. Every subscription to events can result in a memory leak if not unsubscribed
correctly. Catel provides several helper classes to prevent memory leaks in applications.
Change notification wrapper
Weak events

Change notification wrapper


Subscribing to change notifications of objects mostly results in large statements such as the one below:

var itemAsPropertyChanged = obj as INotifyPropertyChanged;


if (itemAsPropertyChanged != null)
{
itemAsPropertyChanged.PropertyChanged += OnPropertyChanged;
}

However, using this code one must be aware that if not unsubscribed, there might be a potential memory leak here. In Catel, there is a solution for
such cases that can raise change notifications using weak events called the ChangeNotificationWrapper. It allows the subscription of both the
INotifyPropertyChanged and INotifyCollectionChanged interfaces.

Subscribing to events of an observable object


Using the code below, one can subscribe to the PropertyChanged event of an object:

var wrapper = new ChangeNotificationWrapper(obj);


wrapper.PropertyChanged += OnPropertyChanged;

Note that it is not required to check whether the object implements INotifyPropertyChanged, the wrapper does it automatically

Subscribing to events of an observable collection


Using the code below, one can subscribe to the CollectionChanged event of an object:

var wrapper = new ChangeNotificationWrapper(observableCollection);


wrapper.CollectionChanged += OnCollectionChanged;

Note that it is not required to check whether the object implements INotifyCollectionChanged, the wrapper does it automatically

Advanced scenario with observable collections


Sometimes it is required to watch both changes inside a collection, but also the items inside a collection. For example, there is a list of customers
and you are also interested in changes of customers inside a collection. This is fully supported by the ChangeNotificationWrapper using the code
below:

var wrapper = new ChangeNotificationWrapper(observableCustomerCollection);


wrapper.CollectionChanged += OnCollectionChanged;
wrapper.CollectionItemPropertyChanged += OnCollectionItemPropertyChanged;

All subscriptions are automatically managed by the ChangeNotificationWrapper when items are added or removed from the collection.

Unsubscribing from events


When you are no longer interested in events from the source object, there are two options:
1. Just leave them coming, as soon as the objects are no longer used, they will be garbage collected
2. Unsubscribe using the following code:

wrapper.UnsubscribeFromAllEvents();

Weak events
Open instance delegates
Weak references
What does it support
What does it not support and what are the downsides
How to use
Instance to instance
Instance to static
Static to instance
Static to static
You have probably heard about weak events before. This documentation is not about the issue of the cause of weak events, there are lots of
articles about that. This documentation writes about the solution, which is the WeakEventListener. Shortly said, when you do this in every class
(just for the sake of explaining the problem, dont start thinking this code has no business value):

var log = Log.Instance;


log.LogReceived += OnLogReceived;

As you can see, the log is a singleton, so there is only one living instance of the Log class. It will probably live as long as the app itself. Now you
might be thinking: whats wrong with this code? Nothing, until the app starts growing and growing and your users start complaining about memory
issues.
What happens here is that you subscribe to the LogReceived event of the Log class. This subscription contains 2 things:
1. What class do I need to call (null for static, otherwise the instance of the class)
2. What method do I need to call
So, in fact now the Log class knows about the instance of the class that just subscribed to it and holds a reference to it (how else can it deliver the
event, if it doesnt know the address). Thus, the classes that subscribe to the Log and that do no unsubscribe will never be collected by the
garbage collection.

Open instance delegates


The key feature behind this implementation of the weak event pattern is open instance delegates. You are probably wondering: what the hell are
open instance delegates? Well, good question, and I will try to explain it. An open instance delegate is just as a regular delegate, it points to the
method of a specific class, but the biggest difference is that it does not bind to a specific instance. This means that it can be described as: I know

you live on that street (method), but I have not clue in which city (instance) that is. The instance can be specified later. The delegate for a regular
event handler looks like this:

public delegate void OpenInstanceHandler(TTarget @this, object sender, TEventArgs e);

The @this is nothing special, it allows us to use the this keyword so everyone knows that the target should be passed there. As you can see, it
contains 3 parameters. The first one is the target (the city), the second and third parameters are the parameters of the regular event handler.

Weak references
The weak event listener creates an open instance delegate and stores both the source and target in a WeakReference class. As soon as one of
these references are no longer valid, the class is unbound. The good side of this approach is that this weak event listener does not leak when the
event never fires.

What does it support


The following use cases are supported:
Instance source (event) and instance target (handler)
Static source (event) and instance target (handler)
Instance source (event) and static target (handler)
So, actually it handles everything that can cause a memory leak via event subscriptions!

What does it not support and what are the downsides


This weak event listener follows the rules of the .NET framework. So, it cannot subscribe to private events. If you want private events, do your
own hacking (the source is available, you only have to change the DefaultEventBindingFlags at the top of the class).
There are a few downsides about using a weak event listeners in general:
Its notation is ugly, the original .NET way looks way better
You have to name the event by string, that sucks (if you know a better way, contact me!)
It can only handle events with a handler of EventHandler<TEventArgs>
You become a lazy developer not caring about subscriptions

How to use
There are 4 categories of event subscriptions, all described below.

Instance to instance
This is the situation where an instance target subscribes to an instance event. The events are unbound as soon as either the target or source are
collected.

var source = new EventSource();


var listener = new EventListener();
var weakEventListener = WeakEventListener<EventListener, EventSource,
EventArgs>.SubscribeToWeakEvent(listener, source, "PublicEvent",
listener.OnPublicEvent);

Instance to static
This is the situation where a static target subscribes to an instance event. The events are unbound as soon as the source is collected.

var source = new EventSource();


var weakEventListener = WeakEventListener<EventListener, EventSource,
EventArgs>.SubscribeToWeakEvent(null, source, "PublicEvent",
EventListener.OnEventStaticHandler);

Static to instance
This is the situation where an instance target subscribes to a static event. The events are unbound as soon as the target is collected.

var listener = new EventListener();


var weakEventListener = WeakEventListener<EventListener, EventSource,
EventArgs>.SubscribeToWeakEvent(listener, null, "StaticEvent",
listener.OnPublicEvent);

Static to static
This is not supported because you shouldnt be using a weak event listener here. Static events with static event handlers simply cannot cause
memory leaks because both the source and the target have no instance. However, it might be possible that you subscribe to an event too many
times and the event fires too many times. But again, no memory issues here.

Reflection
Internally, Catel uses lots of reflection to implement some of its behavior. And why not make all these excellent reflection classes public?

Getting loaded assemblies


In WPF, it is very simple to get all the loaded assemblies. In Silverlight, it already gets a bit harder. Silverlight in combination with modules that
are separately loaded are horrible to use via reflection. In Catel, it is possible to register xap files to the AssemblyHelper class:

AssemblyHelper.RegisterAssembliesFromXap(xapStream);

Catel unpacks the xap (which is basically just a zip file) and adds all the assemblies to an internal list of assemblies. This way, the
AssemblyHelper.GetLoadedAssemblies method actually returns all the loaded assemblies, also the ones in dynamically loaded xaps that are not
available by default.

Getting types in Silverlight


Sometimes you know what type to get and what assembly it is living in. However, you don't want to be version-dependent by specifying the fully
qualified assembly name. Using the TypeHelper.GetType method, it is possible to get a type by only the assembly name (say Catel.Silverlight)
and the type name (say Catel.Data.ObservableObject).

var type = PropertyHelper.GetType("Catel.Data.ObservableObject", "Catel.Silverlight");

Setting or getting properties of objects


In lots of cases, you need to possibility to set or get properties of an object via reflection. This behavior is implemented in the PropertyHelper
class. Below are a few examples.

Check if a property is available on an object


PropertyHelper.IsPropertyAvailable(person, "FirstName");

Getting a property value


PropertyHelper.GetValue(person, "FirstName");

or

string firstName;
PropertyHelper.TryGetValue(person, "FirstName", out firstName);

Setting a property value


PropertyHelper.SetValue(person, "FirstName", "Geert");

or

PropertyHelper.TrySetValue(person, "FirstName", "Geert");

Scoping
Sometimes scoping is important to share an object inside a specific scope which cannot be determined upfront. A great example is the
serialization inside Catel which requires a serialization scope which can be shared over a lot of objects. Scoping in Catel is really. To create a
scope of an object with a specific tag, use the code below:

using (var scopeManager = ScopeManager<object>.GetScopeManager("object"))


{
var scopeObject = scopeManager.ScopeObject;
// scope can be used here
}

When the scope does not yet exist, it will be created and the object will be created by the TypeFactory.

Serialization
Supported serialization formats
Type

Assembly / package

Available from
version

Binary

Catel.Core

1.0.0

Json

Catel.Serialization.Json

4.2.0

Xml

Catel.Core

1.0.0

Additional information

Work in progress, uses Json.net for the json serialization.

Yaml

Catel.Serialization.Yaml

Work in progress

More about serialization


Introduction to serialization
Specifying what gets serialized
Customizing serialization
Supported serializers

Introduction to serialization
Serialization modes
Serializing a model
Warming up serialization
Warming up specific types
Warming up automatically
Warming up using multiple threads
Backwards compatibility for binary serialization

Serialization modes
Depending on the target framework, several options are available as serialization modes:
Serialization
mode

WPF

Silverlight

Windows Phone
(SL)

Windows Phone
(RT)

WinRT

Xamarin.Android

Xamarin.iOS

Comments

Binary
Json

Available in separate Catel.Serializatio


n.Json package

XML

Note that it is possible to implement custom serialization techniques or customize the serialization

Serializing a model
The code below shows how to save an object (which can, of course, be a complex graph of nested objects):

var myObject = new MyObject();


using (var fileStream = File.Create(@"C:\myobject.dob"))
{
myObject.Save(fileStream);
}

Looks too easy, but this really is the only thing you need to do. You can specify the serialization mode in the several available overloads of the Sa
ve method.
Loading is as easy as saving, as you can see in the following code:

MyObject myObject = null;


using (var fileStream = File.Open(@"C:\myobject.dob", FileMode.Open))
{
myObject = ModelBase.Load<MyObject>(fileStream, SerializationMode.Xml);
}

Note that for a model to support the Save and Load methods, it must derive from SavableModelBase

Warming up serialization
The first time a serializer needs to serialize an object, it needs to perform some reflection to gather all the required information. This can have a
negative impact on performance for the end-user during serialization. This load cannot be prevented, but it is possible to warmup the serializer at
any time when it is convenient (for example, during startup of the application).

Warming up specific types


This code will warm up all the specified types:

var typesToWarmup = new type[] {

typeof(Settings) };

var xmlSerializer = SerializationFactory.GetXmlSerializer();


xmlSerializer.Warmup(typesToWarmup);
var binarySerializer = SerializationFactory.GetBinarySerializer();
binarySerializer.Warmup(typesToWarmup);

Warming up automatically
This code will warm up all types implementing the ModelBase class:

var xmlSerializer = SerializationFactory.GetXmlSerializer();


xmlSerializer.Warmup();
var binarySerializer = SerializationFactory.GetBinarySerializer();
binarySerialzier.Warmup();

Note that warming up for all types might take a serious amount of time and might increase the memory footprint of your application
depending on the number of models

Warming up using multiple threads


By default, Catel will optimize the initialization and dispatch them to different threads. Using extensive testing, the Catel team discovered that
approximately 1000 types / thread is the ideal load balancing (otherwise the spawning of the threads is more expensive than it handling it on the
same thread). If this behavior needs to be customized, simply provide the number of types per thread. If -1 is specified, all types will be warmed
up in a single thread.
The code example below shows how to initialize all types deriving from ModelBase on a single thread:

var xmlSerializer = SerializationFactory.GetXmlSerializer();


xmlSerialzier.Warmup(null, -1);

Backwards compatibility for binary serialization


This example shows how an old (standard .NET) data class that uses custom binary serialization can easily be converted to a ModelBase to use
the ModelBase even for all your existing classes.
Declare a new ModelBase class (remember the dataobject code snippet). If the new class is in a new assembly, or has a new name or
namespace, use the RedirectType attribute to let the ModelBase know that when it finds the old type, it should deserialize that type into the new
type.
Then, by default, the ModelBase class will try to deserialize the old object. If it fails to do so, it will fall back on the default values provided by the
property declarations. However, it is also possible to override the GetDataFromSerializationInfo method:

/// <summary>
/// Retrieves the actual data from the serialization info.
/// </summary>
/// <remarks>
/// This method should only be implemented if backwards compatibility should be
implemented for
/// a class that did not previously implement the ModelBase class.
/// </remarks>
protected override void GetDataFromSerializationInfo(SerializationInfo info)
{
// Check if deserialization succeeded
if (DeserializationSucceeded)
{
return;
}
// Deserialization did not succeed for any reason, so retrieve the values manually
// Luckily there is a helper class (SerializationHelper)
// that eases the deserialization of "old" style objects
FirstName = SerializationHelper.GetString(info, "FirstName",
FirstNameProperty.GetDefaultValue());
LastName = SerializationHelper.GetString(info, "LastName",
LastNameProperty.GetDefaultValue());
}

Specifying what gets serialized


Including fields and properties using IncludeInSerialization attribute
Excluding fields and properties using ExcludeFromSerialization attribute
Implementing a custom ISerializationManager
By default, Catel only serializes the defined Catel properties on the ModelBase or any deriving classes. It is possible to customize this behavior.
Below is a class which will be used in all examples:

public class MyModel : ModelBase


{
private string _fieldValue;
public string RegularProperty { get; set; }
public string CatelProperty
{
get { return GetValue<string>(CatelPropertyProperty); }
set { SetValue(CatelPropertyProperty, value); }
}
public static readonly PropertyData CatelPropertyProperty =
RegisterProperty("CatelProperty", typeof(string), null);
}

Member name

Gets serialized

_fieldValue

RegularProperty

CatelProperty

Including fields and properties using IncludeInSerialization attribute


To include fields or regular properties on an object, use the following code:

public class MyModel : ModelBase


{
[IncludeInSerialization]
private string _fieldValue;
[IncludeInSerialization]
public string RegularProperty { get; set; }
public string CatelProperty
{
get { return GetValue<string>(CatelPropertyProperty); }
set { SetValue(CatelPropertyProperty, value); }
}
public static readonly PropertyData CatelPropertyProperty =
RegisterProperty("CatelProperty", typeof(string), null);
}

Member name

Gets serialized

_fieldValue

RegularProperty

CatelProperty

Note that private members can only be serialized in .NET and not in Silverlight, Windows Phone or the Windows Runtime

Excluding fields and properties using ExcludeFromSerialization attribute


To exclude Catel properties on an object, use the following code:

public class MyModel : ModelBase


{
private string _fieldValue;
public string RegularProperty { get; set; }
[ExcludeFromSerialization]
public string CatelProperty
{
get { return GetValue<string>(CatelPropertyProperty); }
set { SetValue(CatelPropertyProperty, value); }
}
public static readonly PropertyData CatelPropertyProperty =
RegisterProperty("CatelProperty", typeof(string), null);
}

Member name

Gets serialized

_fieldValue

RegularProperty

CatelProperty

Implementing a custom ISerializationManager


Internally Catel uses a default implementation of the ISerializationManager to determine what members of a type should be serialized. It is
possible to customize this behavior by overriding a single method or by creating a brand new type. Below is an example which always excludes P
assword properties and fields from serialization.

public class SafeSerializationManager : SerializationManager


{
public override HashSet<string> GetFieldsToSerialize(Type type)
{
var fieldsList = new List<string>(base.GetFieldsToSerialize(type));
for (int i = 0; i < fieldsList.Count; i++)
{
if (string.Equals(fieldsList[i], "_password"))
{
fieldsList.RemoveAt(i--);
}
}
return new HashSet<string>(fieldsList);
}
public override HashSet<string> GetPropertiesToSerialize(Type type)
{
var propertiesList = new List<string>(base.GetPropertiesToSerialize(type));
for (int i = 0; i < propertiesList.Count; i++)
{
if (string.Equals(propertiesList[i], "Password"))
{
propertiesList.RemoveAt(i--);
}
}
return new HashSet<string>(propertiesList);
}
}

Don't forget to register it in the ServiceLocator as well:

var serviceLocator = ServiceLocator.Default;


serviceLocator.RegisterType<ISerializationManager, SafeSerializationManager>();

Customizing serialization
The serialization engine explained
Customizing serialization
Customizing the serialization for specific models
Creating the modifier
Registering the modifier
Customizing the serialization engines
The documentation engine has been completely rewritten for Catel 3.7. This documentation only applies to Catel 3.7 and higher.

The serialization engine explained


All classes deriving from ModelBase use the serialization engine of Catel to serialize itself in a whole or as a subset of properties. Below is a

schema which sheds some light on the architecture.

The SerializerBase now contains all the serialization and deserialization logic. The advantage is that this logic is no longer contained by the Model
Base itself which makes the class much simpler to understand and maintain. Now the SerializerBase contains all the heavy lifting, the deriving
classes (XmlSerializer and BinarySerializer) only have to implement a few methods.
The serialization process works as shown in the diagram below:

Workflow 1 represents the serialization. Workflow 2 represents the deserialization.

Customizing serialization
Customizing the serialization for specific models
Catel has a default behavior for what gets serialized. It can be tweaked by including / excluding fields and properties by using the IncludeInSeriali
zation and ExcludeFromSerialization attributes. But sometimes one needs more specific customization of the serialization for a specific type. This
customization is possible via the ISerializerModifier.

Creating the modifier


To customize the serialization of a specific model type, one needs to implement the ISerializerModifier interface. The example belows shows how
to encrypt the Password property on the Person model class.

public class PersonSerializerModifier : SerializerModifierBase<Person>


{
public override void SerializeMember(ISerializationContext context, MemberValue
memberValue)
{
if (string.Equals(memberValue.Name, "Password"))
{
memberValue.Value = EncryptionHelper.Encrypt(memberValue.Value);
}
}
public override void DeserializeMember(ISerializationContext context, MemberValue
memberValue)
{
if (string.Equals(memberValue.Name, "Password"))
{
memberValue.Value = EncryptionHelper.Decrypt(memberValue.Value);
}
}
}

Registering the modifier


To register a modifier for a specific class, define the SerializerModifier attribute:

[SerializerModifier(typeof(PersonSerializerModifier))]
public class Person : ModelBase
{
// .. class contents
}

Note that modifiers are inherited from base classes. When serializing, the modifiers defined on the most derived classes will be called
last. When deserializing, the modifies defined on the most derived classes will be called first.

Customizing the serialization engines


Since the SerializerBase does all the heavy lifting, it is very easy to customize the behavior of an existing serializer or create a completely new
one. Each serializer implements its own interface and are registered in the ServiceLocator using the following interfaces:
XmlSerializer => IXmlSerializer
BinarySerializer => IBinarySerializer
To customize a serializer, derive from an existing class and customize a method. The serializer below makes sure that specific members are
never serialized. It keeps all other serialization logic intact.

public class SafeXmlSerializer : XmlSerializer


{
protected override bool ShouldIgnoreMember(ModelBase model, PropertyData property)
{
if (model is SecurityModel)
{
if (string.Equals(property.Name, "Password"))
{
return true;
}
}
return base.ShouldIgnoreProperty(model, property);
}
}

The only thing to do now is to register this custom instance in the ServiceLocator:

ServiceLocator.Default.RegisterType<IXmlSerializer, SafeXmlSerializer>();

The following methods on the serializer classes might be of interest when customizing the serialization:
ShouldIgnoreProperty
BeforeSerialization
BeforeSerializeProperty
AfterSerializeProperty
AfterSerialization
BeforeDeserialization
BeforeDeserializeProperty
AfterDeserializeProperty
AfterDeserialization

Supported serializers
Below is a list of supported serializers. Note that the serializers are an implementation detail for Catel. You can use all the serializer features
(such as serializer modifiers) the same way on all serializers.
BinarySerializer
JsonSerializer
XmlSerializer

BinarySerializer
The binary serializer uses the .NET binary serializer formatters to serialize the objects.

JsonSerializer
Preserve references (and support circular references)
Support complex dynamic types
The JsonSerializer is implemented in a separate assembly because it uses Json.Net under the hood.

Preserve references (and support circular references)


By default the JsonSerializer supports circular references. It does so by adding additional property values to the json. Below is a json object with
support for circular references:

{
"$graphid":1,
"Name":"1",
"CircularModel":{
"$graphid":2,
"Name":"2",
"CircularModel":{
"$graphrefid":1
}
}
}

or

{
"$graphid": 1,
"Collection1": [1,
2,
3,
4,
5],
"$Collection1_$graphid": 2,
"Collection2": [1,
2,
3,
4,
5],
"$Collection2_$graphrefid": 2
}

To disable the support for reference preservation, use the code below:

var jsonSerializer = dependencyResolver.Resolve<IJsonSerializer>();


jsonSerializer.PreserveReferences = false;

Support complex dynamic types


Catel can support complex dynamic types. For this to be supported in json, the objects need additional type information in order to restore the
type info again during deserialization. Below is a json object with the type information stored inside the json:

{
"$typename":"Catel.Test.Data.IniFile",
"FileName":"MyIniFile",
"IniEntryCollection":[
{
"$typename":"Catel.Test.Data.IniEntry",
"Group":"Group 0",
"Key":"Key 0",
"Value":"Value 0",
"IniEntryType":0
},
{
"$typename":"Catel.Test.Data.IniEntry",
"Group":"Group 1",
"Key":"Key 1",
"Value":"Value 1",
"IniEntryType":1
},
{
"$typename":"Catel.Test.Data.IniEntry",
"Group":"Group 2",
"Key":"Key 2",
"Value":"Value 2",
"IniEntryType":0
}
]
}

To disable the type information in json, use the code below:

var jsonSerializer = dependencyResolver.Resolve<IJsonSerializer>();


jsonSerializer.WriteTypeInfo = false;

XmlSerializer
The xml serializer uses the DataContractSerializer from .NET to serialize the object graphs.

Thread safe code


Writing a multiple threading application is always a challenge. Eventually you need use objects or statements with the ability to synchronize
access to the critical sections of the code by taking and releasing a lock.

Background information
The common solution to access the thread-sensitive resources is use the lock statement just as follow:

private readonly object _syncObj = new object();


public void DoTheWork()
{
lock (_syncObj)
{
// Access to the thread-sensitive resources here.
}
}

But some times the scenario is not quite simple, then you need to use the Monitor class in order to synchronize cross method operations. Here is
an example:

private readonly object _syncObj = new object();


public void DoTheWork()
{
StartTheWork();
object result = EndTheWork();
}
private void StartTheWork()
{
Monitor.Enter(_syncObj);
try
{
// Access to the thread-sensitive resources here.
}
catch(Exception)
{
Monitor.Exit(_syncObj);
throw;
}
}
private object EndTheWork()
{
try
{
// Access to the thread-sensitive resources here.
return new object();
}
finally
{
Monitor.Exit(_syncObj);
}
}

To combine the power of the simplicity of the lock statement syntax and the flexibility of the Monitor class, Catel introduces the
SynchronizationContext class, allowing you to write the code like this.

private readonly List<IValidator> _validators = new List<IValidator>();


private readonly SynchronizationContext _synchronizationContext = new
SynchronizationContext();
public bool Contains(IValidator validator)
{
Argument.IsNotNull("validator", validator);
return _synchronizationContext.Execute(() => _validators.Contains(validator));
}
public void Remove(IValidator validator)
{
Argument.IsNotNull("validator", validator);
_synchronizationContext.Execute(() => _validators.Remove(validator));
}
public void BeforeValidation(object instance, List<IFieldValidationResult>
previousFieldValidationResults, List<IBusinessRuleValidationResult>
previousBusinessRuleValidationResults)
{
_synchronizationContext.Acquire();
try
{
foreach (IValidator validator in _validators)
{
validator.BeforeValidation(instance, previousFieldValidationResults,
previousBusinessRuleValidationResults);
}
}
catch (Exception)
{
_synchronizationContext.Release();
throw;
}
}
public void AfterValidateBusinessRules(object instance,
List<IBusinessRuleValidationResult> validationResults)
{
try
{
foreach (IValidator validator in _validators)
{
validator.AfterValidateBusinessRules(instance, validationResults);
}
}
catch (Exception)
{
_synchronizationContext.Release();
throw;
}
}

SynchronizationContext also allow you create asynchronous locking request, that could be useful in Silverlight Application where the
action of lock the main thread is not allowed.

Acquiring a lock
To acquire a lock, only a call to Acquire is required:

_synchronizationContext.Acquire();

Releasing a lock
To release a lock, only a call to Release is required:

_synchronizationContext.Release();

Automatic locking of a method


It is also possible to automatically lock and release a method call. This can be accomplished using the Execute method.

_synchronizationContext.Execute(() => ThreadSafeCodeExecution());

Validation
The ViewModelBase derives from ModelBase, thus all information here also applies to the ViewModelBase

Validation is very important for data objects. Therefore, the ModelBase supports all kinds of different validation:
Internal validation via the ValidateFields and ValidateBusinessRules methods
Validation via data annotations (attributes)
External validators using the IValidatorProvider and IValidator interfaces
The validation results are cached and only executed when a property changes (the object becomes dirty) or when the validation is forced.
Validation via validate methods
Validation via data annotations
Validation via special model validators
Validation via IValidator
Using the validation context
Getting a summary of validation results
Deferring validation

Different types of validation


There are two different types of validation in Catel, namely warnings and errors. There are also two flavors of validations, namely field validation
and business rule validation.

Order of execution of events


The order of execution is very important if you want to perform very advanced validation (such as translating validations at the end of each
validation sequence).
1. IValidator.BeforeValidation
2. OnValidation (raises Validating event)
if not already validated
3.

3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.

IValidator.BeforeValidateFields
OnValidatingFields (raises the ValidatingFields event)
IValidator.ValidateFields
ValidateFields
OnValidatedFields (raises the ValidatedFields event)
IValidator.AfterValidateFields
IValidator.BeforeValidateBusinessRules
OnValidatingBusinessRules (raises the ValidatingBusinessRules event)
IValidator.ValidateBusinessRules
ValidateBusinessRules
OnValidatedBusinessRules (raises the ValidatedBusinessRules event)
IValidator.AfterValidateBusinessRules
end if not already validated
15. OnValidated (raises the Validated event)
16. IValidator.AfterValidation
There are lots of events, and it may seem complex and confusing at first sight. However, all these events give developers the opportunity to hook
into the validation sequence at any time.

Validation via validate methods


The ViewModelBase derives from ModelBase, thus all information here also applies to the ViewModelBase

The easiest way to implement validation is to override the ValidateFields and ValidateBusinessRules methods. Below is an example of an
implementation of the ValidateFields method:

protected override void ValidateFields(List<IFieldValidationResult> validationResults)


{
if (string.IsNullOrEmpty(FirstName))
{
validationResults.Add(FieldValidationResult.CreateError(FirstNameProperty,
"First name is required"));
}
if (string.IsNullOrEmpty(LastName))
{
validationResults.Add(FieldValidationResult.CreateError(LastNameProperty,
"Last name is required"));
}
if (Gender == Gender.Unknown)
{
validationResults.Add(FieldValidationResult.CreateError(GenderProperty,
"Gender cannot be unknown"));
}
}

Validation via data annotations


The ViewModelBase derives from ModelBase, thus all information here also applies to the ViewModelBase

Data annotations are validation when the specific property is set. For example, when a property FirstName is set, all the data annotations on the
FirstName property are validated.

Decorating properties with data annotations


Decorating properties is very simple. For example, to make a property mandatory, use the following definition (note the Required attribute):

/// <summary>
/// Gets or sets the middle name.
/// </summary>
[Required]
public string MiddleName
{
get { return GetValue<string>(MiddleNameProperty); }
set { SetValue(MiddleNameProperty, value); }
}
/// <summary>
/// Register the property so it is known in the class.
/// </summary>
public readonly PropertyData MiddleNameProperty = RegisterProperty("MiddleName",
typeof(string), string.Empty);

For more information about data annotations, read the official MSDN documentation .

Validation via special model validators


By default, Catel registers the AttributeValidatorProvider as the IValidatorProvider. This way the ModelBase and all the classes that derive from it
can easily add a custom validator by using the ValidateModelAttribute.
Note that it is still possible to register a custom IValidatorProvider to customize this behavior. It is even possible to set the Validator prop
erty of the ModelBase on a specific instance of a model
Implementing the validator

Implementing the validator


The first thing that needs to be done is to write a custom implementation of the IValidator interface. You can either implement all the members
yourself or derive from ValidatorBase as is shown below:

public class PersonValidator : ValidatorBase<PersonModel>


{
public override void ValidateFields(PersonModel instance,
List<IFieldValidationResult> validationResults)
{
if (string.IsNullOrWhiteSpace(instance.FirstName))
{
validationResults.Add(FieldValidationResult.CreateError(PersonModel.FirstNameProperty,
"First name is required"));
}
if (string.IsNullOrWhiteSpace(instance.LastName))
{
validationResults.Add(FieldValidationResult.CreateError(PersonModel.FirstNameProperty,
"First name is required"));
}
}
public override void ValidateBusinessRules(PersonModel instance,
List<IBusinessRuleValidationResult> validationResults)
{
// No business rules validations yet
}
}

Decorating a model with the attribute


Once a validator is available, the only thing that needs to be done is to decorate the model with the ValidateModelAttribute:

[ValidateModel(typeof(PersonValidator))]
public class PersonModel : ModelBase
{
public string FirstName
{
get { return GetValue<string>(FirstNameProperty); }
set { SetValue(FirstNameProperty, value); }
}
public static readonly PropertyData FirstNameProperty = RegisterProperty("FirstName",
typeof(string), string.Empty);
public string LastName
{
get { return GetValue<string>(LastNameProperty); }
set { SetValue(LastNameProperty, value); }
}
public static readonly PropertyData LastNameProperty = RegisterProperty("LastName",
typeof(string), string.Empty);
}

The custom validator will now automatically be called.

Validation via IValidator


The ViewModelBase derives from ModelBase, thus all information here also applies to the ViewModelBase

The validation in Catel is extremely flexible, but sometimes it is just not enough or you are forced to use external validators. For such cases, Catel
provides the IValidatorProvider and IValidator interfaces. These allow very flexible injection or external validators into data objects and view
models of Catel.

Implementing the IValidatorProvider


The IValidatorProvider is responsible to return the right IValidator for a specific type. There is a convenience implementation named
ValidatorProviderBase which only requires the implementation of one single method. Below is an example of an implementation of the
IValidatorProvider.

public class ValidatorProvider : ValidatorProviderBase


{
/// <summary>
/// Gets a validator for the specified target type.
/// </summary>
/// <param name="targetType">The target type.</param>
/// <returns>
/// The <see cref="T:Catel.Data.IValidator"/> for the specified type or
<c>null</c> if no validator is available for the specified type.
/// </returns>
/// <exception cref="T:System.ArgumentNullException">The <paramref
name="targetType"/> is <c>null</c>.</exception>
public override IValidator GetValidator(Type targetType)
{
if (targetType == typeof(ValidationInIValidatorViewModel))
{
return new Validator();
}
// No validator available for other types
return null;
}
}

Implementing the IValidator


The IValidator exposes lots of methods to gain the as much freedom as possible. However, most of the methods that are exposed by the interface
are hardly used. Therefore there is a convenience base class named ValidatorBase. To create a basic validator, derive from the class and
override the methods required for validation.

public class Validator : ValidatorBase<TargetClass>


{
/// <summary>
/// Validates the fields of the specified instance. The results must be added to
the list of validation
/// results.
/// </summary>
/// <param name="instance">The instance to validate.</param>
/// <param name="validationResults">The validation results.</param>
/// <exception cref="T:System.ArgumentNullException">The <paramref
name="instance"/> is <c>null</c>.</exception>
/// <exception cref="T:System.ArgumentNullException">The <paramref
name="validationResults"/> is <c>null</c>.</exception>
public override void ValidateFields(TargetClass instance,
List<IFieldValidationResult> validationResults)
{
if (string.IsNullOrEmpty(instance.FirstName))
{
validationResults.Add(FieldValidationResult.CreateError(TargetClass.FirstNameProperty,
"First name cannot be empty"));
}
if (string.IsNullOrEmpty(instance.LastName))
{
validationResults.Add(FieldValidationResult.CreateError(TargetClass.LastNameProperty,
"Last name cannot be empty"));
}
}
/// <summary>
/// Validates the business rules of the specified instance. The results must be
added to the list of validation
/// results.
/// </summary>
/// <param name="instance">The instance to validate.</param>
/// <param name="validationResults">The validation results.</param>
/// <exception cref="T:System.ArgumentNullException">The <paramref
name="instance"/> is <c>null</c>.</exception>
/// <exception cref="T:System.ArgumentNullException">The <paramref
name="validationResults"/> is <c>null</c>.</exception>
public override void ValidateBusinessRules(TargetClass instance,
List<IBusinessRuleValidationResult> validationResults)
{
// No business rules (yet)
}
}

Setting the validator in ModelBase


To register an IValidator instance on a ModelBase, use the following code:

myObject.Validator = new MyValidator();

If an IValidatorProvider instance is available, the following code can be used to allow a more generic approach. This code assumes that the
IValidatorProvider is registered in the ServiceLocator.

var validatorProvider = ServiceLocator.Instance.ResolveType<IValidatorProvider>();


myObject.Validator = validatorProvider.GetValidator(myObject.GetType());

If the IValidatorProvider returns null (which is allowed), no custom validator will be used.

Setting the validator in ViewModelBase


The ViewModelBase has it's own ServiceLocator. The easiest way to support a validator is to register an IValidatorProvider instance in the
ServiceLocator:

ServiceLocator.Instance.RegisterType<IValidatorProvider, MyValidatorProvider>();

The ViewModelBase will automatically retrieve the right IValidator for the view model. If no IValidatorProvider is registered in the ServiceLocator,
no validator will be set automatically. It is also possible to set the Validator property manually, but it is recommended to use an IValidatorProvider
and register it.

Using the validation context


The ViewModelBase derives from ModelBase, thus all information here also applies to the ViewModelBase

Sometimes detailed information about validation is required. This is possible in Catel thanks to the ValidationContext class. The ValidationContext
serves as the container for all validation results that are gathered via the available validation methods. The ValidationContext has lots of methods
that all return lists of either IFieldValidationResult or IBusinessRuleValidationResult.
The examples below are shown a starter examples, but you can gather every type of validation result by using the ValidationContext. To retrieve
the validation context of an object, use the following code:

var modelValidation = new MyViewModel() as IModelValidation;


var validationContext = modelValidation.ValidationContext;

Getting the number of or warnings and errors


To retrieve the total number of warnings and errors, use the following code:

int count = validationContext.GetValidationCount();

Getting all the field errors


To retrieve all the field errors, use the following code:

var fieldErrors = validationContext.GetFieldErrors();

Getting all the field errors of a specific property


To retrieve all the field errors of a specific property, use the following code:

var fieldErrors = validationContext.GetFieldErrors("MyProperty");

Getting all the business rule warnings


To retrieve all the business rule warnings:

var businessRuleWarnings = validationContext.GetBusinessRuleWarnings();

Getting all the business rule errors with a specific tag


To retrieve all the business rule errors with a specific tag, use the following code:

var businessRuleErrors = validationContext.GetBusinessRuleErrors("myTag");

Getting a summary of validation results


Sometimes you just need to get a summary of all warnings and errors of an object. All validation is gathered in the IValidationContext and
available on that class. However, there are some convenience classes that allow a developer to create a summary based on a specific tag. This
convenience class is IValidationSummary, which gathers the right information from an instance of IValidationContext.

Creating a summary of all validations


To retrieve a summary of all validations from a IValidationContext, use the following code:

var validationSummary = validationContext.GetValidationSummary();

Creating a summary of all validations with a specific tag


To retrieve a summary of all validations with a specific tag from a IValidationContext, use the following code:

var validationSummary = validationContext.GetValidationSummary("tag");

Using the ValidationToViewModel attribute


The ValidationToViewModel attribute allows a developer to gather a summary of an object easily. For example, to get all the person related
validation into the PersonValidationSummary property, use the property definition below:

[ValidationToViewModel(Tag = "PersonValidation")]
public IValidationSummary PersonValidationSummary { get; set; }

All validation results that have the tag PersonValidation will automatically be gathered into the PersonValidationSummary property after each
validation sequence.

Deferring validation
The opinions about validation differ from person to person. Some people think it is best practice to immediately show the errors to the users.

Others want to defer it to the moment where the user clicks the Save or OK button. Catel supports both "best practices".
Suspending validation for a batch of changes
Deferring validation in view models

Suspending validation for a batch of changes


Sometimes you need to change a batch of properties and don't want validation to be called after every property change. This can be
accomplished by using the following code inside a ModelBase class:

SuspendValidation = true;
// change several properties here
SuspendValidation = false;
// Now force validation
Validate(true);

Deferring validation in view models


Below is a table of properties that can be used to affect the validation deferring.
Property

Validate immediately

Defer to a later moment

DeferValidationUntilFirstSaveCall

false

true

ValidateModelsOnInitialization

true

false

If the DeferValidationUntilFirstSaveCall property, is used, it must be set as first property in the view model because the validation kicks
in immediately when properties change.

Catel.MVVM
The last few years, MVVM has become the number one pattern to write applications using WPF, Silverlight, and Windows Phone 7. The actual
pattern is very simple, but there are some flaws and questions lots of MVVM users have, such as:
How to show modal dialogs or message boxes inside a View-Model?
How to run processes inside a View-Model?
How to let the user select a file inside a View-Model?
In my opinion, this is where the good frameworks separate themselves from the bad ones. For example, people actually calling
MessageBox.Show inside a View-Model are using the pattern wrong. If you are one of the developers that directly call a MessageBox inside a
View-Model, ask yourself this: who is going to click the button during a unit test?
Before we actually started developing Catel, we did lots of investigations to make sure that the MVVM pattern was really useful in Line of
Business (LoB) applications and does not miss the finishing touch. Thanks to this investigation and research, we created a solid MVVM
framework which solves all the known problems of the MVVM pattern.
This part of the documentation explains all about the MVVM framework included with Catel. The MVVM framework that ships with Catel has the
following characteristics and features:
Very easy to use, a view model is created within 10 minutes
Direct pass-through of view model properties to Models
Validation mapping from model to view model and back
Solves the nested user controls problem
If you are not yet familiar with MVVM, it is advised to read a small introduction on Wikipedia.
Auditing
Behaviors & triggers
Bindings

Commands & events


Converters
Designers
Handling application initialization parameters
Locators and naming conventions
Services
View models
Views

Auditing
There are lots of lightweight MVVM frameworks out there, which work great for the basics. However, if you are writing larger enterprise
applications, notifying the UI of changed properties isn't enough. For example, did you think about Command Authentication? Or what about
sensor emulation for Windows Phone 7 (that Microsoft dont provide)?
Why auditing
Creating an auditor
Registering an auditor

Why auditing
There are many reasons why auditing should be added to an application. Most developers only add auditing to the database, but below are
several reasons to add auditing to the client as well:
Logging (what user did what on specific moments)
Gather statistics (which views (view models) are used most)
See what features of your software are being used by checking if anyone is actually invoking specific commands
Measure performance (how long does it take to update specific properties or why is a specific view-model so slow?)
With the auditing capabilities of Catel, you can create and register custom auditors that can handled changes and events of view models. This
way, you can gather a lot of statistics or any information that you want to gather about the user experience. Below is a list of events that can be
handled:
OnViewModelCreating
OnViewModelCreated
OnPropertyChanging
OnPropertyChanged
OnCommandExecuting
OnViewModelSaving
OnViewModelSaved
OnViewModelCanceling
OnViewModelCanceled
OnViewModelClosing
OnViewModelClosed
The developer has all the freedom to handle one or more methods in an auditor. Of course multiple auditors are possible as well.

Creating an auditor
Creating a new auditor is very simple. Create a new class, derive from AuditorBase and override the methods you are interested in. The class
example tracks the event to a fake analytics framework.

/// <summary>
/// Logs all commands to a custom analytics service.
/// </summary>
public class CommandAuditor : AuditorBase
{
private Analytics _analytics = new Analytics();
/// <summary>
/// Called when a command of a view model has just been executed.
/// </summary>
/// <param name="viewModel">The view model.</param>
/// <param name="commandName">Name of the command, which is the name of the command
property.</param>
/// <param name="command">The command that has been executed.</param>
/// <param name="commandParameter">The command parameter.</param>
public override void OnCommandExecuted(IViewModel viewModel, string commandName,
ICatelCommand command, object commandParameter)
{
_analytics.TrackEvent(viewModel.GetType(), "commandName");
}
}

Registering an auditor
Registering a new auditor is extremely easy as you can see in the code below:

AuditingManager.RegisterAuditor(new CommandAuditor());

Behaviors & triggers


Behaviors and triggers are very important to correctly separate the view from the view model. For example, to respond to and event in a view
model, you cannot simply subscribe to the events in the view. The EventToCommand behavior is a great example to solve this problem.
Catel offers lots of behaviors out of the box, so it is definitely worth taking a look at the behaviors.
Note that Windows 8.0 does not support any behaviors or triggers. Windows 8.1 does support behaviors, but no triggers.

Authentication
AutoCompletionBehavior
AutoScroll
DelayBindingUpdate
DoubleClickToCommand
EventToCommand
Focus
FocusFirstControl
FocusOnKeyPress
HideUntilViewModelLoaded
KeyPressToCommand
MouseInfo
Navigate
NumericTextBox
SelectTextOnFocus
UpdateBindingOnPasswordChanged
UpdateBindingOnTextChanged

Managing interactivity classes

Starting with Catel 4.0, it is possible to manage interactivity classes such as behaviors from the InteractivityManager class. This allows a
developer to get notified when a behavior or trigger is loaded or unloaded.
Note that the InteractivityManager is only compatible with behaviors and triggers using one of the Catel base classes

The manager contains both events and methods to retrieve information about triggers. For example, if one is interested in all the Focus triggers,
one could do the following:

public class FocusWatcher


{
private static readonly ILog Log = LogManager.GetCurrentClassLogger();
private readonly IInteractivityManager _interactivityManager;
public FocusWatcher(IInteractivityManager interactivityManager)
{
Argument.IsNotNull(() => interactivityManager);
_interactivityManager = interactivityManager;
_interactivityManager.BehaviorLoaded += OnBehaviorLoaded;
_interactivityManager.BehaviorUnloaded += OnBehaviorUnloaded;
}
private void OnBehaviorLoaded(object sender, BehaviorEventArgs e)
{
var focus = e.Behavior as Focus;
if (focus != null)
{
Log.Info("Focus behavior loaded");
}
}
private void OnBehaviorUnloaded(object sender, BehaviorEventArgs e)
{
var focus = e.Behavior as Focus;
if (focus != null)
{
Log.Info("Focus behavior unloaded");
}
}
}

Authentication
The Authentication behavior is able to hide, collapse or disable UI elements based on the current user state. The behavior uses the registered
IAuthenticationProvider instances to determine whether the user has access to the specified UI element.
1) Creating an authentication provider:

/// <summary>
/// Example implementation of the <see cref="AuthenticationProvider"/>. This class is
not really implemented
/// like it should, because it shouldn't be this easy to set the current role.
However, for the sake of simplicity,
/// this class has a simple property with the role of the user.
/// </summary>
public class AuthenticationProvider : IAuthenticationProvider
{
/// <summary>
/// Gets or sets the role the user is currently in.
/// </summary>
/// <value>The role.</value>
public string Role { get; set; }
public bool CanCommandBeExecuted(ICatelCommand command, object commandParameter)
{
return true;
}
public bool HasAccessToUIElement(FrameworkElement element, object tag, object
authenticationTag)
{
var authenticationTagAsString = authenticationTag as string;
if (authenticationTagAsString != null)
{
if (string.Compare(authenticationTagAsString, Role, true) == 0)
{
return true;
}
}
return false;
}
}

2) Register the authentication provider in the ServiceLocator:

Catel.IoC.ServiceLocator.Instance.RegisterType<IAuthenticationProvider,
AuthenticationProvider>();

3) Add the following XML namespaces to your view:

xmlns:i="clr-namespace:System.Windows.Interactivity;assembly=System.Windows.Interactiv
ity"
xmlns:catel="http://catel.codeplex.com"

4) Add the behavior. As you can see, it is possible to provide a custom AuthenticationTag, which is passed to the IAuthenticationProvider:

<TextBox>
<i:Interaction.Behaviors>
<catel:Authentication AuthenticationTag="Administrator" Action="Disable" />
</i:Interaction.Behaviors>
</TextBox>

5) Below are screenshots of the example applications (which can be found at http://catelexamples.codeplex.com):
Logged in as administrator:

Logged in as read-only user:

AutoCompletionBehavior
To enable auto completion features, once can use the services and behaviors provided by Catel. There are two components required for auto
completion:
1. AutoCompletionService => takes care of the actual filtering
2. AutoCompletionBehavior => can be attached to a TextBox to support a dropdown with recommended values
The auto completion features looks like the screenshot below:

AutoCompletion service
The default implementation automatically filters the collection specified. If there is no filter yet, it will filter the top 10 occurrences from the
collection. When a filter is available, it will do the same but with the filter applied.

AutoCompletion behavior
The behavior can be used as follows:

<catel:AutoCompletionBehavior PropertyName="{Binding PropertyName, Mode=OneWay}"


ItemsSource="{Binding RawCollection}"
IsEnabled="{Binding EnableAutoCompletion}"/>

If the PropertyName is null or whitespace, the ItemsSource will be treated as collection of strings to be filtered directly

AutoScroll
The AutoScroll behavior automatically scrolls to a specific direction when the ItemsSource of an ItemsControl changes.
1) Add the following XML namespaces:

xmlns:i="clr-namespace:System.Windows.Interactivity;assembly=System.Windows.Interactiv
ity"
xmlns:catel="http://catel.codeplex.com"

2) Add behavior

<ListBox ItemsSource="{Binding LogEntries}">


<i:Interaction.Behaviors>
<catel:AutoScroll ScrollDirection="Bottom" ScrollTreshold="10" />
</i:Interaction.Behaviors>
</ListBox>

The ScrollDirection determines the direction (Top or Bottom).


The ScrollTreshold allows the treshold of the real offset (to determine whether auto scroll should be enabled). For example, when the user is
manually scrolling, this behavior will pause.

DelayBindingUpdate
Sometimes, a binding update should be delayed for performance reasons. This is possible using the DelayBindingUpdate behavior. This behavior
modifies the binding mode to explicit and internally watches for property changes. If the bound dependency property changes, the behavior will
wait for the time to pass and then update. If the value changes again within the timeframe, the timer is reset (so you won't get "double" updates).
1) Add the following XML namespaces:

xmlns:i="clr-namespace:System.Windows.Interactivity;assembly=System.Windows.Interactiv
ity"
xmlns:catel="http://catel.codeplex.com"

2) Use the following definition. This example will delay the update of the SelectedItem binding with 100 milliseconds:

<ListBox x:Name="listBox" ItemsSource="{Binding PersonCollection}"


SelectedItem="{Binding SelectedPerson}">
<i:Interaction.Behaviors>
<catel:DelayBindingUpdate PropertyName="SelectedItem" UpdateDelay="100" />
</i:Interaction.Behaviors>
</ListBox>

DoubleClickToCommand
Lots of times, a developer needs to handle a double click event. However, somehow the Silverlight team thought that double click had no priority
at all. Luckily, Catel offers the solution by providing the DoubleClickToCommand trigger. This trigger allows a developer to track a double click on
any FrameworkElement and respond to that using a command.
1) Add the following XML namespaces:

xmlns:i="clr-namespace:System.Windows.Interactivity;assembly=System.Windows.Interactiv
ity"
xmlns:catel="http://catel.codeplex.com"

2) Use the following definition. This example will invoke the Edit command of the view model when the item is double clicked):

<ListBox x:Name="listBox" ItemsSource="{Binding PersonCollection}"


SelectedItem="{Binding SelectedPerson}">
<ListBox.ItemTemplate>
<DataTemplate>
<Grid>
<i:Interaction.Behaviors>
<catel:DoubleClickToCommand Command="{Binding ElementName=listBox,
Path=DataContext.Edit}" />
</i:Interaction.Behaviors>
<StackPanel Orientation="Horizontal">
<Label Content="{Binding FirstName}" />
<Label Content="{Binding MiddleName}" />
<Label Content="{Binding LastName}" />
</StackPanel>
</Grid>
</DataTemplate>
</ListBox.ItemTemplate>
</ListBox>

The trigger contains an additional property AutoFixListBoxItemTemplate which is set to true by default to easily allow the addition of a double click
event to a ListBox. The item template must contain a grid as a base like shown above.
This behavior also supports a constructor that accepts an Action. This way, an anonymous delegate can be executed when the
behavior is created in code

EventToCommand
Almost every respectable MVVM framework supports the EventToCommand trigger. It is a trigger that allows a an event to be turned into a
command. This way, you never have to manually add event handlers, search for the view model in the code-behind and then call the right
command.
The usage is really simple, but requires the System.Windows.Interactivity.dll reference (ships with Catel). The example below shows how to add a
trigger for the double click of a ListBox.
1) Add the following XML namespaces:

xmlns:i="clr-namespace:System.Windows.Interactivity;assembly=System.Windows.Interactiv
ity"
xmlns:catel="http://catel.codeplex.com"

2) Use the following definition. This example will invoke the Edit command of the view model):

<ListBox ItemsSource="{Binding PersonCollection}" SelectedItem="{Binding


SelectedPerson}">
<i:Interaction.Triggers>
<i:EventTrigger EventName="MouseDoubleClick">
<catel:EventToCommand Command="{Binding Edit}"
DisableAssociatedObjectOnCannotExecute="False" />
</i:EventTrigger>
</i:Interaction.Triggers>
<ListBox.ItemTemplate>
<DataTemplate>
<StackPanel Orientation="Horizontal">
<Label Content="{Binding FirstName}" />
<Label Content="{Binding MiddleName}" />
<Label Content="{Binding LastName}" />
</StackPanel>
</DataTemplate>
</ListBox.ItemTemplate>
</ListBox>

If you want to use parameters (in the case of this example, get the MouseDoubleClick event args, set PassEventArgsToCommand to true:

<Commands:EventToCommand Command="{Binding Edit}"


DisableAssociatedObjectOnCannotExecute="False" PassEventArgsToCommand="True" />

Then, in the view model, you can even make the command "type-safe":

/// <summary>
/// Gets the Edit command.
/// </summary>
public Command<MouseEventArgs> Edit { get; private set; }
// TODO: Move code below to constructor
Edit = new Command<MouseEventArgs>(OnEditExecute, OnEditCanExecute);
// TODO: Move code above to constructor
/// <summary>
/// Method to check whether the Edit command can be executed.
/// </summary>
private bool OnEditCanExecute(MouseEventArgs e)
{
return true;
}
/// <summary>
/// Method to invoke when the Edit command is executed.
/// </summary>
private void OnEditExecute(MouseEventArgs e)
{
// TODO: Handle command logic here
}

Focus
To set the focus on a UI element, one must write code in the code-behind. With the Focus behavior, this is no longer necessary. This behavior
sets the focus only once on the first time the associated object is loaded.
Add the following XML namespaces:

xmlns:i="clr-namespace:System.Windows.Interactivity;assembly=System.Windows.Interactiv
ity"
xmlns:catel="http://catel.codeplex.com"

Focus when the control is loaded


The easiest and default method is to set the focus when the associated control is loaded. In WPF, this is immediately when the control is focused.
In Silverlight, there is a delay of 400 milliseconds by default, otherwise the focus is not set correctly.

<ListBox ItemsSource="{Binding PersonCollection}" SelectedItem="{Binding


SelectedPerson}">
<i:Interaction.Behaviors>
<catel:Focus />
</i:Interaction.Behaviors>
</ListBox>

In Silverlight, simply calling Focus() on the associated object is not enough. Therefore, the focus is set with a timer with a default delay
of 500 milliseconds. This is customizable via the FocusDelay property

Focus when an event occurs


It is possible to set the focus when a specific event occurs. For example, when the layout root gets a MouseEnter event, the focus must be set on
a specific control. This can be done via the following code:

<ListBox ItemsSource="{Binding PersonCollection}" SelectedItem="{Binding


SelectedPerson}">
<i:Interaction.Behaviors>
<catel:Focus FocusMoment="Event" Source="{Binding ElementName=layoutRoot}"
EventName="MouseEnter" />
</i:Interaction.Behaviors>
</ListBox>

If you are using Silverlight, and you don't want the default delay of 500 milliseconds, make sure to explicitly set it to 0

Focus when a property changes


It is possible to set the focus when a specific property changes. For example, when a value is set, the focus must move on to a new control. This
can be done via the following code:

<ListBox ItemsSource="{Binding PersonCollection}" SelectedItem="{Binding


SelectedPerson}">
<i:Interaction.Behaviors>
<catel:Focus FocusMoment="PropertyChanged" Source="{Binding }"
PropertyName="MyProperty" />
</i:Interaction.Behaviors>
</ListBox>

If you are using Silverlight, and you don't want the default delay of 500 milliseconds, make sure to explicitly set it to 0

FocusFirstControl
The Focus behavior is very powerful, but sometimes you just need to focus the first control on a window or control. This can be done by using the
FocusFirstControl behavior instead. This behavior will focus the first control on a window or control and has only one property: FocusParentFirst.
Add the following XML namespaces:

xmlns:i="clr-namespace:System.Windows.Interactivity;assembly=System.Windows.Interactiv
ity"
xmlns:catel="http://catel.codeplex.com"

Focus when the control is loaded


The easiest and default method is to focus the first control. The parent is also focused by default (just in case if it doesn't have any focus):

<Window ...>
<i:Interaction.Behaviors>
<catel:FocusFirstControl />
</i:Interaction.Behaviors>
</Window>

FocusOnKeyPress
Sometimes you need to handle a key press and then set the focus on an element.
1) Add the following XML namespaces:

xmlns:i="clr-namespace:System.Windows.Interactivity;assembly=System.Windows.Interactiv
ity"
xmlns:catel="http://catel.codeplex.com"

2) Use the following definition:

<TextBox x:Name="textBox">
<i:Interaction.Behaviors>
<catel:FocusOnKeyPress Key="F" Modifiers="Ctrl" />
</i:Interaction.Behaviors>
</ListBox>

HideUntilViewModelLoaded
The HideUntilViewModelLoaded hides (Visibility.Collapsed) any view model container (IViewModelContainer) when it does not have a valid view
model. This is a great way to hide lazy-loaded views that should only be visible when they contain an actual view model.
Add the following XML namespaces:

xmlns:i="clr-namespace:System.Windows.Interactivity;assembly=System.Windows.Interactiv
ity"
xmlns:catel="http://catel.codeplex.com"

Focus when the control is loaded


The easiest and default method is to focus the first control. The parent is also focused by default (just in case if it doesn't have any focus):

<local:MyUserControl ...>
<i:Interaction.Behaviors>
<catel:HideUntilViewModelLoaded />
</i:Interaction.Behaviors>
</local:MyUserControl>

KeyPressToCommand
Sometimes you need to handle a key press and convert it to a command. An excellent example is a ListBox that should respond to an Ctrl + Enter
key press.

1) Add the following XML namespaces:

xmlns:i="clr-namespace:System.Windows.Interactivity;assembly=System.Windows.Interactiv
ity"
xmlns:catel="http://catel.codeplex.com"

2) Use the following definition:

<ListBox x:Name="listBox" ItemsSource="{Binding PersonCollection}"


SelectedItem="{Binding SelectedPerson}">
<i:Interaction.Behaviors>
<catel:KeyPressToCommand Command="{Binding MyCommand}" Key="Enter"
Modifiers="Ctrl" />
</i:Interaction.Behaviors>
</ListBox>

MouseInfo
Silverlight is missing a lot. One of the things that is missing are decent mouse events such as IsMouseOver. To implement such behavior, the
MouseInfo behavior is created. It supports several mouse events (even in Silverlight!).

OnMouseOver
1) Add the following XML namespaces:

xmlns:i="clr-namespace:System.Windows.Interactivity;assembly=System.Windows.Interactiv
ity"
xmlns:catel="http://catel.codeplex.com"

2) Use the following definition:

<ListBox ItemsSource="{Binding PersonCollection}" SelectedItem="{Binding


SelectedPerson}">
<i:Interaction.Behaviors>
<catel:MouseInfo x:Name="personCollectionMouseInfo" />
</i:Interaction.Behaviors>
</ListBox>

3) Now, it is easy to bind to the mouse information like this (textblock will become visible when the listbox is hovered):

<TextBlock Visibility="{Binding ElementName=personCollectionMouseInfo,


Path=IsMouseOver, Converter={StaticResource BooleanToCollapsingVisibilityConverter},
ConverterParameter=false}" Text="Hovering listbox" />

Navigate
Note that this behavior is only available for WPF

The Hyperlink control in WPF is very powerful, but it is hard to make them work outside pages.

Add the following XML namespaces:

xmlns:i="clr-namespace:System.Windows.Interactivity;assembly=System.Windows.Interactiv
ity"
xmlns:catel="http://catel.codeplex.com"

To execute the NavigateUrl, simply use the behavior as shown below:

<TextBlock>
<Hyperlink NavigateUri="http://catel.codeplex.com">
<i:Interaction.Behaviors>
<catel:Navigate />
</i:Interaction.Behaviors>
<TextBlock Text="The best MVVM Framework" />
</Hyperlink>
</TextBlock>

Another alternative is to use the LinkLabel control

NumericTextBox
The NumericTextBox behavior makes it easy to allow specific numeric input on a TextBox.
1) Add the following XML namespaces:

xmlns:i="clr-namespace:System.Windows.Interactivity;assembly=System.Windows.Interactiv
ity"
xmlns:catel="http://catel.codeplex.com"

2) Use the following definition:

<TextBox Text={Binding Amount}">


<i:Interaction.Behaviors>
<catel:NumericTextBox />
</i:Interaction.Behaviors>
</TextBox>

Use the properties on the behavior to customize the behavior to your needs

SelectTextOnFocus
The SelectTextOnFocus behavior makes it easy to select all text when a TextBox receives the focus.
1) Add the following XML namespaces:

xmlns:i="clr-namespace:System.Windows.Interactivity;assembly=System.Windows.Interactiv
ity"
xmlns:catel="http://catel.codeplex.com"

2) Use the following definition:

<TextBox Text={Binding Amount}">


<i:Interaction.Behaviors>
<catel:SelectTextOnFocus />
</i:Interaction.Behaviors>
</TextBox>

UpdateBindingOnPasswordChanged
The UpdateBindingOnPasswordChanged is a very useful behavior which allows to bind the Password property of the PasswordBox Control. Use
it, it's really simple.

Usage in WPF
1) Add the following XML namespaces:

xmlns:i="clr-namespace:System.Windows.Interactivity;assembly=System.Windows.Interactiv
ity"
xmlns:catel="http://catel.codeplex.com"

2) Use the following definition:

<PasswordBox>
<i:Interaction.Behaviors>
<catel:UpdateBindingOnPasswordChanged Password="{Binding Password,
Mode=TwoWay}" />
</i:Interaction.Behaviors>
</PasswordBox>

Usage in Silverlight
1) Add the following XML namespaces:

xmlns:i="clr-namespace:System.Windows.Interactivity;assembly=System.Windows.Interactiv
ity"
xmlns:catel="http://catel.codeplex.com"

2) Use the following definition:

<PasswordBox Password="{Binding Password, Mode=TwoWay}">


<i:Interaction.Behaviors>
<catel:UpdateBindingOnPasswordChanged />
</i:Interaction.Behaviors>
</PasswordBox>

UpdateBindingOnTextChanged
The UpdateBindingOnTextChange is a very useful behavior which allows to delay a binding update on the TextChanged event of a TextBox. This
way, it is possible to implement search boxes that only start a search after a specific time when no new key presses have occurred. For example,

when a user types a new search string, and the user doesn't enter a new key for 500 ms, the binding is updated.
1) Add the following XML namespaces:

xmlns:i="clr-namespace:System.Windows.Interactivity;assembly=System.Windows.Interactiv
ity"
xmlns:catel="http://catel.codeplex.com"

2) Use the following definition. This example will update the binding after 500 ms where normally it would only occur when the user tabs out of the
TextBox:

<TextBox Text="{Binding SearchParam, Mode=TwoWay}">


<i:Interaction.Behaviors>
<catel:UpdateBindingOnTextChanged UpdateDelay="500" />
</i:Interaction.Behaviors>
</TextBox>

Bindings
By default, all XAML technologies support binding out of the box. However other platforms (such as Xamarin.Android and Xamarin.iOS) don't.
Catel provides a binding system for these platforms, which is described in this topic.
Note that although the binding system in Catel is very powerful, it will never be as flexible / powerful as the native XAML binding
system. We do try to support as many features as possible though.
For examples, check out the following pages:
Property bindings
Command bindings

Binding system explained


The binding system consists of several classes. Below is an architectural overview.

As the image shows, each view will have their own BindingContext. A BindingContext contains all the bindings currently available in the view and
allows adding / removing bindings dynamically when required. As soon as a major change occurs (such as a new view model), a new BindingCon
text will be created and the old one will be cleaned up. The views in Catel will automatically take care of the BindingContext initialization and
lifetime management.
Each Binding is a mapping from source to target. It also allows the specification of a converter like available in the XAML platforms. Each Binding
also contains several BindingParty objects. The default value for BindingMode is BindingMode.TwoWay.
A BindingParty is an object that will take care of watching the source or target of the binding and inform the binding when a value has been
changed. The binding parties are considered equal and contain the same logic for both the source and target of the binding.
All bindings must be initialized in the AddBindings method that is available on all views provided by Catel.

Property bindings
Property bindings are very important in the MVVM pattern. The binding system in Catel will automatically map properties when the binding system
is used.
Binding properties one way
Android
iOS
Binding properties two way
Android
iOS
Binding properties with a converter
Android
iOS

Binding properties one way


To bind properties one way, use the code below.

Android

protected override void AddBindings(BindingContext bindingContext, IViewModel


viewModel)
{
var vm = (MainViewModel) viewModel;
bindingContext.AddBinding(() => vm.FirstName, () => _firstNameEditText.Text,
BindingMode.OneWay);
}

iOS
iOS not yet documented

Binding properties two way


To bind properties two way, use the code below.

Android

protected override void AddBindings(BindingContext bindingContext, IViewModel


viewModel)
{
var vm = (MainViewModel) viewModel;
bindingContext.AddBinding(() => vm.FirstName, () =>
_firstNameEditText.Text).AddTargetEvent("TextChanged");
}

Note that you need to use the AddTargetEvent to allow two way binding in Android

iOS
iOS not yet documented

Binding properties with a converter


Converters are a well-known topic in MVVM. Catel supports the use of converters in the binding system. The example below will convert an
integer (vm.Counter) to a string with a format to "{0} clicks!". The converter will automatically be instantiated using the TypeFactory. Note that
using converters in Catel support both TwoWay bindings and ConverterHelper.UnsetValue to prevent any changes in the binding system.

Android

protected override void AddBindings(BindingContext bindingContext, IViewModel


viewModel)
{
var vm = (MainViewModel) viewModel;
bindingContext.AddBindingWithConverter<ClicksConverter>(() => vm.Counter, () =>
_testButton.Text, BindingMode.OneWay);
}

iOS
iOS not yet documented

Command bindings
Catel will automatically hook up the CanExecute of the command to the Enabled property of the element it is bound to. A command binding is
always bound to an event of a specific element as shown below.

Android

protected override void AddBindings(BindingContext bindingContext, IViewModel


viewModel)
{
var vm = (MainViewModel) viewModel;
bindingContext.AddCommandBinding(_testButton, "Click", vm.RunCommand);
}

iOS
iOS not yet documented

Commands & events


Commanding is supported by Catel. Catel supports Command classes, which is also known as RelayCommand or DelegateCommand in other
frameworks. Defining a command on a view model is very easy, as you can see in the code below:

// TODO: Move code below to constructor


Edit = new Command(OnEditExecute, OnEditCanExecute);
// TODO: Move code above to constructor
/// <summary>
/// Gets the Edit command.
/// </summary>
public Command Edit { get; private set; }
/// <summary>
/// Method to check whether the Edit command can be executed.
/// </summary>
private bool OnEditCanExecute()
{
return true;
}
/// <summary>
/// Method to invoke when the Edit command is executed.
/// </summary>
private void OnEditExecute()
{
// TODO: Handle command logic here
}

There are some people who dont like the ICommand implementations. For example, Caliburn (Micro) uses convention and does not require the
creation of a command. There are a few downsides for that:
It requires you to make sure the name of the control is the same as the method;
It is not clear that it is actually a command if you are not fully familiar with the conventions;
The methods need to be public (otherwise, how are you going to invoke the commands during unit tests?), which make them freely
available (and thats not something we like);
You will always have to invoke CanExecute yourself again in Execute, because you have no guarantee that the source of Execute is
actually the convention mapping;
There is no way to manually refresh the CanExecute state on the bound controls.
For more information, see:
Commands
CommandManager and command containers (Application-wide commands)
Asynchronous commands
Commands authentication
Hooking a command to validation automatically

Commands
Commands are supported in Catel. The base class for commands is Command.

Code snippets
vmcommand - declare a command on a view model
vmcommandwithcanexecute - declare a command with support for CanExecute on a view model

Explanation
To implement commands, and still be able to unit test the view models, a separate command is introduced. This command allows a developer to
implement a command that can be invoked both via code (unit testing) and UI.
There is one real Command class: Command<TCanExecuteParameter, TExecuteParameter>
The TCanExecuteParameter is the parameter that is passed to the CanExecute of the command, ands saves the developer from casting the

object (as in the interface ICommand to a typed object). The same goes for TExecuteParameter which makes the Execute of the command typed.
There are also several wrappers available in case object is used as type parameter:
Command<TExecuteParameter> (wraps Command<TCanExecuteParameter, TExecuteParameter> with object for TCanExecuteParamet
er)
Command (wraps Command<TExecuteParameter> with object for TExecuteParameter)

Examples
Code:

private readonly IMessageService _messageService;


public void MyViewModel(IMessageService messageService)
{
Argument.IsNotNull(() => messageService);
_messageService = messageService;
// Add commands
MyAction = new Command(MyAction_Execute);
}
/// <summary>
/// Gets the MyAction command.
/// </summary>
public Command MyAction { get; private set; }
/// <summary>
/// Method to invoke when the MyAction command is executed.
/// </summary>
/// <param name="parameter">The parameter of the command.</param>
private void MyAction_Execute(object parameter)
{
// Show message box
_messageService.ShowInfo("My action in MVVM");
}

Xaml (assuming that the view model is set as datacontext):

<Button Content="Click me" Command="{Binding MyCommand}" />

CommandManager and command containers (Application-wide commands)


Most commands are registered per view and available per view model. Some commands (such as commands on a Ribbon or Toolbar) are
application-wide. Catel supports both types, and this part of the documentation explains how to use the ICommandManager to work with
application-wide commands such as Refresh with a key bound to F5.
CommandManager
Creating application-wide commands
Registering a custom command
Using application-wide commands in xaml
Command containers
Creating a command container
Registering a command container
Command definitions
Registering the command container

CommandManager

There is no generic way to specify application-wide commands in WPF and Silverlight. To overcome this issue, Catel introduces the CommandMa
nager. This manager allows to create commands which are hosted by the CommandManager. The commands on the command manager can be
created with input gestures (on both WPF and Silverlight). Once a view model wants to hook into a specific command, it only has to register the
view model command with the application-wide command.
Note that application-wide commands by default are only available on the main window of an application. To support this on other
windows, add the following code in the constructor of a window:

public class SomeWindow


{
private readonly CommandManagerWrapper _commandManagerWrapper;
public SomeWindow()
{
InitializeComponent();
_commandManagerWrapper = new CommandManagerWrapper(this);
}
}

Creating application-wide commands


To create application-wide commands, one must resolve the ICommandManager from the DependencyResolver and create the command:

var dependencyResolver = IoCConfiguration.DefaultDependencyResolver;


var commandManager = dependencyResolver.Resolve<ICommandManager>();
commandManager.CreateCommand("Refresh", new InputGesture(Key.F5));

It is recommended to put all the command creation in a single place so they are easily manageable.

Registering a custom command


When a view model wants to use application-wide specific commands, the only thing it has to do is register the command in the CommandManag
er.

public class CommandSubscribingViewModel : ViewModelBase


{
private readonly IMessageService _messageService;
public CommandSubscribingViewModel(ICommandManager commandManager, IMessageService
messageService)
{
Argument.IsNotNull(() => commandManager);
Argument.IsNotNull(() => messageService);
_messageService = messageService;
ExampleCommand = new Command(OnExampleCommandExecute);
commandManager.RegisterCommand("Refresh", ExampleCommand, this);
}
public Command ExampleCommand { get; private set; }
private void OnExampleCommandExecute()
{
_messageService.Show("Application-wide command executed");
}
}

Using application-wide commands in xaml


To make it easy to bind to application-wide commands, Catel provides the CommandManagerBinding markup extension for WPF and Silverlight.
To bind to commands in xaml, use the following code:

<Ribbon catel:StackGrid.ColumnSpan="4">
<RibbonTab Header="Home" KeyTip="H" >
<RibbonGroup Header="Example commands">
<RibbonButton Command="{catel:CommandManagerBinding Refresh}"
LargeImageSource="..\Resources\Images\Refresh.png"
Label="Refresh" KeyTip="F5" />
</RibbonGroup>
</RibbonTab>
</Ribbon>

As the code shows, the CommandManagerBinding extension automatically resolves the Refresh command from the CommandManager.

Command containers
When implementing a ribbon or any menu structure inside an application can result in a very complex view model containing all the commands.
Catel solves this issue by implementing so-called command containers. These are containers that have only 1 purpose: contain a command so
the logic can easily be viewed / edited and the commands will be available during the whole lifetime of the app. Internally command containers
use the ICommandManager to register commands, so the ICommandManager is still responsible for the commands.

Creating a command container


Creating a command container is very simple. It can be done by creating a class deriving from CommandContainerBase as shown in the example
below:

public class ApplicationAboutCommandContainer : CommandContainerBase


{
private readonly IAboutService _aboutService;
public ApplicationAboutCommandContainer(ICommandManager commandManager, IAboutService
aboutService)
: base(Commands.Application.About, commandManager)
{
Argument.IsNotNull(() => aboutService);
_aboutService = aboutService;
}
protected override Execute(object parameter)
{
_aboutService.ShowAbout();
}
}

As you can see the implementation is very clean and won't pollute any other view models.

Registering a command container


If you don't use the extension methods below, you must register the command container inside the service locator and register the command
inside the ICommandManager. To make this process easier, use a definition file and the code below.

Command definitions
To make it very easy to register new commands, Catel uses naming conventions and extension methods. The name of the command (for
example, About must be a constant on the command definitions class). If the command definition also contains a <CommandName>InputGesture,
in this case AboutInputGesture, it will use that input gesture as a default to register the command with.

public static class Commands


{
public static class Application
{
public const string Exit = "Application.Exit";
public static readonly InputGesture ExitInputGesture = new InputGesture(Key.F4,
ModifierKeys.Alt);
public const string About = "Application.About";
public static readonly InputGesture AboutInputGesture = new InputGesture(Key.F1);
}
public static class OtherPartOfApplication
{
public const string SomeCommand = "OtherPartOfApplication.SomeCommand";
public static readonly InputGesture SomeCommandInputGesture = null;
}
}

It is recommended to keep a well formed structure for your command definitions to keep them manageable, even in very large
applications

Registering the command container

Once you have the command container and the command definition (command name and the input gesture), it is time to register the command
container:

var commandManager = ServiceLocator.Default.ResolveType<ICommandManager>();


commandManager.CreateCommandWithGesture(typeof(Commands.Application), "About");

This will keep the command registration very readable and maintainable when using a lot of commands:

var commandManager = ServiceLocator.Default.ResolveType<ICommandManager>();


commandManager.CreateCommandWithGesture(typeof(AppCommands.Application), "Exit");
commandManager.CreateCommandWithGesture(typeof(AppCommands.Application), "About");
commandManager.CreateCommandWithGesture(typeof(Commands.Project),
commandManager.CreateCommandWithGesture(typeof(Commands.Project),
commandManager.CreateCommandWithGesture(typeof(Commands.Project),
commandManager.CreateCommandWithGesture(typeof(Commands.Project),

"Open");
"Save");
"SaveAs");
"Refresh");

commandManager.CreateCommandWithGesture(typeof(AppCommands.Settings),
"ToggleTooltips");
commandManager.CreateCommandWithGesture(typeof(AppCommands.Settings),
"ToggleQuickFilters");
commandManager.CreateCommandWithGesture(typeof(ExtensibilityCommands.Application),
"Extensions");
commandManager.CreateCommandWithGesture(typeof(ExtensibilityCommands.Application),
"ExtensionsSettings");

Asynchronous commands
Commands in MVVM are a very precious good. Actually, MVVM can't exist without them because they allow a developer to bind to a method
(that's actually all an ICommand implementation is). However, sometimes it is required to create asynchronous commands. Starting with Catel
3.1, the AsynchronousCommand is introduced.
With the AsynchronousCommand, it is possible to create a command that executes a method in the background without blocking the UI thread. It
is possible to report progress to the UI thread.
Want to use async methods? Use the TaskCommand

Creating the command


The AsynchronousCommand can be used the same as the the regular Command class. The command must be constructed like this:

CancelableAsyncCommand = new AsynchronousCommand(OnCancelableAsyncCommand, () =>


!CancelableAsyncCommand.IsExecuting);

The second parameter is the CanExecute delegate, and this example does not allow multiple executions of the same command at the same time.

Running the command


Running the command is the same as the regular Command class. The view can simply bind to the command like the code below:

<Button Command="{Binding CancelableAsyncCommand}" Content="Execute Command" />

Canceling the command


Last but not least, the cool thing about the AsynchronousCommand is that it can complete in two ways. It either completes the method by itself, or
it is canceled from the outside. To cancel a running command, two steps must be accomplished:
1. Bind to the CancelCommand property of the AsynchronousCommand:

<Button Command="{Binding CancelableAsyncCommand.CancelCommand}" Content="Cancel


Command" />

2. Make sure the execute action checks the ShouldCancel property like in the example below:

private void OnCancelableAsyncCommand()


{
for (var i = 1; i <= 100; i++)
{
if (CancelableAsyncCommand.ShouldCancel)
{
// If we should cancel, break out of the loop
break;
}
Thread.Sleep(100);
}
}

Note that this example looks stupid and you should not use Thread.Sleep, but this is just for the sake of simplicity and the example

Reporting progress
During the execution of a command, it is possible to report progress back to the main thread. This can done by using the ReportProgress method.
All code inside the ReportProgress will be executed in the UI thread:

private void OnCancelableAsyncCommand()


{
for (var i = 1; i <= 100; i++)
{
if (CancelableAsyncCommand.ShouldCancel)
{
// If we should cancel, break out of the loop
break;
}
var i1 = i;
CancelableAsyncCommand.ReportProgress(() =>
Messages.Add(i1.ToString(CultureInfo.InvariantCulture)));
Thread.Sleep(100);
}
}

Commands authentication
One of the questions an MVVM developer faces is how to control the executation state of a command by role or user authentication method. Catel
offers an out-of-the-box solution for this problem to check the CanExecute state of the commands in the UI.
It is very important that this way of disabling commands is only used to easy the development of consistent user interfaces. It cannot
replace the actual check whether a user can or cannot modify data. The actual and final responsibility still lays at the business layer.

Tagging your commands


To know whether a specific user can execute a command, you need to be able to distinguish one command from another. The ICatelCommand in
terface (which derives from ICommand) providers a Tag property that allows you to tag the command with any object that fits your needs. In one
application, commands might be distinguished using strings, other applications use integer ID's.
A tag must be set in the constructor of a command and cannot be changed:

Edit = new Command(OnEditExecute, OnEditCanExecute, "editCommand");

IAuthenticationProvider
The IAuthenticationProvider is a provider that needs to be implemented per application and must be registered in the IoC container. Below is the
interface definition:

/// <summary>
/// Interface to allow an authentication mechanism to control the CanExecute state of
a command.
/// </summary>
public interface IAuthenticationProvider
{
/// <summary>
/// Determines whether the specified <paramref name="command"/> can be executed.
The class implementing this interface
/// can use any required method to check the command.
/// <para />
/// It is recommended to use the <see cref="ICatelCommand.Tag"/> property to
identify a command.
/// </summary>
/// <param name="command">The command that is requested.</param>
/// <param name="commandParameter">The command parameter.</param>
/// <returns>
///
<c>true</c> if this instance [can command be executed] the specified
command; otherwise, <c>false</c>.
/// </returns>
/// <remarks>
/// The <c>CanExecute</c> state of a command is queried a lot. The command itself
does not cache any results because
/// it is not aware of role or identity changes. If caching is required, this must
be implemented in the class implementing
/// the <see cref="ICommandAuthenticationProvider"/> interface.
/// </remarks>
bool CanCommandBeExecuted(ICatelCommand command, object commandParameter);
}

To register a custom implementation of the command authentication provider, use the code below:

Catel.IoC.ServiceLocator.Instance.RegisterType<IAuthenticationProvider,
RoleAuthenticationProvider>();

The code above registers a custom made command authentication provider that checks whether a specific role can execute the command.
Catel checks whether an IAuthenticationProvider is registered. If not, the way commands are handled is not affected in any way. If there
is an IAuthenticationProvider available, the CanExecute state is checked, even when there is no custom CanExecute implemented.

Hooking a command to validation automatically


It is possible to hook the CanExecute of a Command to the IValidationSummary automatically. This way, there is no need to check for errors
manually in the CanExecute method. The example below first adds a validation summary to a view model to get the validation result. Then, it uses
this validation summary to automatically determine whether a command can be executed.
1. Add validation to a person view model (note how the validation adds the tag PersonValidation to a validation):

/// <summary>
/// Validates the field values of this object. Override this method to enable
/// validation of field values.
/// </summary>
/// <param name="validationResults">The validation results, add additional results to
this list.</param>
protected override void
ValidateFields(System.Collections.Generic.List<IFieldValidationResult>
validationResults)
{
if (string.IsNullOrEmpty(FirstName))
{
validationResults.Add(FieldValidationResult.CreateErrorWithTag(FirstNameProperty,
"First name cannot be empty", "PersonValidation"));
}
if (string.IsNullOrEmpty(LastName))
{
validationResults.Add(FieldValidationResult.CreateErrorWithTag(LastNameProperty, "Last
name cannot be empty", "PersonValidation"));
}
}

2. Add a property to the view model containing the validation summary using the ValidationToViewModel attribute.

[ValidationToViewModel(Tag = "PersonValidation")]
public IValidationSummary PersonValidationSummary { get; set; }

3. Define a command on the view model:

/// <summary>
/// Gets the Save command.
/// </summary>
public Command Save { get; private set; }
/// <summary>
/// Method to invoke when the Save command is executed.
/// </summary>
private void OnSaveExecute()
{
// TODO: Handle command logic here
}

4. Create the command that automatically uses the validation summary using the CommandHelper class:

Save = CommandHelper.CreateCommand(OnSaveExecute, () => PersonValidationSummary);

With this example, the Save command on the view model can only be executed when there are no errors with the PersonValidation tag.

Converters

In MVVM, there will be some point where you will need to use converters. Most of these converters are used in any project, so we have decided
to add them to Catel. Below is a list of converters and a short description what they are used for.
Note that the behavior of most converters can be inverted by using the ConverterParameter

Linking converters
Available converters

Linking converters
It is possible to link converters. To link converters, simply set the Link property in xaml:

<catel:NullableValueConverter x:Key="NullableValueConverter" />


<catel:BooleanToVisibilityConverter>
<catel:BooleanToVisibilityConverter.Link>
<code:NullToBoolConverter Link="{StaticResource NullableValueConverter}" />
</catel:BooleanToVisibilityConverter.Link>
</catel:BooleanToVisibilityConverter>

Available converters
Name

Description

AreEqualMultiValueConverter

Converts the comparison of 2 values to a boolean

BooleanToCollapsingVisibilityConverter

Convert from bool to Visibility and back.

BooleanToHidingVisibilityConverter

Convert from bool to Visibility and back.

BooleanToGrayscaleConverter

Converts a boolean to a grayscale saturation value. If the input is false, this converter will return 0,
otherwise 1.

BooleanToOppositeBooleanConverter

Convert a boolean to it's inverted value.

BooleanToTextConverter

Converts a boolean value to text, for example "yes" and "no", or "x" and " ".

BooleanToCollapsingVisibilityConverter

Convert from bool to Visibility and back. True returns Visibility.Visible, False returns Visibility.Collapsed.

BooleanToHidingVisibilityConverter

Convert from bool to Visibility and back. True returns Visibility.Visible, False returns Visibility.Hidden.

ColorToBrushConverter

Converts a color value to a brush and vice versa.

ContainsItemsConverter

Convert the count of an ICollection or IEnumerable to true or false, depending on whether the instance
contains items.
For an instance which implements ICollection, check Count > 0
For an instance which implements IEnumerable, if the instance can be Enumerated.

CountCollapsedConverter

Converts the 'count' of ICollection, string, long, int or short to Visibility.Visible or Visibility.Collapsed
Visible means: ICollection.Count > 0, String.Length > 0 or long, int, short > 0.

CountHiddenConverter

Converts the 'count' of ICollection, string, long, int or short to Visibility.Visible or Visibility.Hidden
Visible means: ICollection.Count > 0, String.Length > 0 or long, int, short > 0.

EmptyStringToCollapsingVisibilityConverter

Converts a string to Visibility. If the string is empty, it will return Visibility.Collapsed.

EmptyStringToHidingVisibilityConverter

Converts a string to Visibility. If the string is empty, it will return Visibility.Hidden.

EnumToCollapsingVisibilityConverter

Converts an enum to Visibility. The allowed values must be defined inside the ConverterParameter as
shown below (element will be visible when MyEnumValue is Enum1 or Enum3):

<TextBlock Visibility="{Binding MyEnumValue,


Converter={converters:EnumToCollapsingVisibilityConverter},
ConverterParameter=Enum1|Enum3}"/>

If the ConverterParameter starts with !, the element will not be visible for the specified enum
values

EnumToHidingVisibilityConverter

Converts an enum to Visibility. The allowed values must be defined inside the ConverterParameter as
shown below (element will be visible when MyEnumValue is Enum1 or Enum3):

<TextBlock Visibility="{Binding MyEnumValue,


Converter={converters:EnumToHidingVisibilityConverter},
ConverterParameter=Enum1|Enum3}"/>

If the ConverterParameter starts with !, the element will not be visible for the specified enum
values

FormattingConverter

Formats the value using the format string provided in the ConverterParameter

IsSelectedConverter

Converts a selected value to either true of false.

IsSelectedValueConverter

Converts a selected value to either true of false.

GetFirstValidationErrorConverter

Converts a collection containing ValidationError objects to return the first error or an empty string in case
there are no errors.

IsSelectedConverter

Converts a selected value to either true or false. Useful whena mutually exclusive selection must be
made.

IntToStringConverter

Converts an inteteger to a string and back.

MethodToValueConverter

Converts the result of a method to a value. This makes it possible to bind to a method. See Source

MultiplyConverter

Calculates the product of given value and factor in parameter.

NullableValueConverter

Converts a value to a representive value for nullable.

PlatformToBooleanConverter

Converts a value of KnownPlatforms to a boolean based on the current platform. This makes it possible
to enable / disable functionality in shared projects based on the target platform.

ReferenceToBooleanConverter

Converts a reference to a boolean. If the reference is null, it will return false.

ReferenceToCollapsingVisibilityConverter

Converts a reference to Visibility. If the reference is null, it will return Visibility.Collapsed.

ReferenceToHidingVisibilityConverter

Converts a reference to Visibility. If the reference is null, it will return Visibility.Hidden.

ShortDateFormattingConverter

Converts a date to a short date and back.

StringToIntConverter

Converts string to an integer and back.

ViewModelToViewConverter

Converts a view model to a view. Great way to locate a view based on a view model inside xaml.

Designers
Lots of developers are using designers such as the built-in designer in Visual Studio 2010 or Expression Blend to design their xaml based
applications. Although you should use designers with lots of care, we strive to fully support all designers.
This part of the documentation shows the several design-time features that Catel provides.

Design-time view models


Running code at design-time

Design-time view models


Lots of developers are using designers such as the built-in designer in Visual Studio 2010 or Expression Blend to design their xaml based
applications. Although you should use designers with lots of care, we strive to fully support all designers.
Since Catel 1.3, it is possible to create design-time versions of a view model. This way, you can preview the UserControl or DataWindow impleme
ntations using example data. Since Silverlight does not support defining types in xaml, the way that the design time works is a bit different.
WPF
Silverlight & Windows Phone

WPF
To create design-time support for a data window, use the following steps:
1. Create a design time view model. Normally, this can easily be achieved by deriving a new class from the actual view-model and inject the
model. Below is an example of a design time version of a person view model:

/// <summary>
/// Design time version of the <see cref="PersonViewModel"/>.
/// </summary>
public class DesignPersonViewModel : PersonViewModel
{
/// <summary>
/// Initializes a new instance of the <see cref="DesignPersonViewModel"/> class.
/// </summary>
public DesignPersonViewModel()
: base(new Person { FirstName = "Geert", MiddleName = "van", LastName =
"Horrik", Gender = Gender.Male })
{
}
}

2. Define the type of the design time view model.

d:DataContext="{d:DesignInstance ViewModels:DesignPersonViewModel}"

If you want it to actually show demo data (instead of allowing to configure bindings), use IsDesignTimeCreatable:

d:DataContext="{d:DesignInstance ViewModels:DesignPersonViewModel,
IsDesignTimeCreatable=True}"

Full DataWindow declaration:

<catel:DataWindow x:Class="Catel.Examples.PersonApplication.UI.Windows.PersonWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:catel="http://catel.codeplex.com"
xmlns:ViewModels="clr-namespace:Catel.Examples.PersonApplication.ViewModels"
xmlns:Converters="clr-namespace:Catel.Examples.PersonApplication.Data.Converters"
xmlns:Models="clr-namespace:Catel.Examples.Models;assembly=Catel.Examples.Models"
mc:Ignorable="d"
d:DataContext="{d:DesignInstance ViewModels:DesignPersonViewModel,
IsDesignTimeCreatable=True}">

3. Example of design time data support:

Silverlight & Windows Phone


To create design-time support for a data window, use the following steps:
Although the DataWindow is not available in Windows Phone, it still shows how to add design time support

1. Create a design time view model. Normally, this can easily be achieved by deriving a new class from the actual view-model and inject the
model. Below is an example of a design time version of a person view model:

/// <summary>
/// Design time version of the <see cref="PersonViewModel"/>.
/// </summary>
public class DesignPersonViewModel : PersonViewModel
{
/// <summary>
/// Initializes a new instance of the <see cref="DesignPersonViewModel"/> class.
/// </summary>
public DesignPersonViewModel()
: base(new Person { FirstName = "Geert", MiddleName = "van", LastName =
"Horrik", Gender = Gender.Male })
{
}
}

2. Define the type of the design time view model.

d:DataContext="{d:DesignInstance ViewModels:DesignPersonViewModel}"

If you want it to actually show demo data (instead of allowing to configure bindings), use IsDesignTimeCreatable:

d:DataContext="{d:DesignInstance ViewModels:DesignPersonViewModel,
IsDesignTimeCreatable=True}"

Full DataWindow declaration:

<catel:DataWindow x:Class="Catel.Examples.Silverlight.UI.Windows.PersonWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:catel="http://catel.codeplex.com"
xmlns:ViewModels="clr-namespace:Catel.Examples.PersonApplication.ViewModels"
xmlns:Converters="clr-namespace:Catel.Examples.Silverlight.Data.Converters"
xmlns:ExampleWindows="clr-namespace:Catel.Examples.Silverlight.Views"
mc:Ignorable="d"
d:DataContext="{d:DesignInstance ViewModels:DesignPersonViewModel,
IsDesignTimeCreatable=True}">

3. Example of design time data support:

Running code at design-time


Sometimes one needs to run code during design-time. A good example is to register a custom LanguageResourceSource in the LanguageService
to show translations in the designer. Unfortunately it is not as easy as putting some code in the code-behind to get this working.
Introducing the DesignTimeCode attribute
Introducing the DesignTimeInitializer

Introducing the DesignTimeCode attribute


To allow users to run code in the designer (Visual Studio or Blend), Catel introduces the DesignTimeCodeAttribute. This is an assembly-wide
attribute which will specify the class to create at design time. This means that it is possible to create multiple attributes. Below is an example of
the usage of the attribute:

[assembly: DesignTimeCode(typeof(WpfApplication.Catel.DesignTimeLanguageService))]
[assembly: DesignTimeCode(typeof(WpfApplication.Catel.DesignTimeServiceLocator))]

When the attribute is found by Catel, it will automatically construct the types specified in the attribute. This will allow the constructor to execute
any code during design time.

Introducing the DesignTimeInitializer


The DesignTimeCodeAttribute contains the types that are constructed during design-time. Although the reflection in Catel is protected by only
checking these arguments at design-time, it cannot be guaranteed for other systems. Therefore Catel also provides the DesignTimeInitializer bas
e class. This is a base class that checks whether the type being constructed is actually running inside a design tool.
Below is an example of the usage, which registers custom language resource sources in the language service. This allows real-time updates of
the LanguageService in the designer.

public class DesignTimeLanguageService : Catel.DesignTimeInitializer


{
protected override void Initialize()
{
var dependencyResolver = this.GetDependencyResolver();
var languageService = dependencyResolver.Resolve<ILanguageService>();
languageService.CacheResults = false;
var resourcesSource = new LanguageResourceSource("WpfApplication.Catel",
"WpfApplication.Catel.Properties", "Resources");
languageService.RegisterLanguageSource(resourcesSource);
}
}

Handling application initialization parameters


Sometimes you need enable or disable some application options as the outcome / result of some initialization parameters. Typically this work is
done at the application main entry point or in a notification such as start event receiving this arguments. But its pretty dirt do all this work at the
application start. May that some application modules are actually unloaded and you dont have actually a way to disable such option or the same
argument have a different meaning cross modules.
The fact is that with Catel, you can delay the processing of such initialization parameters using the StartUpInfoProvider and make the right
interpretation of any parameter at any application point.

Using the StartUpInfoProvider


Now Catel comes with StartUpInfoProvider. This class provides the access to the initialization parameters of the application. Basically if you are in
building a NET application you can access to the command line arguments array or if you are building a Silverlight application you can access to
the initialization parameter dictionary.
The interface of this service is defined below:

/// <summary>
/// The IStartUpInfoProvider interface.
/// </summary>
public interface IStartUpInfoProvider
{
#if SILVERLIGHT
/// <summary>
/// Gets the silverlight application initialization parameters.
/// </summary>
IDictionary<string, string> InitParms { get; }
#endif
#if NET
/// <summary>
/// Gets the application command line argument.
/// </summary>
string[] Arguments { get; }
#endif
}

We are evaluating the way to automatically map the command line array into a meaning full strong typed options and switches map or
dictionary to direct access to command line options

Advantages of the StartUpInfoProvider


Think that you want to test or debug an application that require analyses the initialization parameters to work. Typically you have options to modify
this argument in a configuration windows of the visual studio or in the test page of the Silverlight application.
By default, there no easy way to mock or fake the initialization parameters for an application. Think about it:

Process.GetCurrentProcess().StartInfo.Arguments

or

Application.Current.Host.InitParams

Such thing are actually unmockable. But now, thanks to Catel, you can do it registering fakes or mock instances into the service locator. Just like
this:

var startUpInfoProviderMock = new Moq<IStartUpInfoProvider>();

....
ServiceLocator.Default.RegisterInstance<IStartUpInfoProvider>(startUpInfoProviderMock.
Object);

Locators and naming conventions


Catel contains several "locators". These locators are services that allow a developer to resolve types, such as view models, based on another
type.
ViewModelLocator
ViewLocator
UrlLocator
Naming conventions

ViewModelLocator
Starting with Catel 3.0, there are several ways to hook up a view model to the view. When a view is constructed, an MVVM behavior is added to
the view. Thanks to these MVVM behaviors, it is possible to use exactly the same logic on 3rd party controls.
Note that the while using the conventions, magic words such as "View", "Control", "UserControl", "Window" and "Page" will be stripped
from the view name while locating the view model type

Resolving by naming convention


If the GetViewModelType method returns null (which is the default behavior), the view will resolve the IViewModelLocator from the ServiceLocator
. Then it will use the ResolveViewModel method to resolve the view model based on the type of the view.
For example, the following view:

Catel.Examples.Views.MyView

will be resolved as:

Catel.Examples.ViewModels.MyViewModel

Manually resolving a view model using naming convention


To manually resolve a view model using naming convention, use the following code:

var viewModelLocator = ServiceLocator.Default.ResolveType<IViewModelLocator>();


var viewModelType = viewModelLocator.ResolveViewModel(typeof(MyView));

Customizing naming conventions


By default, the IViewModelLocator uses the following naming conventions to resolve view models:
[UP].ViewModels.[VW]ViewModel
[UP].ViewModels.[VW]ControlViewModel
[UP].ViewModels.[VW]WindowViewModel
[UP].ViewModels.[VW]PageViewModel
[UP].ViewModels.[VW]ActivityViewModel
[UP].ViewModels.[VW]FragmentViewModel
[AS].ViewModels.[VW]ViewModel
[AS].ViewModels.[VW]ControlViewModel
[AS].ViewModels.[VW]WindowViewModel
[AS].ViewModels.[VW]PageViewModel
[AS].ViewModels.[VW]ActivityViewModel
[AS].ViewModels.[VW]FragmentViewModel
[CURRENT].[VW]ViewModel
[CURRENT].[VW]ControlViewModel
[CURRENT].[VW]WindowViewModel
[CURRENT].[VW]PageViewModel
[CURRENT].[VW]ActivityViewModel
[CURRENT].[VW]FragmentViewModel

For more information about naming conventions, see Naming conventions

However, it is possible to add or remove new naming conventions to support your own naming convention. For example, to add a new naming
convention for a different assembly, use this code:

var viewModelLocator = ServiceLocator.Default.ResolveType<IViewModelLocator>();


viewModelLocator.NamingConventions.Add("MyCustomAssembly.ViewModels.[VW]ViewModel");

Registering custom view models


Sometimes, a class doesn't follow a naming convention (for whatever reason possible). In such a case, it is possible to register a mapping
manually using the following code:

var viewModelLocator = ServiceLocator.Default.ResolveType<IViewModelLocator>();


viewModelLocator.Register(typeof(MyViewNotFollowingNamingConvention),
typeof(MyViewModel));

Using a custom ViewModelLocator


If you want to have total freedom to determine which view model is provided per view (maybe there are other services that have an impact on
this), it is possible to create a custom IViewModelLocator implementation. Then the only thing to do is to register it using the following code:

ServiceLocator.Default.Register<IViewModelLocator, MyViewModelLocator>();

Using a generic implementation of the view


Last but not least, it is still possible to use the "old-fashioned" way by using the generic view bases. These classes directly derive from the
non-generic views and return the generic type definition of the view model using the GetViewModelType method.

ViewLocator
The IViewLocator class is responsible for resolving the right views for a view model. Before Catel 3.0, the IUIVisualizerService was responsible for
resolving the view, but this responsibility is now taken over by the IViewLocator. The UIVisualizerService internally uses the IViewLocator to
resolve the views.

Resolving by naming convention


It is possible to resolve views using the IViewLocator. Then you can use the ResolveView method to resolve the view based on the type of the
view model.
For example, the following view model:

Catel.Examples.ViewModels.MyViewModel

will be resolved as:

Catel.Examples.Views.MyView

Manually resolving a view using naming convention


To manually resolve a view using naming convention, use the following code:

var viewLocator = ServiceLocator.Instance.ResolveType<IViewLocator>();


var viewType = viewLocator.ResolveView(typeof(MyViewModel));

Customizing naming conventions


By default, the IViewLocator uses the following naming conventions to resolve views:
[UP].Views.[VM]
[UP].Views.[VM]View
[UP].Views.[VM]Control
[UP].Views.[VM]Window
[UP].Views.[VM]Page
[UP].Views.[VM]Activity
[UP].Views.[VM]Fragment
[UP].Controls.[VM]
[UP].Controls.[VM]Control

[UP].Pages.[VM]
[UP].Pages.[VM]Page
[UP].Windows.[VM]
[UP].Windows.[VM]Window
[AS].Views.[VM]
[AS].Views.[VM]View
[AS].Views.[VM]Control
[AS].Views.[VM]Page
[AS].Views.[VM]Window
[AS].Views.[VM]Activity
[AS].Views.[VM]Fragment
[AS].Controls.[VM]
[AS].Controls.[VM]Control
[AS].Pages.[VM]
[AS].Pages.[VM]Page
[AS].Windows.[VM]
[AS].Windows.[VM]Window
[AS].Activities.[VM]
[AS].Activities.[VM]Activity
[AS].Fragments.[VM]
[AS].Fragments.[VM]Fragment
[AS].UI.Views.[VM]
[AS].UI.Views.[VM]View
[AS].UI.Views.[VM]Control
[AS].UI.Views.[VM]Page
[AS].UI.Views.[VM]Window
[AS].UI.Views.[VM]Activity
[AS].UI.Views.[VM]Fragment
[AS].UI.Controls.[VM]
[AS].UI.Controls.[VM]Control
[AS].UI.Pages.[VM]
[AS].UI.Pages.[VM]Page
[AS].UI.Windows.[VM]
[AS].UI.Windows.[VM]Window
[AS].UI.Activities.[VM]
[AS].UI.Activities.[VM]Activity
[AS].UI.Activities.[VM]Fragment
[CURRENT].[VM]View
[CURRENT].[VM]Control
[CURRENT].[VM]Page
[CURRENT].[VM]Window
[CURRENT].[VM]Activity
[CURRENT].[VM]Fragment

For more information about naming conventions, see Naming conventions

However, it is possible to add or remove new naming conventions to support your own naming convention. For example, to add a new naming
convention for a different assembly, use this code:

var viewLocator = ServiceLocator.Instance.ResolveType<IViewLocator>();


viewLocator.NamingConventions.Add("MyCustomAssembly.Views.[VM]View");

Registering custom views

Sometimes, a class doesn't follow a naming convention (for whatever reason possible). In such a case, it is possible to register a mapping
manually using the following code:

var viewLocator = ServiceLocator.Instance.ResolveType<IViewLocator>();


viewLocator.Register(typeof(MyViewModelNotFollowingNamingConvention), typeof(MyView));

Using a custom ViewLocator


If you want to have total freedom to determine which view is provided per view model (maybe there are other services that have an impact on
this), it is possible to create a custom IViewLocator implementation. Then the only thing to do is to register it using the following code:

ServiceLocator.Default.RegisterType<IViewLocator, MyViewLocator>();

UrlLocator
The IUrlLocator class is responsible for resolving the right urls for the xaml views for a view model in navigation based applications. Before Catel
3.0, the INavigationService was responsible for resolving the url, but this responsibility is now taken over by the IUrlLocator. The NavigationServic
e internally uses the IUrlLocator to resolve the views.

Resolving by naming convention


It is possible to resolve views using the IUrlLocator. Then you can use the ResolveUrl method to resolve the url based on the type of the view
model.
For example, the following view model:

Catel.Examples.ViewModels.MyViewModel

will be resolved as:

/Views/MyPage.xaml

Note that the UrlLocator checks whether the resource actually exists. If the resource does not exists, it will not be able to resolve a view

Manually resolving a naming convention


To manually resolve a naming convention, use the following code:

var urlLocator = ServiceLocator.Instance.ResolveType<IUrlLocator>();


var url = viewLocator.ResolveUrl(typeof(MyViewModel));

Customizing naming conventions


By default, the IUrlLocator uses the following naming conventions to resolve urls:
/Views/[VM].xaml
/Views/[VM]View.xaml
/Views/[VM]Control.xaml

/Views/[VM]Page.xaml
/Views/[VM]Window.xaml
/Controls/[VM].xaml
/Controls/[VM]Control.xaml
/Pages/[VM].xaml
/Pages/[VM]Page.xaml
/Windows/[VM].xaml
/Windows/[VM]Window.xaml
/UI.Views/[VM].xaml
/UI.Views/[VM]View.xaml
/UI.Views/[VM]Control.xaml
/UI.Views/[VM]Page.xaml
/UI.Views/[VM]Window.xaml
/UI.Controls/[VM].xaml
/UI.Controls/[VM]Control.xaml
/UI.Pages/[VM].xaml
/UI.Pages/[VM]Page.xaml
/UI.Windows/[VM].xaml
/UI.Windows/[VM]Window.xaml
/[VM].xaml
/[VM]Control.xaml
/[VM]Page.xaml
/[VM]Window.xaml

For more information about naming conventions, see Naming conventions

However, it is possible to add or remove new naming conventions to support your own naming convention. For example, to add a new naming
convention for a different assembly, use this code:

var urlLocator = ServiceLocator.Instance.ResolveType<IUrlLocator>();


urlLocator.NamingConventions.Add("/MyPages/[VM]Page.xaml");

Registering custom urls


Sometimes, a class doesn't follow a naming convention (for whatever reason possible). In such a case, it is possible to register a mapping
manually using the following code:

var urlLocator = ServiceLocator.Instance.ResolveType<IUrlLocator>();


urlLocator.Register(typeof(MyViewModelNotFollowingNamingConvention),
"/MyVerySpecialUrl.xaml");

Using a custom UrlLocator


If you want to have total freedom to determine which url is provided per view model (maybe there are other services that have an impact on this),
it is possible to create a custom IUrlLocator implementation. Then the only thing to do is to register it using the following code:

ServiceLocator.Default.Register<IUrlLocator, MyUrlLocator>();

Naming conventions
Some services in Catel support naming conventions. For example, the IViewLocator and IViewModelLocator allow naming conventions to prevent

a user from having to register all views and view models. Internally, the naming conventions are resolved using the NamingConvention helper
class. This part of the documentation explains the possible constants in naming conventions.

[AS] constant
The [AS] constant will be replaced by the assembly name. For example, the following naming convention:

[AS].Views

in assembly Catel.Examples will be resolved as:

Catel.Examples.Views

[VM] constant
The [VM] constant will be replaced by the name of the view model without the ViewModel postfix. For example, the following naming convention:

[AS].Views.[VM]View

in assembly Catel.Examples and for type Catel.Examples.ViewModels.MyViewModel will be resolved as:

Catel.Examples.Views.MyView

[VW] constant
The [VW] constant will be replaced by the name of the view without the View, Control, Page or Window postfixes. For example, the following
naming convention:

[AS].ViewModels.[VW]ViewModel

in assembly Catel.Examples and for type Catel.Examples.Views.MyView will be resolved as:

Catel.Examples.ViewModels.MyViewModel

[UP] constant
Sometimes it is not possible to use the [AS] constant because the assembly name is not used in the namespace. For example, for an application
called PersonApplication where the client assembly is PersonApplication.Client, the root namespace will still be PersonApplication. Therefore, it is
recommend to use the [UP] constant for this situation.
The [UP] constant will move the namespaces up by one step. It automatically detects the right separator (\ (backslash), / (slash), . (dot) and |
(pipe) are supported).
The following naming convention:

[UP].Views.[VM]View

for type Catel.Examples.ViewModels.MyViewModel will be resolved as:

Catel.Examples.Views.MyView

[CURRENT] constant
Some people prefer to put classes into the same namespace (such as views and view models).
The [CURRENT] constant will use the same namespace.
The following naming convention:

[CURRENT].[VM]View

for type Catel.Examples.MyViewModel will be resolved as:

Catel.Examples.MyView

Services
Catel offers lots of out-of-the-box services and implementations. Services can be used to separate the logic of external functionality in a service.
The advantages of this technique are:
Separation of Concerns
Unit testing (mocking interfaces is easy)
All services provided by Catel have both a unit test version and a real (or production version). For example, the IMessageService has a test
implementation that does not show a message box, but checks the result only.
AccelerometerService
CameraService
CompassService
GyroscopeService
LocationService
MessageService
NavigationService
OpenFileService
PleaseWaitService
ProcessService
SaveFileService
SchedulerService
SelectDirectoryService
SplashScreenService
UIVisualizerService
VibrateService
ViewExportService

AccelerometerService
The IAccelerometerService allows a developer to access the accelerometer of a Windows Phone device.
Platform info
Check if the sensor is supported by the device
Starting the service
Stopping the service
It is important that the service must be started and stopped to retrieve values

Platform info

Framework

Supported

WPF
Silverlight 5
Windows Phone 8.0
Windows Phone 8.1
Windows RT 8.0
Windows RT 8.1
Android
iOS
Test/emulation service

Check if the sensor is supported by the device


It is important to check whether the sensor is actually supported by the device. This can be done using the following code:

var dependencyResolver = this.GetDependencyResolver();


var accelerometerService = dependencyResolver.Resolve<IAccelerometerService>();
if (accelerometerService.IsSupported)
{
// Sensor is supported
}

Starting the service


When a service is started, the service will start raising the CurrentValueChanged event as soon as new values come in from the sensor. To start
the service, use the following code:

var dependencyResolver = this.GetDependencyResolver();


var accelerometerService = dependencyResolver.Resolve<IAccelerometerService>();
accelerometerService.CurrentValueChanged += OnAccelerometerValueChanged;
accelerometerService.Start();

Stopping the service


It is important to stop the service when it is no longer needed by the application. To stop the service, use the following code:

var dependencyResolver = this.GetDependencyResolver();


var accelerometerService = dependencyResolver.Resolve<IAccelerometerService>();
accelerometerService.CurrentValueChanged -= OnAccelerometerValueChanged;
accelerometerService.Stop();

CameraService
The ICameraService allows a developer to use the PhotoCamera class in an MVVM manner.
Platform info
Starting and stopping the service

Capturing images
Showing a video of camera in a view
Instantiating the test implementation
Customizing camera settings for testing
It is important that the service must be started and stopped to retrieve values

There is also an article available about this service: WP7 Mango and Unit Testing the Camera

Platform info
Framework

Supported

WPF
Silverlight 5
Windows Phone 8.0
Windows Phone 8.1
Windows RT 8.0
Windows RT 8.1
Android
iOS
Test/emulation service

Starting and stopping the service


The PhotoCamera documentation continuously states that the camera object must be created and disposed properly. In the service, this is
encapsulated by the Start and Stop methods. To start the service, use the code below:

var dependencyResolver = this.GetDependencyResolver();


var cameraService = dependencyResolver.Resolve<ICameraService>();
cameraService.CaptureThumbnailAvailable += OnCameraServiceCaptureThumbnailAvailable;
cameraService.CaptureImageAvailable += OnCameraServiceCaptureImageAvailable;
cameraService.Start();

To stop the service, use the code below: (note: the Close method on a view model is feature of Catel):

protected override void Close()


{
var dependencyResolver = this.GetDependencyResolver();
var cameraService = dependencyResolver.Resolve<ICameraService>();
cameraService.Stop();
cameraService.CaptureThumbnailAvailable -=
OnCameraServiceCaptureThumbnailAvailable;
cameraService.CaptureImageAvailable -= OnCameraServiceCaptureImageAvailable;
}

Capturing images

To capture images, several things must be done. The first action to accomplish is to subscribe to the ICameraService.CaptureImageAvailable eve
nt. The next step is to invoke the CaptureImage method like shown below:

CameraService.CaptureImage();

The last part is very important. You will need to read the image stream from the CaptureImageAvailable event:

BitmapImage bitmap = new BitmapImage();


bitmap.SetSource(e.ImageStream);

Showing a video of camera in a view


To show a preview of the camera input on the phone, first subscribe to the ICameraService.CaptureThumbnailImageAvailable event. Next step is
to create a property on the view model:

/// <summary>
/// Gets or sets the current photo.
/// </summary>
public BitmapImage CurrentPhoto
{
get { return GetValue<BitmapImage>(CurrentPhotoProperty); }
set { SetValue(CurrentPhotoProperty, value); }
}

/// <summary>
/// Register the CurrentPhoto property so it is known in the class.
/// </summary>
public static readonly PropertyData CurrentPhotoProperty =
RegisterProperty("CurrentPhoto", typeof(BitmapImage));

This property definition is a Catel property, but if you prefer using a different MVVM framework or your own property definition style, you are free
to do that as well.
In the view, use the Image control to show the current photo:

<Image Grid.Row="0" Source="{Binding CurrentPhoto}" />

Last but not least, we need to update the CurrentPhoto property when a new thumbnail is available.

private void OnCameraServiceCaptureThumbnailAvailable(object sender,


ContentReadyEventArgs e)
{
BitmapImage bitmap = new BitmapImage();
bitmap.SetSource(e.ImageStream);
CurrentPhoto = bitmap;
}

Instantiating the test implementation


The test implementation of the ICameraService needs to be instantiated with an image. The service will use this image to create an animation.

The animation that will be applied is the image scrolling to the right pixel by pixel.
To instantiate the test service, add an image to the Windows Phone project and set its build action to Resource. Then instantiate the service like
in the code below:

var testImage = new BitmapImage();


var streamResourceInfo = Application.GetResourceStream(new
Uri("/MyAssembly;component/Resources/Images/MyImage.png",
UriKind.RelativeOrAbsolute));
testImage.CreateOptions = BitmapCreateOptions.None;
testImage.SetSource(streamResourceInfo.Stream);
_testCameraService = new CameraService(testImage);
serviceLocator.RegisterInstance<ICameraService>(_testCameraService);

By default, the ICameraService will generate a new thumbnail image every 50 milliseconds. It is possible to customize this with a constructor
overload.

Customizing camera settings for testing


Sometimes it is required to test different resolutions. One way to do this is to buy all available Windows Phone devices and test the software on all
the cameras. An easier way is to use the ICameraService and customize the camera options to test how the application responds to the different
settings.
The settings are stored in the CameraServiceTestData class. This class allows customizing all the properties normally found on the PhotoCamera
class. For example, to only allow the primary camera (because front facing cameras are not supported by all devices), use the following code:

var cameraTestSettings = new CameraServiceTestData();


cameraTestSettings.SupportedCameraTypes = CameraType.Primary;
cameraService.UpdateTestData(cameraTestSettings);

It is also possible to change the thumbnail and final resolution of the images:

var cameraTestSettings = new CameraServiceTestData();


cameraTestSettings.PreviewResolution = new Size(400, 800);
cameraTestSettings.Resolution = new Size(1200, 2400);
cameraService.UpdateTestData(cameraTestSettings);

CompassService
The ICompassService allows a developer to access the compass of a Windows Phone device.
Platform info
Check if the sensor is supported by the device
Starting the service
Stopping the service
Note that the Compass service is available as separate assembly to make sure Catel.MVVM does also work on older devices without a
Compass

It is important that the service must be started and stopped to retrieve values

Platform info
Framework

Supported

WPF
Silverlight 5
Windows Phone 8.0
Windows Phone 8.1
Windows RT 8.0
Windows RT 8.1
Android
iOS
Test/emulation service

Check if the sensor is supported by the device


It is important to check whether the sensor is actually supported by the device. This can be done using the following code:

var dependencyResolver = this.GetDependencyResolver();


var compassService = dependencyResolver.Resolve<ICompassService>();
if (compassService.IsSupported)
{
// Sensor is supported
}

Starting the service


When a service is started, the service will start raising the CurrentValueChanged event as soon as new values come in from the sensor. To start
the service, use the following code:

var dependencyResolver = this.GetDependencyResolver();


var compassService = dependencyResolver.Resolve<ICompassService>();
compassService.CurrentValueChanged += OnCompassValueChanged;
compassService.Start();

Stopping the service


It is important to stop the service when it is no longer needed by the application. To stop the service, use the following code:

var dependencyResolver = this.GetDependencyResolver();


var compassService = dependencyResolver.Resolve<ICompassService>();
compassService.CurrentValueChanged -= OnCompassValueChanged;
compassService.Stop();

GyroscopeService
The IGyroscopeService allows a developer to access the gyroscope of a Windows Phone device.
Platform info
Check if the sensor is supported by the device
Starting the service
Stopping the service

Note that the Gyroscope service is available as separate assembly to make sure Catel.MVVM does also work on older devices without
a Gyroscope

It is important that the service must be started and stopped to retrieve values

Platform info
Framework

Supported

WPF
Silverlight 5
Windows Phone 8.0
Windows Phone 8.1
Windows RT 8.0
Windows RT 8.1
Android
iOS
Test/emulation service

Check if the sensor is supported by the device


It is important to check whether the sensor is actually supported by the device. This can be done using the following code:

var dependencyResolver = this.GetDependencyResolver();


var gyroscopeService = dependencyResolver.Resolve<IGyroscopeService>();
if (gyroscopeService.IsSupported)
{
// Sensor is supported
}

Starting the service


When a service is started, the service will start raising the CurrentValueChanged event as soon as new values come in from the sensor. To start
the service, use the following code:

var dependencyResolver = this.GetDependencyResolver();


var gyroscopeService = dependencyResolver.Resolve<IGyroscopeService>();
gyroscopeService.CurrentValueChanged += OnGyroscopeValueChanged;
gyroscopeService.Start();

Stopping the service


It is important to stop the service when it is no longer needed by the application. To stop the service, use the following code:

var dependencyResolver = this.GetDependencyResolver();


var gyroscopeService = dependencyResolver.Resolve<IGyroscopeService>();
gyroscopeService.CurrentValueChanged -= OnGyroscopeValueChanged;
gyroscopeService.Stop();

LocationService
The ILocationService allows a developer to use GPS devices inside a view model.
Platform info
Starting the service
Stopping the service
Emulating GPS without device
It is important that the service must be started and stopped to retrieve values

Platform info
Framework

Supported

WPF
Silverlight 5
Windows Phone 8.0
Windows Phone 8.1
Windows RT 8.0
Windows RT 8.1
Android
iOS
Test/emulation service

Starting the service


The GPS service needs to be started and stopped. To start the GPS service, use the following code:

var dependencyResolver = this.GetDependencyResolver();


var locationService = dependencyResolver.Resolve<ILocationService>();
locationService.LocationChanged += OnCurrentLocationChanged;
locationService.Start();

The service will raise the LocationChanged event when a new location becomes available.

Stopping the service


It is required to stop the service when it is no longer needed. The service can be stopped using the following code:

var dependencyResolver = this.GetDependencyResolver();


var locationService = dependencyResolver.Resolve<ILocationService>();
locationService.LocationChanged -= OnCurrentLocationChanged;
locationService.Stop();

Emulating GPS without device


It is possible to emulate GPS without actually owning a Windows Phone 7 or emulate data in the emulator. To accomplish this, it is required to use
the Catel.MVVM.Services.Test.LocationService class. This class can be used in the following way:

var dependencyResolver = this.GetDependencyResolver();


Test.LocationService service =
(Test.LocationService)dependencyResolver.Resolve<ILocationService>();
// Queue the next location (and then wait 5 seconds)
var locationTestData = new LocationTestData(new Location(100d, 100d), new TimeSpan(0,
0, 0, 5)));
service.ExpectedLocations.Add(locationTestData);
// Go to the next location manually
service.ProceedToNextLocation();

It is also possible to enqueue lots of coordinates with a time span and emulate a path.

MessageService
The IMessageService allows a developer to show message boxes from a view model.
Platform info
Screenshot
Showing a message
Showing an error
Requesting confirmation
Asynchronous confirmation

Platform info
Framework
WPF
Silverlight 5
Windows Phone 8.0
Windows Phone 8.1
Windows RT 8.0
Windows RT 8.1
Android
iOS
Test/emulation service

Screenshot

Supported

Showing a message
To show a message from a view model, use the following code:

var dependencyResolver = this.GetDependencyResolver();


var messageService = dependencyResolver.Resolve<IMessageService>();
await messageService.Show("My first message via the service");

Showing an error
Showing a warning or error is very easy. Use the following code:

var dependencyResolver = this.GetDependencyResolver();


var messageService = dependencyResolver.Resolve<IMessageService>();
await messageService.ShowError("Whoops, something went wrong");

Requesting confirmation
It is also possible to request confirmation from the user. The number of possibilities depends on WPF, Silverlight or Windows Phone is used (for
example, not all platforms support YesNo).
The following code must be used to request confirmation:

var dependencyResolver = this.GetDependencyResolver();


var messageService = dependencyResolver.Resolve<IMessageService>();
if (await messageService.Show("Are you sure you want to do this?", "Are you sure?",
MessageButton.YesNo) == MessageResult.Yes)
{
// Do it!
}

Asynchronous confirmation
Sometimes you don't want to use regular message boxes, and in Silverlight this means that your call has to be asynchronous. The
implementation is very simple:

var dependencyResolver = this.GetDependencyResolver();


var messageService = dependencyResolver.Resolve<IMessageService>();
await messageService.Show("Are you sure you want to do this?", "Are you sure?",
MessageButton.YesNo, OnMessageServiceComplete);

There are two possible callbacks, one with a result of type Func<MessageResult> or one without a result of type Action.

NavigationService
The INavigationService allows a developer to navigate to other pages inside an application using view models only.
All pages will have to be registered manually or following the right naming convention.
Platform info
Closing an application
Preventing an application to be closed
Navigating to a new view
Navigating with parameters
Navigating back and forward
Navigating to a custom Uri
Registering custom views
Using naming conventions to find pages
For WPF and Silverlight, the pages must inherit from Page. For WP7, the pages must inherit from PhoneApplicationPage. In WPF, the
parameters are of type Dictionary<string, object>, in Silverlight and WP7, the arguments are of type Dictionary<string, string>.

Platform info
Framework

Supported

WPF
Silverlight 5
Windows Phone 8.0
Windows Phone 8.1
Windows RT 8.0
Windows RT 8.1
Android
iOS
Test/emulation service

Closing an application
It is possible to close an application using the following code:

var dependencyResolver = this.GetDependencyResolver();


var navigationService = dependencyResolver.Resolve<INavigationService>();
navigationService.CloseApplication();

Preventing an application to be closed


To prevent an application to be closed, one can subscribe to the ApplicationClosing event:

var dependencyResolver = this.GetDependencyResolver();


var navigationService = dependencyResolver.Resolve<INavigationService>();
navigationService.ApplicationClosing += (sender, e)
=>
{
e.Cancel = true;
};

Navigating to a new view


To navigate to a new page, use the following code:

var dependencyResolver = this.GetDependencyResolver();


var navigationService = dependencyResolver.Resolve<INavigationService>();
navigationService.Navigate<EmployeeViewModel>();

Navigating with parameters


It is very easy to navigate to a new page with parameters. Use the following code:

var parameters = new Dictionary<string, object>();


parameters.Add("id", employee.EmployeeID);
var dependencyResolver = this.GetDependencyResolver();
var navigationService = dependencyResolver.Resolve<INavigationService>();
navigationService.Navigate<EmployeeViewModel>(parameters);

To read the navigation parameters in the receiving view model, use the OnNavigationCompleted method.

Navigating back and forward


The service also supports navigating back and forward:

var dependencyResolver = this.GetDependencyResolver();


var navigationService = dependencyResolver.Resolve<INavigationService>();
navigationService.GoBack(); // navigates to the previous page, obviously
navigationService.GoForward(); // navigates to the next page, obviously

Navigating to a custom Uri


To navigate to a custom uri without a view model type, use the following code. Of course it's also possible to pass parameters using the right
method overload.

var dependencyResolver = this.GetDependencyResolver();


var navigationService = dependencyResolver.Resolve<INavigationService>();
navigationService.Navigate("/UI/Pages/EmployeePage.xaml");

Registering custom views


To register custom views, use the following code:

var dependencyResolver = this.GetDependencyResolver();


var navigationService = dependencyResolver.Resolve<INavigationService>();
navigationService.Register(typeof(EmployeeViewModel), typeof(EmployeeDetailsPage));

Using naming conventions to find pages


If you use a consistent naming convention for views, it is possible to apply this naming convention to the service. This saves a lot of custom
registration. When a page is not registered, the Show method will try to find the view using the naming convention.
To add a naming convention, use the following code:

var dependencyResolver = this.GetDependencyResolver();


var navigationService = dependencyResolver.Resolve<INavigationService>();
navigationService.NamingConventions.Add(string.Format("/Views/My{0}View",
NamingConvention.ViewModelName));

The above naming convention will use the following combination:


Input: MyAssembly.UI.ViewModels.EmployeeViewModel
Output: MyAssembly.UI.Windows.EmployeeWindow
By default, the following naming conventions will be used:
/Views/[VM].xaml
/Views/[VM]View.xaml
/Views/[VM]Control.xaml
/Views/[VM]Page.xaml
/Views/[VM]Window.xaml
/Controls/[VM].xaml
/Controls/[VM]Control.xaml
/Pages/[VM].xaml
/Pages/[VM]Page.xaml
/Windows/[VM].xaml
/Windows/[VM]Window.xaml
/UI/Views/[VM].xaml
/UI/Views/[VM]View.xaml
/UI/Views/[VM]Control.xaml
/UI/Views/[VM]Page.xaml
/UI/Views/[VM]Window.xaml
/UI/Controls/[VM].xaml
/UI/Controls/[VM]Control.xaml
/UI/Pages/[VM].xaml
/UI/Pages/[VM]Page.xaml
/UI/Windows/[VM].xaml
/UI/Windows/[VM]Window.xaml

OpenFileService
The IOpenFileService allows a developer to let the user choose a file from inside a view model.
Platform info
Opening a file

Platform info
Framework

Supported

WPF
Silverlight 5
Windows Phone 8.0
Windows Phone 8.1
Windows RT 8.0
Windows RT 8.1
Android
iOS
Test/emulation service

Opening a file
To open a file, it is required to set the right properties of the service and then make a call to the DetermineFile method:

var dependencyResolver = this.GetDependencyResolver();


var openFileService = dependencyResolver.Resolve<IOpenFileService>();
openFileService.Filter = "All files|*.*";
if (openFileService.DetermineFile())
{
// User selected a file
}

PleaseWaitService
The IPleaseWaitService allows a developer to show a please wait message (a.k.a. busy indicator) from a view model.
Platform info
Screenshot
Showing
Hiding
Showing and automatically hide
Changing the status
Showing a determinate please wait window
Push/Pop

Platform info
Framework
WPF
Silverlight 5
Windows Phone 8.0
Windows Phone 8.1
Windows RT 8.0
Windows RT 8.1
Android
iOS
Test/emulation service

Supported

Screenshot
This is the WPF service screenshot, the exact look differs per framework

Showing
using Catel.IoC;

var dependencyResolver = this.GetDependencyResolver();


var pleaseWaitService = dependencyResolver.Resolve<IPleaseWaitService>();
pleaseWaitService.Show();

Hiding
var dependencyResolver = this.GetDependencyResolver();
var pleaseWaitService = dependencyResolver.Resolve<IPleaseWaitService>();
pleaseWaitService.Hide();

Showing and automatically hide


The IPleaseWaitService can automatically hide itself when an action is completed. To use this feature, simply pass a delegate to the Show metho
d and the service will hide the window as soon as the delegate has completed.

using Catel.IoC;

var dependencyResolver = this.GetDependencyResolver();


var pleaseWaitService = dependencyResolver.Resolve<IPleaseWaitService>();
pleaseWaitService.Show(() => Thread.Sleep(1500));

Changing the status

var dependencyResolver = this.GetDependencyResolver();


var pleaseWaitService = dependencyResolver.Resolve<IPleaseWaitService>();
pleaseWaitService.UpdateStatus("new status");

Showing a determinate please wait window


By default, the IPleaseWaitService shows an indeterminate state (no actual progress is visible). However, both the Silverlight and WPF
implementation of the service also implement the status that shows the progress of a long running action.
The UpdateStatus method can be used to show the window. The statusFormat argument can contain '{0}' (represents the current item) and '{1}'
(represents the total items). However, they can also be left out.

var dependencyResolver = this.GetDependencyResolver();


var pleaseWaitService = dependencyResolver.Resolve<IPleaseWaitService>();
pleaseWaitService.UpdateStatus(1, 5, "Updating item {0} of {1}");

The determinate version can be hidden via a call to Hide or when the currentItem argument is larger than the number of totalItems.

Push/Pop
Sometimes, multiple view models or multiple actions use the service. It's not possible to hide the window when the first action is completed,
because the user will still have to wait for the other actions to complete (without a please wait window). To implement this correctly, it is possible
to use the Push and Pop methods.
The Push method shows the window if it is not already visible and then increases an internal counter. At the start of each (asynchronous) action,
the developer can call the Push method. When the action is completed, the developer calls Pop which will internally decrease the counter. If the
counter hits zero (0), the window is automatically hidden.
It is possible to hide the window, even when the internal counter is not yet zero. A call to Hide will reset the counter to zero and thus hide the
window.

ProcessService
The IProcessService allows a developer to run processes from inside a view model.
Platform info
Starting a process with arguments
Starting a process with arguments and completed callback

Platform info
Framework
WPF
Silverlight 5
Windows Phone 8.0
Windows Phone 8.1
Windows RT 8.0
Windows RT 8.1
Android
iOS
Test/emulation service

Supported

Starting a process with arguments


To start a process with arguments, use the following code:

var dependencyResolver = this.GetDependencyResolver();


var processService = dependencyResolver.Resolve<IProcessService>();
processService.StartProcess("notepad.exe", @"C:\mytextfile.txt");

Starting a process with arguments and completed callback


To start a process with arguments and receive a callback on completion, use the following code:

var dependencyResolver = this.GetDependencyResolver();


var processService = dependencyResolver.Resolve<IProcessService>();
processService.StartProcess("notepad.exe", @"C:\mytextfile.txt", OnProcessCompleted);

SaveFileService
The ISaveFileService allows a developer to let the user choose a file from inside a view model.
Platform info
Choosing a file

Platform info
Framework

Supported

WPF
Silverlight 5
Windows Phone 8.0
Windows Phone 8.1
Windows RT 8.0
Windows RT 8.1
Android
iOS
Test/emulation service

Choosing a file
To select a file to save, it is required to set the right properties of the service and then make a call to the DetermineFile method:

var dependencyResolver = this.GetDependencyResolver();


var saveFileService = dependencyResolver.Resolve<ISaveFileService>();
saveFileService.Filter = "C# File|*.cs";
if (saveFileService.DetermineFile())
{
// User selected a file
}

SchedulerService
The ISchedulerService allows a developer to schedule an action in the relative or absolute future. The SchedulerService will use the DispatcherTi
mer to invoke the action.
Platform info
Scheduling an action in the relative future
Scheduling an action in the absolute future
Note that the SchedulerService does not provide any persistence of actions and schedules. When the application is closed, all
schedules are lost because they are kept in memory.

Platform info
Framework

Supported

WPF
Silverlight 5
Windows Phone 8.0
Windows Phone 8.1
Windows RT 8.0
Windows RT 8.1
Android
iOS
Test/emulation service

Scheduling an action in the relative future


To schedule an action in the relative future, use the Schedule method with the TimeSpan overload. The code below starts the action with a delay
of 50 milliseconds.

var dependencyResolver = this.GetDependencyResolver();


var schedulerService = dependencyResolver.Resolve<ISchedulerService>();
schedulerService.Schedule(() => DoSomething(), new TimeSpan(0, 0, 0, 0, 50));

Scheduling an action in the absolute future


To schedule an action in the absolute future, use the Schedule method with the DateTime overload. The code below starts the action in 5
minutes.

var dependencyResolver = this.GetDependencyResolver();


var schedulerService = dependencyResolver.Resolve<ISchedulerService>();
schedulerService.Schedule(() => DoSomething(), DateTime.Now.AddMinutes(5));

SelectDirectoryService
The ISelectDirectoryService allows a developer to let the user choose a directory from inside a view model.
Platform info
Selecting a directory

Platform info
Framework

Supported

WPF
Silverlight 5
Windows Phone 8.0
Windows Phone 8.1
Windows RT 8.0
Windows RT 8.1
Android
iOS
Test/emulation service

Selecting a directory
To select a directory, it is required to set the right properties of the service and then make a call to the DetermineDirectory method:

var dependencyResolver = this.GetDependencyResolver();


var selectDirectoryService = dependencyResolver.Resolve<ISelectDirectoryService>();
if (selectDirectoryService.DetermineDirectory())
{
// User selected a directory
}

SplashScreenService
The ISplashScreenService allows a developer execute a batch of tasks en-queued and show the progress through a registered IPleaseWaitServi
ce or IUIVisualizerService type, from the main entry point of the application (typically from the bootstrapper) or a view model.
Platform info
Screenshot
Enqueuing tasks into the SplashScreenService batch
Committing the batch
Committing the batch asynchronously with callback
Smooth progress notification of an executing action task

Platform info
Framework
WPF
Silverlight 5
Windows Phone 8.0
Windows Phone 8.1
Windows RT 8.0
Windows RT 8.1
Android

Supported

iOS
Test/emulation service

Screenshot

Enqueuing tasks into the SplashScreenService batch


First of all is requiered resolve the instance of the registered ISplashScreenService type from the view model:

var dependencyResolver = this.GetDependencyResolver();


var splashScreenService = dependencyResolver.Resolve<ISplashScreenService>();

or from the application bootstrapper, after a previous service registration:

ServiceLocator.Default.RegisterTypeIfNotYetRegistered<ISplashScreenService,
SplashScreenService>();
/*...*/
var splashScreenService = ServiceLocator.Default.ResolveType<ISplashScreenService>();

To en-queue tasks use the following code:

splashScreenService.Enqueue(new ActionTask("Creating the shell", OnCreateShell));


splashScreenService.Enqueue(new ActionTask("Initializing modules",
OnInitializeModules));
splashScreenService.Enqueue(new ActionTask("Starting application",
OnStartApplication));

Committing the batch


To execute the batch of en-queued tasks, and show the progress through the IPleaseWaitService, use the following code:

splashScreenService.Commit();

To execute the batch of en-queued tasks, and show the progress through the IUIVisualizerService, use the following code:

splashScreenService.Commit<MySplashScreenViewModel>();

or:

splashScreenService.Commit(typeof(MySplashScreenViewModel));

Committing the batch asynchronously with callback


To execute the batch of en-queued tasks asynchronously, and show the progress through the IPleaseWaitService, use the following code:

splashScreenService.CommitAsync(OnBatchCompleted);

To execute the batch of en-queued task asynchronously, and show the progress through the IUIVisualizerService, use the following code:

splashScreenService.CommitAsync<MySplashScreenViewModel>(OnBatchCompleted);

or:

splashScreenService.CommitAsync(OnBatchCompleted, typeof(MySplashScreenViewModel));

Smooth progress notification of an executing action task


To notify the progress of an action task smoothly, use the argument of type ITaskProgressTracker just like is used in the following code:

private void OnInitializeModules(ITaskProgressTracker tracker)


{
int registeredModulesCount = 0;
foreach (var module in ModuleCatalog.Modules)
{
tracker.UpdateStatus((int)(100.0f * (registeredModulesCount /
ModuleCatalog.Modules.Count)), string.Format("Registering module '{0}'",
module.ModuleName));
if (RegisterModule(module))
{
registeredModulesCount++;
}
}
}

After committing the batch is cleared, so to execute it again you should en-queue the tasks again

The SplashScreenService is thread-safe

UIVisualizerService
The IUIVisualizerService allows a developer to show (modal) windows or dialogs without actually referencing a specific view. Internally, the UIVisu
alizerService uses the ViewLocator to resolve views.
Platform info
Screenshot
Showing a non-modal window
Showing a modal window
Showing a window with callback
Registering a window
Using naming conventions to find windows

Platform info
Framework
WPF
Silverlight 5
Windows Phone 8.0
Windows Phone 8.0
Windows RT 8.0
Windows RT 8.1
Android
iOS
Test/emulation service

Screenshot

Supported

Showing a non-modal window


To show a non-modal window, use the following code:

var viewModel = new EmployeeViewModel();


var dependencyResolver = this.GetDependencyResolver();
var uiVisualizerService = dependencyResolver.Resolve<IUIVisualizerService>();
uiVisualizerService.Show(viewModel);

Showing a modal window


To show a modal window, use the following code:

var viewModel = new EmployeeViewModel();


var dependencyResolver = this.GetDependencyResolver();
var uiVisualizerService = dependencyResolver.Resolve<IUIVisualizerService>();
uiVisualizerService.ShowDialog(viewModel);

Showing a window with callback


To show a (modal or non-modal) window and get a callback as soon as the window is closed, use the following code:

var viewModel = new EmployeeViewModel();


var dependencyResolver = this.GetDependencyResolver();
var uiVisualizerService = dependencyResolver.Resolve<IUIVisualizerService>();
uiVisualizerService.Show(viewModel, OnWindowClosed);

Registering a window
To register a custom window which is not automatically detected via reflection, it is required to use the Register method:

var dependencyResolver = this.GetDependencyResolver();


var uiVisualizerService = dependencyResolver.Resolve<IUIVisualizerService>();
uiVisualizerService.Register(typeof(EmployeeViewModel), typeof(EmployeeView));

Using naming conventions to find windows


Please see the ViewLocator topic.

VibrateService
The IVibrateService allows a developer to start and stop vibration of the device via a service.
Platform info
Starting vibration
Stopping the vibration earlier than initially planned

Platform info
Framework

Supported

WPF
Silverlight 5
Windows Phone 8.0
Windows Phone 8.1
Windows RT 8.0
Windows RT 8.1
Android
iOS
Test/emulation service

Starting vibration
To start the vibration, use the following code (will vibrate for 250 ms). Note that the time span must be between 0 and 5 seconds.

var dependencyResolver = this.GetDependencyResolver();


var vibrateService = dependencyResolver.Resolve<IVibrateService>();
vibrateService.Start(new TimeSpan(0, 0, 0, 0, 250);

Stopping the vibration earlier than initially planned


By default, the vibration stops automatically after the specified time span has passed. However, it is possible to stop the vibration manually.

var dependencyResolver = this.GetDependencyResolver();


var vibrateService = dependencyResolver.Resolve<IVibrateService>();
vibrateService.Stop();

ViewExportService
The IViewExportService allows a developer to export a specific view that belongs to a view model to the clipboard, a file or a printer.
Platform info
Exporting a view
Supported export methods

Platform info
Framework

Supported

WPF
Silverlight 5
Windows Phone 8.0
Windows Phone 8.1
Windows RT 8.0
Windows RT 8.1
Android
iOS
Test/emulation service

Exporting a view
To export a view, use the following code:

var dependencyResolver = this.GetDependencyResolver();


var viewExportService = dependencyResolver.Resolve<IViewExportService>();
viewExportService.Export(myViewModel, ExportMode.File);

Supported export methods


Export method

WPF

Clipboard
File
Print

View models

Silverlight

The view model is a very important part in the MVVM pattern. The view model is responsible for the actual logic that ensures separation of
concerns, but also allows unit testing on the view logic (which is implemented in the view model) without actually instantiating the views.
Like almost every other MVVM framework, the base class for all View-Models is ViewModelBase. This base class is derived from the ModelBase
class explained earlier in this article, which gives the following advantages:
Dependency property a-like property registration;
Automatic change notification;
Support for field and business errors.
Because the class derives from ModelBase, you can simply add field and business errors that are automatically being reflected to the UI. Writing
View-Models has never been so easy!
Creating a basic view model
Creating a view model that watches over other view models
Creating a view model with a model
Creating a view model with a model and mappings
Mapping properties from view to view model
Nested view models
Validation in view models
Advanced view models

Creating a basic view model


This example shows how to create a view model without a model. This is useful when a UI item should simply acknowledge a step that doesn't
need to be persisted to a persistence store. The view model does include validation.

Code snippets
vm - declare a view model
vmprop - declare a property on a view model

Explanation
When implementing a simple view model without a model, only one property has to be implemented that represents the checkbox that needs to
be checked. The example view model declares a single property using the vmprop code snippet. Then, a field error is set if the user has not
agreed in the ValidateFields method.

Code
C#

/// <summary>
/// Simple view model.
/// </summary>
public class SimpleViewModel : ViewModelBase
{
/// <summary>
/// Gets the title of the view model.
/// </summary>
/// <value>The title.</value>
public override string Title { get { return "Just acknowledge"; } }
/// <summary>
/// Gets or sets whether the user has agreed to continue.
/// </summary>
public bool UserAgreedToContinue
{
get { return GetValue<bool>(UserAgreedToContinueProperty); }
set { SetValue(UserAgreedToContinueProperty, value); }
}
/// <summary>
/// Register the UserAgreedToContinue property so it is known in the class.
/// </summary>
public static readonly PropertyData UserAgreedToContinueProperty =
RegisterProperty("UserAgreedToContinue", typeof(bool));
/// <summary>
/// Validates the fields.
/// </summary>
protected override void ValidateFields(List<FieldValidationResult>
validationResults)
{
// Check if the user agrees to continue
if (!UserAgreedToContinue)
{
validationResults.Add(FieldValidationResult.CreateError(UserAgreedToContinueProperty,
"User must agree to continue");
}
}
}

XAML (assuming that the view model is set as datacontext)

<CheckBox Content="Check me to continue" IsChecked="{Binding UserAgreedToContinue,


NotifyOnValidationError=True, ValidatesOnDataErrors=True}" />

Creating a view model that watches over other view models


Most frameworks require you to set up complex message systems (messengers) or other techniques to communicate with other view models. The
downside of this approach is that once a view model is written in module X, and you are interested in the view model, the developer of module X
must take care of notifying other view models. We think this is not the responsibility of the originating view model.
If a view model is interested in the changes of another view model, its the responsibility of the view model that is interested to watch the view
model, not the other way around. To be notified of changes on other view models, the only thing you have to do is to decorate a view model with

the InterestedInAttribute, like shown in the code below:

[InterestedIn(typeof(FamilyViewModel))]
public class PersonViewModel : ViewModelBase

Then, inside the PersonViewModel (which is interested in the changes of FamilyViewModel), you only have to override the OnViewModelProperty
Changed method:

/// <summary>
/// Called when a property has changed for a view model type
/// that the current view model is interested in. This can
/// be accomplished by decorating the view model with the <see
cref="InterestedInAttribute"/>.
/// </summary>
/// <param name="viewModel">The view model.</param>
/// <param name="propertyName">Name of the property.</param>
protected override void OnViewModelPropertyChanged(IViewModel viewModel, string
propertyName)
{
// You can now do something with the changed property
}

It is possible to be interested in multiple view models. Since the view model is passed to the OnViewModelPropertyChanged method, it is very
easy to check the type of the view model.

Code snippets
vm - declare a view model
vmprop - declare a property on a view model

Explanation
The most important thing to know is that there is a ViewModelManager in the library. This manager keeps track of all view models that are alive. A
view model automatically registers itself to the manager, and when it is closed, the view model automatically unsubscribes itself again.
By using the InterestedInAttribute, it is possible to receive notifications of other view models. The InterestedInAttribute defines a specific type of
view model the decorated view model is interested in. Then, the decorated view model will receive all the PropertyChanged events of the live view
models of that specific type. It is possible to define multiple attributes to watch several different types of view models.

Code
Watched view model

/// <summary>
/// Watched view model.
/// </summary>
public class WatchedViewModel : ViewModelBase
{
/// <summary>
/// Gets the title of the view model.
/// </summary>
/// <value>The title.</value>
public override string Title { get { return "View model being watched"; } }
/// <summary>
/// Initializes the object by setting default values.
/// </summary>
protected override void Initialize()
{
// Not required
}
}

Interested view model

/// <summary>
/// Interested view model.
/// </summary>
[InterestedIn(typeof(WatchedViewModel))]
public class InterestedViewModel : ViewModelBase
{
/// <summary>
/// Gets the title of the view model.
/// </summary>
/// <value>The title.</value>
public override string Title { get { return "View model that is interested"; } }
/// <summary>
/// Initializes the object by setting default values.
/// </summary>
protected override void Initialize()
{
// Not required
}
/// <summary>
/// Called when a property has changed for a view model type that the current view
model is interested in. This can
/// be accomplished by decorating the view model with the <see
cref="InterestedInAttribute"/>.
/// </summary>
/// <param name="viewModel">The view model.</param>
/// <param name="propertyName">Name of the property.</param>
protected override void OnViewModelPropertyChanged(IViewModel viewModel, string
propertyName)
{
// TODO: Check what property was changed
}
/// <summary>
/// Called when a command for a view model type that the current view model is
interested in has been executed. This can
/// be accomplished by decorating the view model with the <see
cref="InterestedInAttribute"/>.
/// </summary>
/// <param name="viewModel">The view model.</param>
/// <param name="command">The command that has been executed.</param>
/// <param name="commandParameter">The command parameter used during the
execution.</param>
protected override void OnViewModelCommandExecuted(IViewModel viewModel,
ICatelCommand command, object commandParameter)
{
// TODO: Check what command has been executed
}
}

Creating a view model with a model


This example shows how to create a "classical" view model without any Catel specific MVVM features such as data pass-through. Although it is
recommended to use the pass-through features, some people want to have custom validation on the view model, or want to be fully in control.

Code snippets
vm - declare a view model
vmprop - declare a property on a view model

Explanation
To be in full control, the only thing required is to create a basic view model with the vm code snippet. Then, the following methods should be
implemented:
Constructor - initialize the properties on the view model
ValidateFields - check for field errors in the view model
ValidateBusinessRules - check for business rules in the view model
Save - save the view model data to the model and then save the model

Code
C#

/// <summary>
/// Classical view model.
/// </summary>
public class ClassicalViewModel : ViewModelBase
{
#region Properties
/// <summary>
/// Gets or sets the Person.
/// </summary>
private Person Person
{
get { return GetValue<Person>(PersonProperty); }
set { SetValue(PersonProperty, value); }
}
/// <summary>
/// Register the Person property so it is known in the class.
/// </summary>
public static readonly PropertyData PersonProperty = RegisterProperty("Person",
typeof(Person));
/// <summary>
/// Gets or sets the first name.
/// </summary>
public string FirstName
{
get { return GetValue<string>(FirstNameProperty); }
set { SetValue(FirstNameProperty, value); }
}
/// <summary>
/// Register the FirstName property so it is known in the class.
/// </summary>
public static readonly PropertyData FirstNameProperty =
RegisterProperty("FirstName", typeof(string));
/// <summary>
/// Gets or sets the last name.
/// </summary>
public string LastName

{
get { return GetValue<string>(LastNameProperty); }
set { SetValue(LastNameProperty, value); }
}
/// <summary>
/// Register the LastName property so it is known in the class.
/// </summary>
public static readonly PropertyData LastNameProperty = RegisterProperty("LastName",
typeof(string));
#endregion
#region Methods
/// <summary>
/// Initializes the object by setting default values.
/// </summary>
protected override void Initialize()
{
// Get the person from (in this case) a magical context
Person = Context.CurrentPerson;
// Load the data manually to the view model
FirstName = Person.FirstName;
LastName = Person.LastName;
}
/// <summary>
/// Validates the field values of this object. Override this method to enable
/// validation of field values.
/// </summary>
/// <param name="validationResults">The validation results, add additional results
to this list.</param>
protected override void ValidateFields(List<FieldValidationResult>
validationResults)
{
if (string.IsNullOrWhiteSpace(FirstName))
{
validationResults.Add(FieldValidationResult.CreateError(FirstNameProperty,
"First name is required"));
}
if (string.IsNullOrWhiteSpace(LastName))
{
validationResults.Add(FieldValidationResult.CreateError(LastNameProperty,
"Last name is required"));
}
}
/// <summary>
/// Saves the data.
/// </summary>
/// <returns>
///
<c>true</c> if successful; otherwise <c>false</c>.
/// </returns>
protected override Task<bool> Save()
{
return Task.Factory.StartNew(() =>
{
// Save the data manually to the model

Person.FirstName = FirstName;
Person.LastName = LastName;
// Save the model
return Person.Save();
});

}
#endregion
}

Creating a view model with a model and mappings


Code snippets
Explanation
During of the use of the MVVM pattern, we noticed that lots and lots of developers have a model, and map the values of the model to all
properties of the view model. When the UI closes, the developers map all the properties back to the model. All this redundant code is not
necessary when using the view models of Catel.
In Catel, we have created attributes that allow you to define a property as a model. A model is a property that a part of the view model represents
to the user. A view model might have multiple models if it is a combination of several models.
To use the mapping features, the following attributes are very important:
ModelAttribute - declare a model in a view model
ViewModelToModelAttribute - declare a mapping from a view model property to a model property
In Catel 4.0 a new mapping mechanism is introduced that makes it possible to convert types of properties of the mappings between the Model an
d ViewModel. It is also possible to map to a collection of properties to a single property as result (like MultiBinding and Converter in WPF).
To use new mechanism you should declare this attributes:
ConverterType - declare a type of converter that converts properties, converter should implement IViewModelToModelConverter. It is
recommended to use ViewModelToModelConverterBase as base class for custom converters. The default converter used is DefaultView
ModelToModelMappingConverter that provides basic 1:1 mappings between the model and view model.
AdditionalConstructorArgs - declare a arguments witch would be passed to converter constructor via reflection
AdditionalPropertiesToWatch - declare properties, which changes would trigger the converter

Code snippets
vm - declare a view model
vmpropmodel - declare a property as model on a view model
vmpropviewmodeltomodel - declare a property as a pass-through property on a view model"

Explanation
Defining a model is very simple, you only have to decorate your property with the ModelAttribute:

/// <summary>
/// Gets or sets the person.
/// </summary>
[Model]
public IPerson Person
{
get { return GetValue<IPerson>(PersonProperty ); }
private set { SetValue(PersonProperty , value); }
}
/// <summary>
/// Register the Person property so it is known in the class.
/// </summary>
public static readonly PropertyData PersonProperty = RegisterProperty("Person",
typeof(IPerson));

Using the ModelAttribute is very powerful. Basically, this is the extended functionality in the view model. If the model supports IEditableObject, Be
ginEdit is automatically called in the initialization of the view model. When the view model is canceled, the CancelEdit is called so the changes are

undone.
When a model is defined, it is possible to use the ViewModelToModelAttribute, as you can see in the code below:

/// <summary>
/// Gets or sets the FirstName of the person.
/// </summary>
[ViewModelToModel("Person")]
public string FirstName
{
get { return GetValue<string>(FirstNameProperty); }
set { SetValue(FirstNameProperty, value); }
}
/// <summary>
/// Register the FirstName property so it is known in the class.
/// </summary>
public static readonly PropertyData FirstNameProperty = RegisterProperty("FirstName",
typeof(string));
/// <summary>
/// Gets or sets the LastName of the person.
/// </summary>
[ViewModelToModel("Person")]
public string LastName
{
get { return GetValue<string>(LastNameProperty); }
set { SetValue(LastNameProperty, value); }
}
/// <summary>
/// Register the LastName property so it is known in the class.
/// </summary>
public static readonly PropertyData LastNameProperty = RegisterProperty("LastName",
typeof(string));

The ViewModelToModelAttribute in the code example above automatically maps the view model FirstName and LastName properties to the Pers
on.FirstName and Person.LastName properties. This way, you dont have to manually map the values from and to the model. Another nice effect
is that the view model automatically validates all objects defined using the ModelAttribute, and all field and business errors mapped are
automatically mapped to the view model.
Sometimes you need the full name of a person, you can easily acquire it by creating a custom converter:

public class CollapsMappingConverter : DefaultViewModelToModelMappingConverter


{
#region Fields
private readonly char _separator;
#endregion
#region Constructors
public CollapsMappingConverter(string[] propertyNames)
: this(propertyNames, ' ')
{ }
public CollapsMappingConverter(string[] propertyNames, char separator = ' ')
: base(propertyNames)
{
_separator = separator;
}
#endregion
#region Properties
public char Separator
{
get { return _separator; }
}
#endregion
#region Methods
public override bool CanConvert(Type[] types, Type outType, Type
viewModelType)
{
return types.All(x => x == typeof (string)) && outType == typeof (string);
//check that all input and output values are strings
}
public override object Convert(object[] values, IViewModel viewModel)
{
return string.Join(Separator.ToString(), values.Where(x =>
!string.IsNullOrWhiteSpace((string) x)));
}
public override bool CanConvertBack(Type inType, Type[] outTypes, Type
viewModelType)
{
return outTypes.All(x => x == typeof (string)) && inType == typeof
(string); //check that all input and output values are strings
}
public override object[] ConvertBack(object value, IViewModel viewModel)
{
return ((string) value).Split(Separator);
}
#endregion
}

Now, when we created the converter we should define it in mapping like this:

/// <summary>
/// Gets or sets the FullName of the person.
/// </summary>
[ViewModelToModel("Person", "FirstName", AdditionalPropertiesToWatch = new[] {
"LastName" }, ConverterType = typeof(CollapsMappingConverter))]
public string FullName
{
get { return GetValue<string>(FullNameProperty); }
set { SetValue(FullNameProperty, value); }
}
/// <summary>
/// Register the LastName property so it is known in the class.
/// </summary>
public static readonly PropertyData FullNameProperty = RegisterProperty("FullName",
typeof(string));

The ViewModelToModelAttribute in the code example above automatically maps the view model FullName property to the Person.FirstName and
Person.LastName properties and converts them with CollapsMappingConverter. This way, you dont have to manually map the values from the
model and update FullName property when FirstName or LastName property changed.
Summarized, the Model and ViewModelToModel attributes make sure no duplicate validation and no manual mappings are required.

Mapping properties from view to view model


Sometimes a view (for example, a user control) contains additional properties besides the DataContext to interact with the view model. By default,
it is hard to implement this in an MVVM sccenario, but Catel solves this issue using the ViewToViewModel attribute.
This attribute automatically keeps track of changes in both the view and the view model and this way, a control can have several properties and
still implement MVVM.

Example implementation
The example below shows how the MapCenter is a dependency property on the control. It automatically maps the property to the ViewModel.Map
Center property.

public partial class MyControl : UserControl


{
public MyControl()
{
InitializeComponent();
}
[ViewToViewModel(MappingType = ViewToViewModelMappingType.ViewModelToView)]
public GeoCoordinate MapCenter
{
get { return (GeoCoordinate) GetValue(MapCenterProperty); }
set { SetValue(MapCenterProperty, value); }
}
// Using a DependencyProperty as the backing store for MapCenter. This enables
animation, styling, binding, etc...
public static readonly DependencyProperty MapCenterProperty =
DependencyProperty.Register("MapCenter", typeof (GeoCoordinate),
typeof (MyControl), new PropertyMetadata(null, (sender, e) => ((MyControl)
sender).UpdateMapCenter()));
private void UpdateMapCenter()
{
map.SetView(ViewModel.MapCenter, ViewModel.ZoomLevel);
}
public new MainPageViewModel ViewModel
{
get { return base.ViewModel as MainPageViewModel; }
}
}

Important note starting with Catel 4.0


Starting with 4.0, Catel no longer subscribes to dependency properties automatically. It is best to let Catel only subscribe to the properties that it
should (for the best performance). To do so, use the IViewPropertySelector.AddPropertyToSubscribe method to add properties:

var serviceLocator = ServiceLocator.Default;


var viewPropertySelector = serviceLocator.ResolveType<IViewPropertySelector>();
viewPropertySelector.AddPropertyToSubscribe("MyProperty", typeof(MyView));

In most cases, the only reason to subscribe to property changes is because of the ViewToViewModel attribute. If that is the case, it is best to use
the extension method AutoDetectViewPropertiesToSubscribe in the static constructor of the view:

static MyView()
{
typeof(MyView).AutoDetectViewPropertiesToSubscribe();
}

Mapping types

Catel supports the following mapping types using the ViewToViewModelMappingType enum.
Type

Description

TwoWayDoNothing

Two way, which means that either the view or the view model will update the values of the other party as soon as
they are updated.
When this value is used, nothing happens when the view model of the view changes. This way, it might be possible
that the values of the view and the view model are different. The first one to update next will update the other.

TwoWayViewWins

Two way, which means that either the view or the view model will update the values of the other party as soon as
they are updated.
When this value is used, the value of the view is used when the view model of the view is changed, and is directly
transferred to the view model value

TwoWayViewModelWins

Two way, which means that either the view or the view model will update the values of the other party as soon as
they are updated.
When this value is used, the value of the view model is used when the view model of the view is changed, and is
directly transferred to the view value.

ViewToViewModel

The mapping is from the view to the view model only.

ViewModelToView

The mapping is from the view model to the view only.

Nested view models


For more information on this topic, see nested user controls.

Validation in view models


Validation is very important to provide both feedback to the user, but also to make sure that no invalid data reaches the model or database. Catel
offers several ways to implement validation. All options are described in this part of the documentation.
Validation in models via mappings
Mapping via ViewModelToModelAttribute
Mapping via ExposeAttribute
Validation in view models
Validating fields
Validating business rules
Translating model validation in the view model
Validating via annotations
To validate required fields or not to validate required fields at startup

Validation in models via mappings


The best way is to put validation into a model. Most model objects nowadays implement INotifyPropertyChanged and IDataErrorInfo, the most
important classes that are required to use mappings from/to a model inside a view model.
The great advantage of mapping properties from/to models automatically using Catel is that you don't have to write lots of plumbing yourself
(getting and setting values in the model and view model). However, if the model implements INotifyPropertyChanged and IDataErrorInfo, Catel
also automatically uses the validation from the model. For example, if there is a Person model that checks if the FirstName and LastName are
entered, why rewrite this validation again in the view model?
There are two ways to use automatic mappings.

Mapping via ViewModelToModelAttribute


Mapping a model property by using the ViewModelToModelAttribute requires the definition of a model property and a separate property per
mapped property. The code below automatically maps the FirstName property.

/// <summary>
/// Gets or sets the person.
/// </summary>
[Model]
public Person Person
{
get { return GetValue<Person>(PersonProperty); }
private set { SetValue(PersonProperty, value); }
}
/// <summary>
/// Register the Person property so it is known in the class.
/// </summary>
public static readonly PropertyData PersonProperty = RegisterProperty("Person",
typeof(Person));

/// <summary>
/// Gets or sets the first name.
/// </summary>
[ViewModelToModel("Person")]
public string FirstName
{
get { return GetValue<string>(FirstNameProperty); }
set { SetValue(FirstNameProperty, value); }
}

/// <summary>
/// Register the FirstName property so it is known in the class.
/// </summary>
public static readonly PropertyData FirstNameProperty = RegisterProperty("FirstName",
typeof(string));

If the Person.FirstName provides an error via the IDataErrorInfo interface, it will automatically be exposed by the view model as well.

Mapping via ExposeAttribute


Mapping a property via the ExposeAttribute is even more simple, but has some disadvantages. First, let's talk about the disadvantages before
showing the code:
1. Catel uses the ICustomTypeDescriptor interface to implement this behavior, and the interface is only available in WPF.
2. The properties are not actually created, so you cannot use them inside your view model as real properties.
In other words, the ExposeAttribute is only very useful if 1) you are using WPF and 2) if the property is not used inside the view model but only
declared to protect the model from the outside world. If both of these constraints are true, then the ExposeAttribute is definitely worth taking a look
at. The usage is very simple:

/// <summary>
/// Gets or sets the person.
/// </summary>
[Model]
[Expose("FirstName")]
[Expose("MiddleName")]
[Expose("LastName")]
private Person Person
{
get { return GetValue<Person>(PersonProperty); }
set { SetValue(PersonProperty, value); }
}
/// <summary>
/// Register the Person property so it is known in the class.
/// </summary>
public static readonly PropertyData PersonProperty = RegisterProperty("Person",
typeof(Person));

Simply declare the model property and decorate it with one or multiple ExposeAttribute instances. Not only are the properties automatically
available for binding, the view model also checks for errors and automatically maps these as well.

Validation in view models


Until now, we only spoke about automatic validation for validation that was written in the model. However, sometimes it is required to write
validation inside the view model as well. One reason might be that the model is a POCO object not providing any validation. Or, sometimes there
is a logical error that has nothing to do with the model, but should be shown to the user anyway.
In such a case, Catel offers lots of possibilities to write custom validation inside the view model. Below are the possibilities:
Field warnings
Field errors
Business rule warnings
Business rule errors
The difference between a field and business rule is that a field error or warning is specific for a property. These are returned via IDataErrorInfo["pr
opertyName"]. A business rule is a rule that applies to multiple fields or even a whole entity. Business rule validations are returned via IDataErrorI
nfo.Error.
To implement validation into a view model, only two methods need to be implemented. Catel clearly separates the field validation from the
business rule validation to make it much clearer to the developer what is going on.

Validating fields
To validate fields, one should override the ValidateFields method. Below is an example of field validation on a view model:

/// <summary>
/// Validates the field values of this object. Override this method to enable
/// validation of field values.
/// </summary>
/// <param name="validationResults">The validation results, add additional results to
this list.</param>
protected override void ValidateFields(List<IFieldValidationResult> validationResults)
{
if (!string.IsNullOrEmpty(FirstName))
{
validationResults.Add(FieldValidationResult.CreateError(FirstNameProperty,
"First name cannot be empty"));
}
}

Validating business rules


To validate business rules, one should override the ValidateBusinessRules method. Below is an example of business rule validation on a view
model:

/// <summary>
/// Validates the field values of this object. Override this method to enable
/// validation of field values.
/// </summary>
/// <param name="validationResults">The validation results, add additional results to
this list.</param>
protected override void ValidateBusinessRules(List<IBusinessRuleValidationResult>
validationResults)
{
if (SomeBusinessErrorOccurs)
{
validationResults.Add(BusinessRuleValidationResult.CreateError("A business
error occurred"));
}
}

Translating model validation in the view model


Thanks to the validation system in Catel, it is very easy to implement very advanced validation features in view models. The example below
shows how to translate errors that are added to a model in the Data Access Layer or validation layer. Assume that the following pseudo code is
used to set an error on a model in the DAL:

SetFieldError(FirstName, FirstNameRequired);

All errors that are mapped from the model to the view model automatically are available in the validationResults parameter. This way, the error
can be easily translated:

/// <summary>
/// Validates the field values of this object. Override this method to enable
/// validation of field values.
/// </summary>
/// <param name="validationResults">The validation results, add additional results to
this list.</param>
protected override void ValidateFields(List<IFieldValidationResult> validationResults)
{
foreach (var validationResult in validationResults)
{
if (validationResult.Message == "FirstNameRequired")
{
validationResult.Message = Properties.Resources.FirstNameRequired;
}
}
}

Of course this is not something you want to actually do in your view model, so youll probably have to write a helper class that translates the
validation for you. You might or might not like delaying the translation of the model errors to as close as the view, but it shows how extremely
powerful the improved validation of Catel is. And if you think a bit about it, wouldn't it be a good idea to delay the translation from the server to the
actual client to as close as the view?

Validating via annotations


Some people like to add validation to their (view)models using annotations (attributes). Catel also supports this method, but adds additional
functionality. The idea behind it is that in the end, Catel always provides all errors of an object via the IDataErrorInfo interface. This means that
when attribute validation is used, the errors are internally registered and provided in the ValidateFields method. This way, all types of validation
that are provided by the .NET framework are gathered into one single location where they can be used by the view.

/// <summary>
/// Gets or sets the first name.
/// </summary>
[Required("This value is required")]
private string FirstName
{
get { return GetValue<string>(FirstNameProperty); }
set { SetValue(FirstNameProperty, value); }
}
/// <summary>
/// Register the FirstName property so it is known in the class.
/// </summary>
public static readonly PropertyData FirstNameProperty= RegisterProperty("FirstName",
typeof(string));

To validate required fields or not to validate required fields at startup


Catel does not validate the properties with data annotations at startup. It will only validate the data annotations when properties change or when
the view model is about to be saved. This is implemented this way to allow a developer to show required fields with an asterisk (*) instead of
errors. If a developer still wants to initially display errors, only a single call has to be made in the constructor:

Validate(true, false);

Advanced view models


This section contains advanced topics about view models.
Keeping view models alive
Exposing properties of a model automatically
Determine the view model type dynamically at runtime
Controlling the instantiation of view models

Keeping view models alive


In Catel, view models are automatically closed when the UserControl is unloaded from the visual tree. This is because there is no guarantee that
the control will be loaded again. This works great in most of the cases, but sometimes you need more control about the lifetime of the view model.
One good example is the use of the TabControl. When a tab control contains a user control with a view model, every time a new tab is selected,
the controls on the previously selected tab are unloaded (and thus the view models are closed).
Also see the TabControl that is available in Catel

It is possible to have more control about the lifetime of view models. To keep a view model alive, even when the view is unloaded, set the CloseVi
ewModelOnUnloaded property of the UserControl to false in the constructor of the view:

CloseViewModelOnUnloaded = false;

The view model will now be re-used when the view is loaded into the visual tree again.
Keep in mind that the developer is responsible for actually closing the view model

The Catel Examples repository contains an example demonstrating controlling the lifetime of view models

Exposing properties of a model automatically


Note that starting with Catel 3.8, this feature is part of Catel.Fody which brings support for this feature on all platforms. More information
can be found here.
Starting with Catel 2.2, a new attribute called ExposeAttribute is introduced. One of the features that already existed in Catel before is the ViewMo
delToModelAttribute. The goal of these attributes is to easily map properties from a model to the view model so as much of the plumbing
(setting/getting properties, rechecking validation, etc) is done automatically for the developer.
This feature is only available in WPF because Silverlight does not provide the ICustomTypeDescriptor or an equivalent feature

Using the ViewModelToModelAttribute, this is the syntax to map properties automatically:

/// <summary>
/// Gets or sets the person.
/// </summary>
[Model]
public Person Person
{
get { return GetValue<Person>(PersonProperty); }
private set { SetValue(PersonProperty, value); }
}
/// <summary>
/// Register the Person property so it is known in the class.
/// </summary>
public static readonly PropertyData PersonProperty = RegisterProperty("Person",
typeof(Person));
/// <summary>
/// Gets or sets the first name.
/// </summary>
[ViewModelToModel("Person")]
public string FirstName
{
get { return GetValue<string>(FirstNameProperty); }
set { SetValue(FirstNameProperty, value); }
}
/// <summary>
/// Register the FirstName property so it is known in the class.
/// </summary>
public static readonly PropertyData FirstNameProperty = RegisterProperty("FirstName",
typeof(string));

However, if you only define the FirstName property just to protect your model, then why should you define the whole property? This is where the E
xposeAttribute property comes in very handy. This attribute internally registers a new dynamic property on the view model, and then uses the
same technique as the ViewModelToModelAttribute.
Below is the new way you can easily expose properties of a model and protect other properties of the model from the view:

/// <summary>
/// Gets or sets the person.
/// </summary>
[Model]
[Expose("FirstName")]
[Expose("MiddleName")]
[Expose("LastName")]
private Person Person
{
get { return GetValue<Person>(PersonProperty); }
set { SetValue(PersonProperty, value); }
}
/// <summary>
/// Register the Person property so it is known in the class.
/// </summary>
public static readonly PropertyData PersonProperty = RegisterProperty("Person",
typeof(Person));

So, this is a very cool feature that allows you to protect your model without having to re-define all the properties on the view model. Also, the
validation in the model is automatically synchronized with the view model when you use this attribute.

Determine the view model type dynamically at runtime


Starting with Catel 3.1, it is possible to determine the view model type of a view dynamically at runtime. This sounds complex, but let's bring up a
user scenario which a user came up with:
I have a shape view and a ShapeBaseViewModel. Then, I have models such as Rectangle, Circle, etc, and each model has its own view model
(RectangleViewModel, CircleViewModel, etc). How can I solve this issue using Catel?
This case proves that it should be at least possible to determine the type of the view model of a view, based on the DataContext of a view.
Note that this feature is available on all controls an behaviors, not only for the UserControl

How to dynamically determine the view model type using a UserControl


Determining the view model dynamically when using the UserControl is extremely easy. You can override the GetViewModelType(object) method
like this:

protected override Type GetViewModelType(object dataContext)


{
if (dataContext is Rectangle)
{
return typeof (RectangleViewModel);
}
if (dataContext is Circle)
{
return typeof (CircleViewModel);
}
return null;
}

When the method returns null, it will fall back on the earlier determined view model type.

How to dynamically determine the view model using a behavior


Determining the view model dynamically when using behaviors must be done via the DetermineViewModelType event like this:

mvvmBehavior.DetermineViewModelType += (sender, e) =>


{
if (e.DataContext is Rectangle)
{
e.ViewModelType = typeof (RectangleViewModel);
}
if (e.DataContext is Circle)
{
e.ViewModelType = typeof(CircleViewModel);
}
};

There is no need to set the e.ViewModelType to null because that is the default value.

Controlling the instantiation of view models

Starting with Catel 3.1, it is possible to take control of the view model instantiation of a view dynamically at runtime. This feature can be used
when the construction of a view model is more complex than injecting the datacontext as model, or when the view model instance in a custom
repository should be re-used.
How to control the view model instantiation using the IViewModelFactory
How to control the view model instantiation using a UserControl
How to control the view model instantiation using a behavior
Preventing the logic to create a view model by itself
Note that this feature is available on all controls an behaviors, not only for the UserControl

How to control the view model instantiation using the IViewModelFactory


The IViewModelFactory is the best way to customize the instantiation of view models in Catel. This allows full control for all view models because
the factory will be used to create all view models, except when any other methods described below are used.
If customization of the view model instantiation is required, it is best the derive from the default ViewModelFactory class to be able to fall back to
the default behavior in non-special cases.

public class CustomViewModelFactory : ViewModelFactory


{
public override IViewModel CreateViewModel(Type viewModelType, object dataContext)
{
if (viewModelType == typeof(MySpecialViewModel))
{
// Use custom constructor with dependency injection
return new MySpecialViewModel(dep1, dep2, dep3, dataContext);
}
// Fall back to default behavior
return base.CreateViewModel(viewModelType, dataContext);
}
}

When a custom factory is used, it is important to register it in the ServiceLocator:

ServiceLocator.Default.RegisterType<IViewModelFactory, CustomViewModelFactory>();

How to control the view model instantiation using a UserControl


Note that it is best to use the IViewModelFactory for view model instantation because it is a more generic solution

Controlling the instantiation of the view model dynamically when using the UserControl is extremely easy. You can override the GetViewModelInst
ance(object) method like this:

protected override IViewModel GetViewModelInstance(object dataContext)


{
if (dataContext is Rectangle)
{
return new RectangleViewModel((Rectangle)dataContext);
}
return null;
}

When the method returns null, the logic will try to construct the view model by itself.

How to control the view model instantiation using a behavior


Note that it is best to use the IViewModelFactory for view model instantation because it is a more generic solution

Controlling the instantiation of the view model dynamically when using behaviors must be done via the DetermineViewModelInstance event like
this:

mvvmBehavior.DetermineViewModelInstance += (sender, e) =>


{
var dataContext = e.DataContext;
if (dataContext is Rectangle)
{
e.ViewModel = new RectangleViewModel((Rectangle)dataContext);
}
};

There is no need to set the e.ViewModel to null because that is the default value.

Preventing the logic to create a view model by itself


When using the behavior, it is possible to prevent the logic to instantiate a view model. In this case, it is really possible to have full control over
view model instantiation. To prevent the logic to create a view model, use this code:

mvvmBehavior.DetermineViewModelInstance += (sender, e) =>


{
var dataContext = e.DataContext;
if (dataContext is Rectangle)
{
e.ViewModel = new RectangleViewModel((Rectangle)dataContext);
}
e.DoNotCreateViewModel = true;
};

Views
Views are what the user actually sees on the screen. The views communicate with the view models. The MVVM Framework that ships with Catel
can be used on its own. However, the framework requires some conventions that you, as end-user of Catel, should not be worrying about.
Therefore, Catel ships with both a UserControl and a Window that fully support the MVVM Framework. Those can both be used as base classes
for all controls and windows developed in an application.

Android
iOS
XAML
Tips & tricks

Android
Bindings
Binding properties
Binding properties with events
Binding properties with converters
Binding commands
You might also be interested in:
Activities (pages)
Fragments (user controls)
Note that this guide is not a full Android development guide. It will cover the basics though.

Bindings
Unfortunately Android does not have a powerful binding system like XAML does. Therefore it is required to manually synchronize data from the
view to the view model and back or to use the binding system in Catel.

Binding properties

[Activity]
public class SecondActivity : Catel.Android.App.Activity
{
private PersonView _personView;
protected override void OnCreate(Bundle bundle)
{
base.OnCreate(bundle);
// Set our view from the "main" layout resource
SetContentView(Resource.Layout.Page_Second);
_personView = FragmentManager.FindFragmentById<PersonView>(Resource.Id.PersonView);
}
protected override void AddBindings(BindingContext bindingContext, IViewModel
viewModel)
{
var vm = (SecondViewModel) viewModel;
bindingContext.AddBinding(() => vm.Title, () => Title);
bindingContext.AddBinding(() => vm.Person, () => _personView.DataContext);
}
}

Binding properties with events

public class PersonView : Catel.Android.App.Fragment


{
private EditText _firstNameEditText;
private EditText _lastNameEditText;
private TextView _lastNameMirrorTextView ;
public override View OnCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState)
{
var inflateResult = inflater.Inflate(Resource.Layout.Fragment_Person, container,
false);
return inflateResult;
}
public override void OnResume()
{
_firstNameEditText = Activity.FindViewById<EditText>(Resource.Id.firstNameText);
_lastNameEditText = Activity.FindViewById<EditText>(Resource.Id.lastNameText);
_lastNameMirrorTextView =
Activity.FindViewById<TextView>(Resource.Id.lastNameMirrorTextView);
base.OnResume();
}
protected override void AddBindings(BindingContext bindingContext, IViewModel
viewModel)
{
var vm = (PersonViewModel)viewModel;
bindingContext.AddBinding(() => vm.FirstName, () =>
_firstNameEditText.Text).AddTargetEvent("TextChanged");
bindingContext.AddBinding(() => vm.LastName, () =>
_lastNameEditText.Text).AddTargetEvent("TextChanged");
bindingContext.AddBinding(() => vm.LastName, () => _lastNameMirrorTextView.Text,
BindingMode.OneWay);
}
}

Binding properties with converters

protected override void AddBindings(BindingContext bindingContext, IViewModel


viewModel)
{
var vm = (MainViewModel)viewModel;
bindingContext.AddBindingWithConverter<ClicksConverter>(() => vm.Counter, () =>
_testButton.Text, BindingMode.OneWay);
}

Binding commands

protected override void AddBindings(BindingContext bindingContext, IViewModel


viewModel)
{
var vm = (MainViewModel)viewModel;
bindingContext.AddCommandBinding(_testButton, "Click", vm.RunCommand);
}

Activities (pages)
The user controls in Android are called fragments. This means that if a user control must be created, it must derive from the Fragment class.
Catel provides a base implementation of this class to ensure full compatibility with the MVVM framework that ships with Catel.
Creating the view model
Creating the view
Designing the view
Setting up synchronization

Creating the view model


The view model can be created (or added as a linked file from another project) just like any platform using Catel (they are all equal on all
platforms).

Creating the view


Make sure that a Views folder exists in the project so the views and view models can automatically be hooked together by Catel. Then create
a new class to the views folder, in this case MainActivity:

[Activity(MainLauncher = true)]
public class MainActivity : Catel.Android.App.Activity
{
protected override void OnCreate(Bundle bundle)
{
base.OnCreate(bundle);
// Set our view from the "main" layout resource
SetContentView(Resource.Layout.Page_Main);
}
}

Note that the class derives from Catel.Android.App.Activity

Designing the view


To create the actual user interface of the fragment, add a new axml file to the Resources/layout folder, in your case Page_Main (but you can
name it whatever you want). Then use the following source:

<?xml version="1.0" encoding="utf-8"?>


<LinearLayout
xmlns:android="http://schemas.android.com/apk/res/androi
d"
android:orientation="vertical"
android:layout_width="fill_parent"
android:layout_height="fill_parent">
<Button
android:id="@+id/MyButton"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:text="@string/Hello" />
</LinearLayout>

Setting up synchronization
In Android it is required to manually synchronize the values between the view and view model. Below is the fully extended MainActivity class
containing these mapping functionality:

[Activity(MainLauncher = true)]
public class MainActivity : Catel.Android.App.Activity
{
private Button _testButton;
protected override void OnCreate(Bundle bundle)
{
base.OnCreate(bundle);
// Set our view from the "main" layout resource
SetContentView(Resource.Layout.Page_Main);
// Note: at this stage the visual tree is guaranteed in Android
_testButton = FindViewById<Button>(Resource.Id.MyButton);
_testButton.Click += delegate {
GetViewModel<MainViewModel>().RunCommand.Execute(); };
}
protected override void SyncViewModel()
{
var vm = GetViewModel<MainViewModel>();
if (vm == null)
{
return;
}
Title = vm.Title;
_testButton.Text = string.Format("{0} clicks!", vm.Counter);
}
}

Fragments (user controls)


The user controls in Android are called fragments. This means that if a user control must be created, it must derive from the Fragment class.
Catel provides a base implementation of this class to ensure full compatibility with the MVVM framework that ships with Catel.
Creating the view model
Creating the view
Designing the view
Setting up synchronization

Creating the view model


The view model can be created (or added as a linked file from another project) just like any platform using Catel (they are all equal on all
platforms).

Creating the view


Make sure that a Views folder exists in the project so the views and view models can automatically be hooked together by Catel. Then create
a new class to the views folder, in this case PersonView:

public class PersonView : Catel.Android.App.Fragment


{
public override View OnCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState)
{
var inflateResult = inflater.Inflate(Resource.Layout.Fragment_Person, container,
false);
return inflateResult;
}
}

Note that the class derives from Catel.Android.App.Fragment

Designing the view


To create the actual user interface of the fragment, add a new axml file to the Resources/layout folder, in your case Fragment_Person (but
you can name it whatever you want). Then use the following source:

<?xml version="1.0" encoding="utf-8"?>


<LinearLayout
xmlns:android="http://schemas.android.com/apk/res/androi
d"
android:orientation="vertical"
android:layout_width="fill_parent"
android:layout_height="fill_parent">
<TextView
android:text="First name"
android:textAppearance="?android:attr/textAppearanceMedi
um"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:id="@+id/textView1" />
<EditText
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:id="@+id/firstNameText" />
<TextView
android:text="Last name"
android:textAppearance="?android:attr/textAppearanceMedi
um"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:id="@+id/textView2" />
<EditText
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:id="@+id/lastNameText" />
</LinearLayout>

Setting up synchronization
In Android it is required to manually synchronize the values between the view and view model. Below is the fully extended PersonView class
containing these mapping functionality:

public class PersonView : Catel.Android.App.Fragment


{
public override View OnCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState)
{
var inflateResult = inflater.Inflate(Resource.Layout.Fragment_Person, container,
false);
return inflateResult;
}
public override void OnActivityCreated(Bundle savedInstanceState)
{
base.OnActivityCreated(savedInstanceState);
// Note: at this stage the visual tree is guaranteed in Android
_firstNameEditText = Activity.FindViewById<EditText>(Resource.Id.firstNameText);
_lastNameEditText = Activity.FindViewById<EditText>(Resource.Id.lastNameText);
}
protected override void SyncViewModel()
{
var vm = GetViewModel<PersonViewModel>();
if (vm == null)
{
return;
}
_firstNameEditText.Text = vm.FirstName;
_lastNameEditText.Text = vm.LastName;
}
}

iOS
You might also be interested in:

XAML
This section contains the XAML related views.
Window and DataWindow
UserControl
MVVM behaviors
Validation controls
Using external controls
Advanced information about views
Customizing DataContext subscription behavior

Window and DataWindow


Introduction to the Window
Introduction to the DataWindow
Using the DataWindow in MVVM
Construction of view models

Automatic validation
Customizing the buttons
Styling the DataWindow

Introduction to the Window


The Window is a simplified class representing the same logic as the regular System.Windows.Window but with the binding support of Catel.

Introduction to the DataWindow


When developing software in WPF or Silverlight, most developers always need the following three types of windows:
OK / Cancel buttons for data windows;
OK / Cancel / Apply buttons for application settings / options;
Close button on windows for action windows.
Creating these windows is just boring and the steps are always the same:
The DataWindow class makes it much easier to create these basic windows, simply by specifying the mode of the Window. By using this window,
you can concentrate on the actual implementation and you dont have to worry about the implementation of the buttons itself, which saves you
time!

Using the DataWindow in MVVM


The easiest object to use with the MVVM Framework is the DataWindow class. The DataWindow takes fully care of the construction of the view
models and the validation of the view models.
The usage of the DataWindow class is very simple, once you know how to do it. First of all, you will have to specify the base class in the xaml file
like shown below:

<catel:DataWindow x:Class="Catel.Articles._03___MVVM.Examples.DataWindow.PersonWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:catel="http://catel.codeplex.com">
<!-- Content left out for the sake of simplicity -->
</catel:DataWindow>

As you can see, one thing has changed in regard to a normal window definition:
1. The type definition has changed from Window to catel:DataWindow;
The code-behind is even simpler:

/// <summary>
/// Interaction logic for PersonWindow.xaml
/// </summary>
public partial class PersonWindow : DataWindow
{
/// <summary>
/// Initializes a new instance of the <see cref="PersonWindow"/> class.
/// </summary>
/// <param name="viewModel">The view model.</param>
public PersonWindow(PersonViewModel viewModel)
: base(viewModel)
{
InitializeComponent();
}
}

The code above is everything you will need when using the MVVM Framework of Catel.
The easiest way to create a new DataWindow is to use item templates

Construction of view models


There are multiple ways to construct a window with a view model. There are three options that you have to construct a view model:
Constructor with view model
This is the best option you can use. This way, it is possible to inject view models into the data window.
Constructor with model
It is possible to save a developer from creating a view model manually by accepting a model as input. Then, the data window will have to
construct the view model manually and pass it through to its base constructor.
Empty constructor
If you use an empty constructor, the developer will have to set the data context manually. This something you really should avoid. But
hey, its all up to you.

Automatic validation
The cool thing about the DataWindow is that is automatically wraps the content that a developer defines into an InfoBarMessageControl. This
way, errors and warnings are shown at the top of the window. Another feature of the DataWindow is that is automatically creates a WarningAndEr
rorValidator control and sets the view model as source. This way, all the warnings of the view model are also shown in the InfoBarMessageContro
l. In other words: you dont have to do anything to implementation validation, except for actually setting the warnings and errors in your view
model. And if the validation takes place in the model, you can use the ViewModelToModelAttribute so you dont have to worry about that either.

Customizing the buttons


It is possible to use custom buttons and still be able to use the DataWindow.
1. First, use the base constructor to specify that you want to use custom mode.

/// <summary>
/// Upload window.
/// </summary>
public class UploadWindow : DataWindow
{
public UploadWindow()
: base(DataWindowMode.Custom)
{
InitializeComponent();
}
}

2. Add the custom buttons. This must be done before the call to InitializeComponent.

/// <summary>
/// Upload window.
/// </summary>
public class UploadWindow : DataWindow
{
public UploadWindow()
: base(DataWindowMode.Custom)
{
AddCustomButton(new DataWindowButton("Upload", "Upload"));
InitializeComponent();
}
}

Styling the DataWindow


Starting with Catel 2.4, the DataWindow has its own styles. These are located in DataWindow.generic.xaml. Below is a table that contains the
available styles and a short description.
Style key

Description

DataWindowStyle

The actual window style which can be used to decorate or customize the window itself.

DataWindowButtonContainerStyle

The container that is used for the buttons. This is a WrapPanel, so the styles must match that.

DataWindowButtonStyle

The style for the buttons. By default, the buttons are right aligned and have a fixed size.

UserControl
The UserControl is a very interesting class of Catel, and fully shows the power of the MVVM Framework that ships with Catel. The user control is
able to fully integrate MVVM on a user control level and solves the nested user control problem, which is explained in detail a bit further in this
documentation.
Automatic construction without parameter
Automatic construction with parameter
Mapping properties from/to view model
Keeping view models alive

Automatic construction without parameter


It simplest thing to do is to create a view model that has an empty constructor (thus without parameters). If the UserControl is added to the visual
tree, the view model is instantly constructed and available for usage. A view model that is used inside a UserControl implementation is exactly the
same as the DataWindow implementation. This way, the developers dont have to worry about whether they can currently writing a view model
that is meant for a window or a control.

Automatic construction with parameter


A bit harder (its still very easy, dont worry), but much more powerful is the construction with a parameter. This way, a control is forced to use the
data context to create the view model. If there is no valid data context that can be used to construct the view model, no view model will be
constructed. This sounds a little abstract, but lets take a look to a more meaningful example.
Say, you want to write an application to manage company trees. The top-level of the data exists of a collection of Company objects (models). You
want to display the companies inside an ItemsControl, which is a very good way to represent the companies. But how are you going to display the
company details? You can simply create a template, but I wouldn't recommend that because the company representation can become very
complex (and dynamic), because it consists of Person objects that can have children (employees), and the children are person objects as well,
that can have children, etc. You might thing that this is a very simple scenario, which it actually is to make sure that all readers understand it
correctly. But, there can be a lot of complex tree scenarios. For example, for a client, I had to write a complete treatment overview of a patient,
which consists of a lot of different objects, which all have a child collection of other object types. Then you can save yourself with writing a simple
and generic data template. Below is a graphical form of the example:

Now comes the real power of UserControl in to play. For example, to show the company and its managers, one has to write an items control that
contains the companies and then a user control containing the details of the company. For the sake of simplicity, I will leave the employees out for
now. The usage might seem a bit complex, but once you get the hang of it, its actually quite simple. First of all, create a view model that has a
constructor of the model that you want to accept, in our case the Company class of which we will show the details:

/// <summary>
/// Initializes a new instance of the <see cref="CompanyViewModel"/> class.
/// </summary>
/// <param name="company">The company.</param>
public CompanyViewModel(Models.Company company)
: base()
{
// Store values
Company = company;
}

As you can see, the view model can only be constructed by passing a company model. This is quite normal, because how can we show details of
a non-existing (null) company? Now we have a view model, we can create our user control:

<catel:UserControl
x:Class="Catel.Articles._03___MVVM.Examples.UserControlWithParameter.Company"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:catel="http://catel.codeplex.com">
<!-- For the sake of simplicity, content is left out -->
</catel:UserControl>

Note that the class definition is now catel:UserControl instead of UserControl

The code behind is even simpler:

/// <summary>
/// Interaction logic for Company.xaml
/// </summary>
public partial class Company : UserControl
{
/// <summary>
/// Initializes a new instance of the <see cref="Company"/> class.
/// </summary>
public Company()
{
InitializeComponent();
}
}

Now the control is created (I dont want to focus on the actual control content here, since its not important), we can use the user control in our
main window that has a collection of companies. The view model also has a SelectedCompany property representing the selected company
inside the listbox. Then, we use the Company control and bind the data context to the SelectedCompany property:

<!-- Items control of companies -->


<ListBox Grid.Column="0" ItemsSource="{Binding CompanyCollection}"
SelectedItem="{Binding SelectedCompany}">
<ListBox.ItemTemplate>
<DataTemplate>
<StackPanel>
<Label Content="{Binding Name}" />
<Label Content="{Binding CEO.FullName}" />
</StackPanel>
</DataTemplate>
</ListBox.ItemTemplate>
</ListBox>
<!-- Company details -->
<UserControlWithParameter:Company Grid.Column="1" DataContext="{Binding
SelectedCompany}" />

As the code shows, there is a listbox containing all the companies. The data context of the user control is bound to the SelectedCompany. The
cool thing is that as soon as a company is selected, the user control will create an instance of the CompanyViewModel because it accepts a Com
pany instance in the constructor. The screenshot of the example application will (hopefully) give more insight in what change is causing the exact
view model creation:

In the image above, you see 2 controls. The first one is an items control that binds to the CompaniesViewModel because the window represents
list of companies. The second one is the CompanyControl, which dynamically constructs the CompanyViewModel as soon as a company is
selected at the left. This means that for every company selection, and new view model is constructed. This way, you can handle the saving,
canceling and closing of the view model before the next is view model is constructed.
The best thing about this is that you can actually start re-using user controls throughout your whole application. Instead of having the main view
model have to define all the properties of (sub) controls, now each control has its own view model, and you dont have to worry about the
implementation in the parent of a control. Simply set the data context of the user control to the right type instance, and the user control will handle
the rest.
The easiest way to create a new UserControl is to use item templates

Mapping properties from/to view model


When developing custom user controls, you still want to use the power of MVVM, right? With Catel, all of this is possible. All other frameworks
require a developer to manually set the data context on a user control. Or what about mapping user control properties from/to the view model?
To map a property of a custom user control to a view model and back, the only thing a developer has to do is to decorate the dependency
property of the control with the ViewToViewModelAttribute. Normally, a developer has to build logic that subscribes to property changes of both
the view model and the control, and then synchronize all the differences. Thanks to the ViewToViewModelAttribute, the UserControl that ships
with Catel takes care of this. The usage of the attribute looks as follows:

[ViewToViewModel]
public bool MyDependencyProperty
{
get { return (bool)GetValue(MyDependencyPropertyProperty); }
set { SetValue(MyDependencyPropertyProperty, value); }
}
// Using a DependencyProperty as the backing store for MyDependencyProperty.
enables animation, styling, binding, etc...
public static readonly DependencyProperty MyDependencyPropertyProperty =
DependencyProperty.Register("MyDependencyProperty", typeof(bool),
typeof(MyControl), new UIPropertyMetadata(true));

This

By default, the attribute assumes that the name of the property on the view model is the same as the property on the user control. To specify a
different name, use the overload of the attribute constructor as shown in the following example:

[ViewToViewModel("MyViewModelProperty")]
public bool MyDependencyProperty
... (remaining code left out for the sake of simplicity)

In the first place, all of this looks fine enough. However, what should happen when the current view model of the control is replaced by another
instance? Or what if the developer only wants to map values from the control to the view model, but not back? By default, the view model will take
the lead when this attribute is used. This means that as soon as the view model is changed, the values of the control will be overwritten by the
values of the view model. If another behavior is required, the MappingType property of the attribute should be used:

[ViewToViewModel("MyViewModelProperty", MappingType =
ViewToViewModelMappingType.TwoWayControlWins)]
public bool MyDependencyProperty
... (remaining code left out for the sake of simplicity)

The table below explains the options in detail:


Enum value

Description

TwoWayDoNothing

Two way, which means that either the control or the view model will update the values of the other party as soon as
they are updated.
When this value is used, nothing happens when the view model of the user control changes. This way, it might be
possible that the values of the control and the view model are different. The first one to update next will update the
other.

TwoWayViewWins

Two way, which means that either the control or the view model will update the values of the other party as soon as
they are updated.
When this value is used, the value of the control is used when the view model of the user control is changed, and is
directly transferred to the view model value.

TwoWayViewModelWins

Two way, which means that either the control or the view model will update the values of the other party as soon as
they are updated.
When this value is used, the value of the view model is used when the view model of the user control is changed,
and is directly transferred to the control value.

ViewToViewModel

The mapping is from the control to the view model only.

ViewModelToView

The mapping is from the view model to the control only.

Keeping view models alive

The UserControl automatically closes view models in the Unloaded event. Reason for this is that there is no guarantee that the control will be
loaded again. However, this can have some negative side effects. On of this side effects is a user control shown as a tab in a tab control. One of
the behaviors of a tab control is that it unloads all non-active tabs from the visual tree. Therefore, the UserControl cancels and closes the view
model. However, the state of the tab is lost then as well.
To prevent this behavior, it is possible to keep view models alive when a user control is unloaded. This can be done by setting CloseViewModelO
nUnloaded to false. This way, the view model is not closed and will be re-used when the control is loaded again. The downside of this is that the
responsibility of closing and disposing the view model is now in the hands of the developer. A great way to make a difference between unloading
(tab switch) and closing is to create a close button on the tabs that will explicitly call ViewModel.CloseViewModel.

MVVM behaviors
Starting with Catel 2.0, it is possible to use the logic of the following controls as a behavior:
DataWindow => WindowBehavior
UserControl => UserControlBehavior
Page => NavigationPageBehavior
This means that you no longer have to derive user controls from the UserControl to use the ability to solve the nested user controls problem. Or, if
you are not happy with the endless possibilities of the DataWindow, why not just creating a custom one without having to think about the MVVM
integration.
WindowBehavior
UserControlBehavior
NavigationPageBehavior

WindowBehavior
The WindowBehavior class takes care of all the MVVM integrations of a window and a view model. So, where you previously had to derive a
Window implementation from DataWindow, you can now create a new Window like any application and then add this:
The Save and Cancel properties are not obligate, and need the format of [controlname].[event]. By default, the Click event is used, so if a button
(or another control that should respond using the Click event), the [controlname] is sufficient.

<i:Interaction.Behaviors>
<catel:WindowBehavior ViewModelType="viewmodels:DemoWindowViewModel"
Save="okButton.Click" Cancel="cancelButton.Click" />
</i:Interaction.Behaviors>

Seems too easy right? Well, it is really all you have to do.
This looks great, but why is there still a DataWindow with this terrific solution?
First of all, we have to think about all the people that are already using Catel. We don't want to break their code and provide backward
compatibility. Updates to the logic will be applied to both the behavior and the view base because the logic is located in a separate class. Also, the
DataWindow is truly a terrific class, which supports lots of customization and takes care of dumb generation of buttons and the InfoBarMessageC
ontrol.
For more information, check out the the Catel.Examples.WPF.AdvancedDemo which shows the differences

UserControlBehavior
The UserControlBehavior class takes care of all the MVVM integrations of a user control and a view model. So, where you previously had to
derive a UserControl implementation from UserControl, you can now create a new UserControl like any application and then add this:

<i:Interaction.Behaviors>
<catel:UserControlBehavior ViewModelType="viewmodels:DemoWindowViewModel" />
</i:Interaction.Behaviors>

This looks great, but why is there still a UserControl with this terrific solution?

First of all, we have to think about all the people that are already using Catel. We don't want to break their code and provide backward
compatibility. Also, the UserControl implements the IViewModelContainer interface which allows chained view models in a hierarchy. If you don't
need this, just go for the behavior. If you need hierarchy chains, either let the custom UserControl implement it or use the UserControl.
To support nested user controls and their validation, it is important to chain views together using the IViewModelContainer interface. You can
choose not to do this, but then it is important to disable SupportParentViewModelContainers for performance reasons (otherwise, the behavior will
keep searching the visual tree for the parent view model).
For more information, check out the the Catel.Examples.WPF.AdvancedDemo which shows the differences

NavigationPageBehavior
The NavigationPageBehavior class takes care of all the MVVM integrations of a page (used in navigation or browser based applications) and a
view model. So, where you previously had to derive a Page implementation from Page, you can now create a new Page like any application and
then add this:

<i:Interaction.Behaviors>
<catel:NavigationPageBehavior ViewModelType="viewmodels:DemoWindowViewModel" />
</i:Interaction.Behaviors>

This looks great, but why is there still a Page with this terrific solution?
First of all, we have to think about all the people that are already using Catel. We don't want to break their code and provide backward
compatibility. Also, the Page class comes with more default functionality that you might be interested in.
For more information, check out the the Catel.Examples.WPF.BrowserApplication which shows the differences

Validation controls
There are some very important controls in Catel which help with visualizing the validation results.
InfoBarMessageControl
WarningAndErrorValidator
Styling in DataWindow

InfoBarMessageControl
Ever wanted to show the details of error messages to your end-users? Then, the InfoBarMessageControl is the control to use! The control shows
a summary of all business and field errors provided by bindings on objects that implement the IDataErrorInfo interface.

In combination with the WarningAndErrorValidator control, the InfoBarMessageControl can even show field and business warnings for objects that
implement the IDataWarningInfo interface that ships with Catel.

<catel:InfoBarMessageControl>
<!-- Actual content here -->
</catel:InfoBarMessageControl>

The InfoBarMessageControl subscribes to the Validation class. This class is responsible for showing the red border around the controls that WPF
shows by default. Then, it requests the actual field error property of the data item. This is added to an internal collection of error messages, and
therefore the control is able to show the errors of all bindings.
When the WarningAndErrorValidator control is found as a child control, the InfoBarMessageControl also subscribes to the events exposed by the
WarningAndErrorValidator. The internal working of that control is explained later in this article. When a data object is subscribed via the WarningA
ndErrorValidator, the InfoBarMessageControl will also handle the warnings and business errors of that data object.

WarningAndErrorValidator
The WarningAndErrorValidator control is not visible to the end user. The only thing this control takes care of is to forward business errors and
warnings to controls that are interested in them. The only control that ships with Catel is the InfoBarMessageControl. Thanks to the WarningAndE
rrorValidator, the InfoBarMessageControl is able to show business errors and warnings to the end user.

<catel:WarningAndErrorValidator Source="{Binding MyObject}" />

The WarningAndErrorValidator needs to be placed inside an InfoBarMessageControl. The control then subscribes to all property changed events
to make sure it receives all change notifications. Then, on every property change, the control checks whether the sender either implements the ID
ataErrorInfo or IDataWarningInfo interfaces.
When an error or warning is found on the changed property, the control invokes the corresponding events so the InfoBarMessageControl can
show the right information. When an error or warning no longer exists in a model, a Removed event is invoked so the InfoBarMessageControl kno
ws that the error or warning should be removed from the summary.

Styling in DataWindow
A InfoBarMessageControl is automatically added to the DataWindow, if you want to use a different style for this InfoBarMessageControl, you
must override the default style, add your own InfoBarMessageControl and disable the default InfoBarMessageControl from the DataWindow.
1. Create a custom style based on the default style.
2. Change the x:Key from x:Key="{x:Type local:InfoBarMessageControl}" to x:Key="yourCustomStyleKey"
3. Set the InfoBarMessageControlGenerationMode to None

/// <summary>
/// Initializes a new instance of the <see cref="DataWindow"/> class.
/// </summary>
/// <param name="viewModel">The view model to inject.</param>
/// <remarks>
/// This constructor can be used to use view-model injection.
/// </remarks>
public DataWindow(DataWindowViewModel viewModel)
: base(viewModel, DataWindowMode.Custom, null,
DataWindowDefaultButton.None, true, InfoBarMessageControlGenerationMode.None)
{
InitializeComponent();
}

4. Add a new InfoBarMessageControl as root control to your DataWindow and set the style.

<catel:InfoBarMessageControl Style="{DynamicResource yourCustomStyleKey}">


<Grid>
<catel:WarningAndErrorValidator Source="{Binding}" />
//Your content
</Grid>
</catel:InfoBarMessageControl>

Using external controls


Catel ships with default controls and the DataWindow. However, some people rather use controls and windows from Telerik, DevExpress or some
other 3rd party controls. This is perfectly possible and it is pretty easy to let those external controls support MVVM in the "Catel way".
The logic can be implemented via the MVVM behaviors that ship with Catel. In fact, the DataWindow and UserControl of Catel also use these
behaviors to implement their logic.
Using a custom control
Using a custom window

Using a custom control


In this part of the documentation, the RadTabItem of Telerik will be used as an example on how to create a RadTabItem that behaves like the Use
rControl.
Creating the base class with behavior
Using the class

Creating the base class with behavior


The first thing to do is to create a new base class that accepts a view model type argument. In this example, we will call it TabItem (to make it as
"external control company independent" as possible). Below is the code for the control definition. The downside of xaml based applications is that
you cannot derive from controls or windows that have a partial class defined in xaml. Therefore, all controls and code must be initialized via code
as you can see in the code below.

/// <summary>
/// Base class for a control with the Catel mvvm behavior.
/// </summary>
public class TabItem : RadTabItem, IUserControl
{
private readonly UserControlLogic _logic;
private event EventHandler<EventArgs> _viewLoaded;
private event EventHandler<EventArgs> _viewUnloaded;
private event EventHandler<Catel.MVVM.Views.DataContextChangedEventArgs>
_viewDataContextChanged;
/// <summary>
/// Initializes a new instance of the <see cref="TabItem"/> class.
/// </summary>
public TabItem()
{
_logic = new UserControlLogic(this, viewModelType);
_logic.PropertyChanged += (sender, e) => PropertyChanged.SafeInvoke(this, e);
Loaded += (sender, e) => _viewLoaded.SafeInvoke(this);
Unloaded += (sender, e) => _viewUnloaded.SafeInvoke(this);
this.AddDataContextChangedHandler((sender, e) =>
_viewDataContextChanged.SafeInvoke(this, new
Catel.MVVM.Views.DataContextChangedEventArgs(e.OldValue, e.NewValue)));

SetBinding(RadTabItem.HeaderProperty, new Binding("Title"));


}
/// <summary>
/// Gets the view model that is contained by the container.
/// </summary>
/// <value>The view model.</value>
public IViewModel ViewModel
{
get { return _logic.ViewModel; }
}
/// <summary>
/// Occurs when a property on the container has changed.
/// </summary>
/// <remarks>
/// This event makes it possible to externally subscribe to property changes of a
<see cref="DependencyObject"/>
/// (mostly the container of a view model) because the .NET Framework does not
allows us to.
/// </remarks>
public event PropertyChangedEventHandler PropertyChanged;
/// <summary>
/// Occurs when the view is loaded.
/// </summary>
event EventHandler<EventArgs> IView.Loaded
{
add { _viewLoaded += value; }
remove { _viewLoaded -= value; }
}
/// <summary>
/// Occurs when the view is unloaded.
/// </summary>
event EventHandler<EventArgs> IView.Unloaded
{
add { _viewUnloaded += value; }
remove { _viewUnloaded -= value; }
}
/// <summary>
/// Occurs when the data context has changed.
/// </summary>
event EventHandler<Catel.MVVM.Views.DataContextChangedEventArgs>
IView.DataContextChanged
{
add { _viewDataContextChanged += value; }

remove { _viewDataContextChanged -= value; }


}
}

You would expect an abstract class here, but the designers (both Visual Studio and Expression Blend) can't handle abstract base
classes

Using the class


The class can now be used the same as the UserControl class. For more information, see UserControl explained.

Using a custom window


In this part of the documentation, the RadWindow of Telerik will be used as an example on how to create a WindowBase that behaves like the Dat
aWindow.

Creating the base class with behavior


The first thing to do is to create a new base class that accepts a view model type argument. In this example, we will call it WindowBase (to make it
as "external control company independent" as possible). Below is the code for the window definition. The downside of xaml based applications is
that you cannot derive from controls or windows that have a partial class defined in xaml. Therefore, all controls and code must be initialized via
code as you can see in the code below.
Because the RadWindow of Telerik does not close the window when the DialogResult is set, this window subscribes to the ViewModelC
losed event to close the window

/// <summary>
/// Base class for a window with the Catel mvvm behavior.
/// </summary>
public class Window : RadWindow, IDataWindow
{
private readonly WindowLogic _logic;
private event EventHandler<EventArgs> _viewLoaded;
private event EventHandler<EventArgs> _viewUnloaded;
private event EventHandler<Catel.MVVM.Views.DataContextChangedEventArgs>
_viewDataContextChanged;
public Window(IViewModel viewModel)
{
_logic = new WindowLogic(this, null, viewModel);
_logic.ViewModelChanged += (sender, e) => ViewModelChanged.SafeInvoke(this,
e);
_logic.PropertyChanged += (sender, e) => PropertyChanged.SafeInvoke(this, e);
Loaded += (sender, e) => _viewLoaded.SafeInvoke(this);
Unloaded += (sender, e) => _viewUnloaded.SafeInvoke(this);
this.AddDataContextChangedHandler((sender, e) =>
_viewDataContextChanged.SafeInvoke(this, new
Catel.MVVM.Views.DataContextChangedEventArgs(e.OldValue, e.NewValue)));
// Because the RadWindow does not close when DialogResult is set, the following code
is required
ViewModelChanged += (sender, e) => OnViewModelChanged();
// Call manually the first time (for injected view models)
OnViewModelChanged();

WindowStartupLocation = WindowStartupLocation.CenterScreen;
SetBinding(RadWindow.HeaderProperty, new Binding("Title"));
}
public IViewModel ViewModel
{
get { return _logic.ViewModel; }
}
public event PropertyChangedEventHandler PropertyChanged;
public event EventHandler<EventArgs> ViewModelChanged;
event EventHandler<EventArgs> IView.Loaded
{
add { _viewLoaded += value; }
remove { _viewLoaded -= value; }
}
event EventHandler<EventArgs> IView.Unloaded
{
add { _viewUnloaded += value; }
remove { _viewUnloaded -= value; }
}
event EventHandler<Catel.MVVM.Views.DataContextChangedEventArgs>
IView.DataContextChanged
{
add { _viewDataContextChanged += value; }
remove { _viewDataContextChanged -= value; }
}
private void OnViewModelChanged()
{
if (ViewModel != null && !ViewModel.IsClosed)
{
ViewModel.Closed += ViewModelClosed;
}
}
private void ViewModelClosed(object sender, ViewModelClosedEventArgs e)
{

Close();
}
}

You would expect an abstract class here, but the designers (both Visual Studio and Expression Blend) can't handle abstract base
classes

Using the class


The class can now be used the same as the DataWindow class. For more information, see Window and DataWindow.

Advanced information about views


If you want to know about the background information on how the UserControl and DataWindow work, you've come to the right place. The
information found in this part is pretty heavy material, so enter at your own risk...
DataWindow - under the hood
UserControl - under the hood

DataWindow - under the hood


This documentation has to be written in the future

UserControl - under the hood


The UserControl is a pretty sophisticated class. In this part of the documentation, the inner workings of the control are explained. What better way
is there than to using flowcharts. There are a few events very important for the inner workings of the user control. The flowcharts are created per
event.
Keep in mind that the actual logic is implemented in the UserControlLogic, which is used by the UserControl. This way, the logic can be
used by any user control via the UserControlBehavior.
Managing the custom DataContext
Main flow
Loaded
Unloaded
DataContextChanged
DetermineDataContext

Managing the custom DataContext


The UserControl logic uses an additional layer to customize the DataContext. Below is a graphical representation of how it works.

Another view can be found in the image below:

Main flow
The following flowchart shows what happens with a user control in the main flow (the startup). First, it checks whether the user control is loaded
(which is not in a normal case). If the control is loaded, it goes directly to determining the datacontext. Otherwise, it will postpone the action until
the Loaded event.

Loaded
When the control is loaded, it starts checking for the first time whether the current datacontext can be used to create a view model. But, before it
does this, it checks whether it should (and can) re-use an existing view model. To control whether view models should be re-used, use the CloseV
iewModelOnUnloaded property.
If a view model can and should be re-used, it sets the view model as data context and that's it. If there is no view model, or the previous view
model should not be re-used, the control continues to determine the datacontext.

Unloaded
Another event that is very important is the Unloaded event. In this event, the control either cleans up the view model or stores it so it can be
re-used later. Then, it also restores the old datacontext so it never breaks existing application bindings. This way, the control won't leave any
traces behind.

DataContextChanged
The DataContextChanged event is used to react to changes of the datacontext. You might be thinking: "there is no DataContextChanged event in
Silverlight". We use the DataContextHelper class for that. If the new datacontext is new (thus not a view model that the control just set itself), it it
continues to determine the datacontext. Otherwise, it will not take any action.

DetermineDataContext
All other flowcharts eventually led to this flowchart, the determination of the datacontext. The determination of the datacontext is very important,
because this is the moment where the user control transforms the datacontext into a new view model if possible. First it tries is to construct the
view model with the datacontext. So, if the datacontext is an object of type Person, and the view model of the user control has a constructor that
accepts a Person object, it injects the datacontext into the constructor of the view model. If that fails, or there is simply no constructor, the control
checks whether the view model has an empty constructor. If so, it constructs the view model and sets it as the new datacontext. If not, it will leave
the datacontext untouched.
Basically, this is all that happens on a higher level to transform a datacontext into a view model. Under the hood, it's a bit more complicated but
again, on a higher level this is what happens.

Customizing DataContext subscription behavior


Starting with Catel 4.0, the views watch both the direct and inherited DataContext. Starting with Catel 4.1, it is possible to mimick the pre 4.0 Data
Context subscription behavior.

Customizing the behavior for all views


To mimick pre Catel 4.0, use the following code:

var dependencyResolver = this.GetDependencyResolver();


var dataContextSubscriptionService =
dependencyResolver.Resolve<IDataContextSubscriptionService>();
dataContextSubscriptionService.DefaultDataContextSubscriptionMode =
DataContextSubscriptionMode.DirectDataContext;

Customizing the behavior per view


It is also customize the behavior per view. This allows very customized fine tuning of the behavior. To use this feature, one needs to create a
custom implementation of the IDataContextSubscriptionService.

public class CustomDataContextSubscriptionService : DataContextSubscriptionService


{
public override DataContextSubscriptionMode GetDataContextSubscriptionMode(Type
viewType)
{
// TODO: Add logic here
return base.GetDataContextSubscriptionMode(viewType);
}
}

Tips & tricks


This section contains some generic tips & tricks for view-related tasks in Catel.
Finding the view of a view model

Finding the view of a view model


Sometimes it is required to find the view of a view model. For example, this comes in handy when implementing drag and drop where you only
want to support code via view models.
Internally, Catel uses with the IViewManager for this. As soon as a view is loaded (via the Loaded event), the view is registered to the view
manager. The view manager will keep an eye on the events of the view and notice view model changes.
A view is removed from the manager as soon as it is unloaded (via the Unloaded event). From this moment on, it is no longer possible to retrieve
a view via its view model.
Remember that only controls implementing IView are supported by the IViewManager

Retrieving the view of a view model


To find the view of a view model, use the steps below:
1) Resolve the view from IViewManager from the ServiceLocator:

var viewManager = ServiceLocator.Default.ResolveType<IViewManager>();

2) Resolve the view:

var views = viewManager.GetViewsOfViewModel(myViewModel);

Note that it is possible that multiple views are linked to the same view model

Catel.Mvc
The MVC library provided by Catel provides code to easily combine the power of Catel with ASP.NET MVC.
Configuring dependency injection

Configuring dependency injection


Dependency injection in ASP.NET MVC controllers
Dependency injection in ASP.NET Web api controllers

Dependency injection in ASP.NET MVC controllers


The ServiceLocator is a very powerful dependency injection class. To allow the ASP.NET MVC to use the ServiceLocator as dependency
resolver, simply call the following in the global.asax class:

Catel.Mvc.DependencyInjectionConfig.RegisterServiceLocatorAsDependencyResolver();

Dependency injection in ASP.NET Web api controllers


If you are using web api as well, a few more things must be done.
1. Create new type implementing the IDependencyResolver of the web api:

public class CatelWebApiDependencyResolver : Catel.IoC.DependencyResolver,


System.Web.Http.Dependencies.IDependencyResolver
{
private readonly IServiceLocator _serviceLocator;
private readonly ITypeFactory _typeFactory;
public CatelWebApiDependencyResolver()
: this(ServiceLocator.Default) { }
public CatelWebApiDependencyResolver(IServiceLocator serviceLocator)
{
Argument.IsNotNull(() => serviceLocator);
_serviceLocator = serviceLocator;
_typeFactory = serviceLocator.ResolveType<ITypeFactory>();
}
public System.Web.Http.Dependencies.IDependencyScope BeginScope()
{
// This resolver does not support child scopes, so we simply return 'this'.
return this;
}
public object GetService(Type serviceType)
{
if (_serviceLocator.IsTypeRegistered(serviceType))
{
return _serviceLocator.ResolveType(serviceType);
}
if (!serviceType.IsInterface && !serviceType.IsAbstract)
{
return _typeFactory.CreateInstance(serviceType);
}
return null;
}
public IEnumerable<object> GetServices(Type serviceType)
{
if (_serviceLocator.IsTypeRegistered(serviceType))
{
return _serviceLocator.ResolveTypes(serviceType);
}
return Enumerable.Empty<object>();
}
public void Dispose()
{
// nothing to dispose
}
}

2. Register the class manually:

GlobalConfiguration.Configuration.DependencyResolver = new
CatelWebApiDependencyResolver();

Catel.Extensions.Controls
Controls
Pixel shaders
StyleHelper
Themes

Controls
There are several controls available. See the child pages.
StackGrid
TabControl
TraceOutputControl
WatermarkTextBox

StackGrid
Although the example looks crappy (I am not a designer), it shows the power of the StackGrid. You don't have to specify the Grid.Row and
Grid.Column attached properties. Remember the times that you want to insert a grid and you had to increase all the numbers? From now on, use
the StackGrid!

<catel:StackGrid>
<!-- Row definitions -->
<catel:StackGrid.RowDefinitions>
<RowDefinition Height="Auto" />
<RowDefinition Height="Auto" MinHeight="15" />
<RowDefinition Height="Auto" />
</catel:StackGrid.RowDefinitions>
<!-- Column definitions -->
<catel:StackGrid.ColumnDefinitions>
<ColumnDefinition Width="Auto" />
<ColumnDefinition Width="*" />
</catel:StackGrid.ColumnDefinitions>
<!-- Name, will be set to row 0, column 1 and 2 -->
<Label Content="Name" />
<TextBox Text="Geert van Horrik" />
<!-- Empty row -->
<catel:EmptyRow />
<!-- Wrappanel, will span 2 columns -->
<WrapPanel Grid.ColumnSpan="2">
<Button Command="ApplicationCommands.Close" />
</WrapPanel>
</catel:StackGrid>

The Grid is an excellent control to show several controls in a nice layout on the screen. However, it happens a lot that a grid consists of only 2 or
3 columns, and the first column is for all the labels, and the second one is for controls such as textboxes. You correctly implement all the windows
and controls of your application based on user requirements, and then the user decides that he/she wants a row inserted into a grid containing
about 20 rows. When this happens, you need to re-define all the row attributes of the grid.
With the StackGrid, it is no longer required to define the row and column definitions. The StackGrid can smartly interpret the location of the
controls and therefore fill in the Grid.Row and Grid.Column attached properties for you. You need an empty row? No problem, you can use the
EmptyRow class to fill up a row for you. You want a column span? No problem, just use the existing Grid.Column attached property and the
StackGrid will automatically handle this for you.
The StackGrid internally uses a Grid to measure the layout. However, it dynamically loops through its children, and then assigns the Grid.Row
and Grid.Column attached properties for the user.

TabControl
A custom implementation of the TabControl which allows the customization of the way tab items are loaded.
The following options are available:
LazyLoading => Load all tabs using lazy loading, but keeps the tabs in memory afterwards.
LazyLoadingUnloadOthers => Load all tabs using lazy loading. As soon as a tab is loaded, all other loaded tabs will be unloaded.
EagerLoading => Load all tabs as soon as the tab control is loaded.
EagerLoadingOnFirstUse => Load all tabs when any of the tabs is used for the first time.

TraceOutputControl
The TraceOutputControl will be removed in Catel v5.0. It is deprecated and replaced by the LogViewerControl in Orc.Controls.

TraceOutputControl is a debugging convenience control. It shows all the trace and logging output in a filterable control. This way, you can easily
view all the binding errors, etc., in your app instead of the non-colored output window in Visual Studio.

XAML sample

<Controls:TraceOutputControl />

C# sample

var TraceOutputWindow = new Window();


TraceOutputWindow.Height = 300;
TraceOutputWindow.Width = 500;
Catel.Windows.Controls.TraceOutputControl NewTraceControl = new TraceOutputControl();
var NewGrid = new StackGrid();
NewGrid.Children.Add(NewTraceControl);
TraceOutputWindow.Content = NewGrid;
TraceOutputWindow.Show();
ILog Log = LogManager.GetCurrentClassLogger(); // Turning this into a public static
might be a good ideia
Log.Info("Hi! I am an INFO log entry");
Log.Warn("Hi! I am an WARN log entry");
Log.Error("Hi! I am an ERROR log entry");

Many times, developers are inside an application viewing the result of what they have created. But, they also want to know what is happening in
the background and view the traces they have written. The output window of Visual Studio is a solution, but it doesnt show errors very well (black,
just as the normal output). Also, it doesnt allow run-time filtering of the results.
The TraceOutputControl allows a developer to embed a control inside a window or control in the actual application and view the information when
the application is actually running. The TraceOutputControl is also available as a separate window in case it cant be embedded into the software
itself (for example, when a plug-in is being developed for a 3rd party application).
The TraceOutputControl subscribes a custom TraceListener to the Trace.Listeners collection. Then, it filters out the messages that the user
actually wants to see and stores these messages into an internal collection so the user can still filter the messages at a later time.
Starting with Catel 4.0, the TraceOutputControl uses the logging system in Catel to display both log and trace messages

WatermarkTextBox

The WatermarkTextBox will be removed in Catel v5.0. It is deprecated and replaced by the WatermarkTextBox in Orc.Controls.
The WatermarkTextBox allows to set a watermark on textboxes that do not yet have a value.

Setting up a simple watermark


A simple watermark is a watermark with text only. Below is an example:

<catel:WatermarkTextBox Watermark="Enter the first name" />

Setting up a complex watermark


A complex watermark is a watermark that can contain any control, for example an image:

<catel:WatermarkTextBox>
<catel:WatermarkTextBox.Watermark>
<StackPanel Orientation="Horizontal">
<Image Source="/Images/Address.png" />
<TextBlock Text="Enter the e-mail" />
</StackPanel>
</catel:WatermarkTextBox.Watermark>
</catel:WatermarkTextBox>

Pixel shaders
This documentation only applies to WPF

Catel also uses pixel shaders to apply effects to controls via themes and styles. One of the pixel shaders is, for example, the GrayscaleEffect.
This effect automatically converts an image on a button to gray scale when the button is disabled. Below is an example of the shader effect:

If there are a lot of buttons used on the screen, it might be possible that the video card does not support so many shaders, and then WPF will start
throwing exceptions. In that case, first try to set the shader mode of Catel to ShaderRenderMode.Software. If that doesnt work, you can turn the
shaders off by using ShaderRenderMode.Off.

// Force software rendering


StyleHelper.PixelShaderMode = PixelShaderMode.Software;
// Turn off
StyleHelper.PixelShaderMode = PixelShaderMode.Off;

StyleHelper
The StyleHelper class has a few static members that will create style forwarders. Style forwarders are styles that are defined on the application
level, not on the theme level. This allows you to create forwarders with the same key as the control name, but that will forward to the
DefaultxxxStyle. Since the new styles are defined at the application level, you will not get any circular references because the style defined in the
theme cannot access the application level resources.
This is accomplished by simply calling StyleHelper.CreateStyleForwardersForDefaultStyles() in the OnStartup of an application.
Catel currently ships with a several theme files. This example theme file is based on the Aero" theme that is included in the WPF libraries. The
theme of Catel corrects the margins, since the default Aero" theme sets the margin of all controls to 0, which will result in all the user controls
being stuck together, as shown in the figure below:

We see too many developers fixing the margins on the control directly, while this can also be accomplished by using the Catel theme and the
included StyleHelper class. See the image below for the final result:

Themes
Using the themes is pretty simple. First, the right theme has to be added to the application resource dictionary:

<Application x:Class="OverrideStyles.App"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
StartupUri="Views/MainWindow.xaml">
<Application.Resources>
<ResourceDictionary>
<ResourceDictionary.MergedDictionaries>
<!-- Set custom theme -->
<ResourceDictionary
Source="/Catel.Extensions.Controls;component/themes/generic.xaml"
/>
</ResourceDictionary.MergedDictionaries>
</ResourceDictionary>
</Application.Resources>
</Application>

The next step is optional. If the margins should automatically be corrected by the stylehelper, it is required to call the following code somewhere in
the application (application startup is recommended):

namespace OverrideStyles
{
/// <summary>
/// Interaction logic for App.xaml
/// </summary>
public partial class App : Application
{
protected override void OnStartup(StartupEventArgs e)
{
// Create style forwarders
Catel.Windows.Helpers.StyleHelper.CreateStyleForwardersForDefaultStyles();
// Call base
base.OnStartup(e);
}
}
}

Catel.Extensions.CSLA
Catel supports CSLA. All MVVM features in Catel (such as nested user controls) can be used with in combination with the CSLA ViewModelBase.
For more information about CSLA, see http://www.lhotka.net/cslanet/

Catel.Extensions.Data
The data extension provides an implementation of the specification pattern.
Specifications

Specifications
Catel provides an implementation of the specification pattern.
A specification pattern outlines a business rule that is combinable with other business rules. In this pattern, a unit of business logic inherits its
functionality from the abstract aggregate Composite Specification class. The Composite Specification class has one method called IsSatisfiedBy
that returns a boolean value.
After instantiation, the specification is "chained" with other specifications, making new specifications easily maintainable, yet highly customizable
business logic. Furthermore upon instantiation the business logic may, through method invocation or inversion of control, have its state altered in
order to become a delegate of other classes such as a persistence repository.
The big advantage is that commonly used queries can be converted to a specification or a combination of specifications. Then if the query should
change (for example, IsDeleted is introduced), only the specification needs to be changed.
The cool thing about the specification implementation in Catel is that it can be used for Entity Framework queries, but also provides implicit
casting to a Func<TEntity, bool>. This way a specification can be passed to any method accepting a method and thus also works with all linq
queries on normal collections.

Using the classes


Creating a specification is very simple. Below is an example of an active products specification:

public class ActiveProductSpecification : Specification<Product>


{
public ActiveProductSpecification()
: base(x => !x.IsDeleted && x.IsActive)
{
}
}

Then the specification can be used like this:

var productRepository = new ProductRepository();


var activeProductSpecification = new ActiveProductSpecification();
var activeProducts = productRepository.GetQuery(activeProductSpecification);

Catel.Extensions.DynamicObjects
In .NET, it is possible to create fully dynamic objects. This makes it possible to create types of which the members are not yet known at compile
time. Starting with Catel 3.7, the DynamicModelBase is fully dynamic and still provides the features such as serialization. Catel supports dynamic
objects by implementing the IDynamicMetaObjectProvider which is available in WPF, Silverlight and Windows RT.
For more information about dynamic programming, see MSDN

Creating dynamic objects


Using ModelBase functionality
Supporting serialization of dynamic objects

Creating dynamic objects


Creating a dynamic object with full Catel functionality is easy. Just add the Catel.Extensions.DynamicObjects reference via NuGet and create a
class that derives from DynamicModelBase:

public class DynamicModel : DynamicModelBase


{
// TODO: Add custom functionality if required
}

Then the dynamic model can be used like this:

dynamic model = new DynamicModel();


model.NonExistingProperty = "a dynamic value";
Console.WriteLine(model.NonExistingProperty);

It is important to know that you must use the keyword dynamic to instantiate the type.

Using ModelBase functionality

The DynamicModelBase class derives from ModelBase. However it must be preceded by the dynamic keyword. To use the ModelBase functionali
ty, cast it to the right type:

dynamic model = new DynamicModel();


model.NonExistingProperty = "a dynamic value";
// Note: the Validate method is available on the ModelBase
var modelBase = (ModelBase)model;
modelBase.Validate();

Supporting serialization of dynamic objects


Dynamic objects in Catel fully support the default serialization that Catel provides. To example below shows how to serialize a dynamic object:

dynamic model = new DynamicModel();


model.NonExistingProperty = "a dynamic value";
var serializer = SerializationFactory.GetXmlSerializer();
using (var memoryStream = new MemoryStream())
{
var dynamicModel = (DynamicModel)model;
serializer.Serialize(dynamicModel, memoryStream);
memoryStream.Position = 0L;
dynamic deserializedModel = serializer.Deserialize(typeof(DynamicModel),
memoryStream);
var deserializedDynamicModel = (DynamicModel) deserializedModel;
// deserializedDynamicModel is now a dynamically deserialized object
}

Catel.Extensions.EntityFramework
Starting with Catel 3.5, support for Entity Framework was added. For more information about Entity Framework, see the official documentation by
Microsoft.
Getting started with Entity Framework in Catel
Using the DbContextManager
Using the repositories and unit of work
Using the ModelBase as base class for code-first entities
Using stored procedures and functions

Getting started with Entity Framework in Catel


This guide will give a very brief explanation how to use Entity Framework together with Catel.
Context
Creating the code-first models
Customizing the code-first models
Repositories
Creating repositories
Registering repositories
Unit of Work
Retrieving data
Saving data

Context
Creating the code-first models
Create a new context with code-first models right-clicking on the solution => Add => New item... Then search for ADO.NET Entity Data Model and
give it a name and follow the wizard.

Customizing the code-first models


By default the code-first models aren't very smart. To add additional functionality such as validation, change notifications, etc, it is best to let it
derive from ModelBase. To do so, make all entities derive from ModelBase as shown in the example below:

[Table("person")]
public partial class Person : ModelBase
{
[StringLength(50)]
public string FirstName { get; set; }
[StringLength(50)]
public string lastname { get; set; }
public long PersonId { get; set; }
public long FamilyId { get; set; }
public virtual Family Family { get; set; }
}

When the classes are derived from ModelBase, EF will try to serialize all the default Catel properties as well. To make sure that EF ignores the
Catel properties, go to the Context class and search for the OnModelCreating method. Then add the IgnoreCatelProperties extension method to
all entity definitions as shown in the example below:

protected override void OnModelCreating(DbModelBuilder modelBuilder)


{
modelBuilder.Entity<Family>()
.IgnoreCatelProperties()
.Property(e => e.FamilyName)
.IsUnicode(false);
modelBuilder.Entity<Family>()
.HasMany(e => e.Person)
.WithRequired(e => e.Family)
.WillCascadeOnDelete(false);
}

Repositories
Creating repositories
Once the DAL is correctly set up, it's time to create the repositories. Creating repositories with Catel is super easy. Just create (or generate with
T4) a class and interface for each entity:

public class FamilyRepository : EntityRepositoryBase<family, int>, IFamilyRepository


{
public FamilyRepository(DbContext dbContext)
: base(dbContext)
{
}
}
public interface IFamilyRepository : IEntityRepository<family, int>
{
}

Registering repositories
In order for the unit of work to find the repositories, they need to be registered in the ServiceLocator. This can be done as follows:

var serviceLocator = ServiceLocator.Default;


serviceLocator.RegisterType<IFamilyRepository, FamilyRepository>();

Unit of Work
Retrieving data
To retrieve data inside a transaction, you can use the UnitOfWork. Inside a method / service call / view model, use the following code:

using (var uow = new UnitOfWork<FamilyContext>())


{
var familyRepository = uow.GetRepository<IFamilyRepository>();
var families = new ObservableCollection<family>(familyRepository.GetAll());
// TODO: Do something with all families
}

Catel will automatically take care of scoping of the DbContext when using unit of work and repositories

Saving data
To save data, the entities must be updated in the repositories and then saved in the unit of work. Below is an example, assuming the list of
families contains updated entities:

using (var uow = new UnitOfWork<FamilyContext>())


{
var familyRepository = uow.GetRepository<IFamilyRepository>();
var personRepository = uow.GetRepository<IPersonRepository>();
foreach (var family in families)
{
familyRepository.Update(family);
}
uow.SaveChanges();
}

Using the DbContextManager


The DbContextManager class allows the sharing of DbContext (with underlying ObjectContext) classes in Entity Framework. The good thing
about this is that the same context can be used in the same scope without having to recreate the same type of the same context over and over
again.
A very good example of this scoping is an ASP.NET (MVC) application where a context is normally shared throughout the whole thread that
handles a request. A big advantage of reusing the same instance of a context is that already fetched entities don't need to be refetched over and
over again.

Obtaining a DbContext
Obtaining a DbContext is very simple by using the DbContextManager.

using (var dbContextManager = DbContextManager<MyEntities>.GetManager())


{
var dbContext = dbContextManager.DbContext;
// TODO: handle logic with dbContext here
}

It is very important to wrap the DbContextManager in a using state because it must be disposed

Scoping is all done automatically because when a DbContextManager is instantiated, a reference counter is increased. Every time an instance of
the DbContextManager is disposed, the reference counter is decreased. When the reference count reaches zero (0), it will dispose the DbContext
that it manages.

Sharing a single DbContext per ASP.NET request


When a request is started, a context can be created by calling this code:

DbContextManagerHelper.CreateDbContextForHttpContext<MyEntities>();

When a request is ended, the context can be disposed by using this code:

DbContextManagerHelper.DisposeDbContextForHttpContext<MyEntities>();

Using the repositories and unit of work


The Repository and Unit of Work (UoW) pattern are very useful patterns to create an abstraction level over the DbContext that is provided by
Entity Framework. A much heard excuse not to use repositories is that EF itself already works with repositories (the DbContext) and a UoW (in
the SaveChanges method). Below are a few examples why it is a good thing to create repositories:
Abstract away some of the more complex features of Entity Framework that the end-developer should not be bothered with
Hide the actual DbContext (make it internal) to prevent misuse
Keep security checks and saving and rollback in a single location
Force the use of the Specification pattern on queries

Note that repositories and UoW should not be used to abstract away the ORM tool because that is just another abstraction layer which
is not required. Use it for the advantages mentioned above
A Unit of Work (UoW) is a a combination of several actions that will be grouped into a transaction. This means that either all actions inside a UoW
are committed or rolled back. The advantage of using a UoW is that multiple save actions to multiple Repositories can be grouped as a unit.
A repository is a class or service responsible for providing objects and allowing end-developers to query data. Instead of querying the DbContext
directly, the DbContext can be abstracted away to provide default queries and force required functionality to all end-developers of the DbContext.

Overview of Unit of Work and repositories


There are different interpretations of how repositories should be used in combination with unit of work. Let's start with an overview how the
DbContext, Repositories and Unit of Work relate to each other. The image below represents an overview of the situation as Catel deals with the
DbContext, Repositories and Unit of Work:

The image above shows that the Unit of Work is the top-level component to be used. Each UoW contains its own DbContext instance. The
DbContext can either be injected or will be created on the fly. Then the UoW also contains repositories which always get the DbContext injected.
This way, all repositories inside a UoW share the same DbContext.

Creating a Unit of Work


A UoW can be created by simply instantiating it. The end-developer has the option to either inject the DbContext or let the DbContextManager ta
ke care of it automatically.

using (var uow = new UnitOfWork<MyDbContext>())


{
// get repositories and query away
}

Creating a repository
A repository can be created very easily by deriving from the EntityRepositoryBase class. Below is an example of a customer repository:

public class CustomerRepository : EntityRepositoryBase<Customer, int>,


ICustomerRepository
{
public CustomerRepository(DbContext dbContext)
: base(dbContext)
{
}
}
public interface ICustomerRepository : IEntityRepository<Customer, int>
{
}

Retrieving repositories from a Unit of Work


Once a UoW is created, it can be used to resolve repositories. To retrieve a repository from the UoW, the following conditions must be met:
1. The repository must be registered in the ServiceLocator as Transient type. If the repository is declared as non-transient, it will be
instantiated as new instance anyway.
2. The repository must have a constructor accepting a DbContext instance
To retrieve a new repository from the UoW, use the following code:

using (var uow = new UnitOfWork<MyDbContext>())


{
var customerRepository = uow.GetRepository<ICustomerRepository>();
// all interaction with the customer repository is applied to the unit of work
}

Saving a Unit of Work


It is very important to save a Unit of Work. Once the Unit of Work gets out of scope (outside the using), all changes will be discarded if not
explicitly saved.

using (var uow = new UnitOfWork<MyDbContext>())


{
var customerRepository = uow.GetRepository<ICustomerRepository>();
// all interaction with the customer repository is applied to the unit of work
uow.SaveChanges();
}

Using the ModelBase as base class for code-first entities


The ModelBase provides lots of functionality such as change tracking, property notifications and validation. It is possible to use this in code first.
To do so, derive the entities from the ModelBase class as shown in the example below:

[Table("person")]
public partial class Person : ModelBase
{
[StringLength(50)]
public string FirstName { get; set; }
[StringLength(50)]
public string lastname { get; set; }
public long PersonId { get; set; }
public long FamilyId { get; set; }
public virtual Family Family { get; set; }
}

In the context, add additional initialization code to ignore the Catel properties on the ModelBase class:

protected override void OnModelCreating(DbModelBuilder modelBuilder)


{
modelBuilder.Entity<Family>()
.IgnoreCatelProperties()
.Property(e => e.FamilyName)
.IsUnicode(false);
modelBuilder.Entity<Family>()
.HasMany(e => e.Person)
.WithRequired(e => e.Family)
.WillCascadeOnDelete(false);
}

Now the entities are ready to be used and can contain validation.

Using stored procedures and functions


Sometimes it's required to use stored procedures or functions. This is still possible with Catel. Below is an example on how to call a stored
procedure:

using (var dbContextManager = DbContextManager<MyEntities>.GetManager())


{
var dbContext = dbContextManager.DbContext;
var result = dbContext.Database.SqlQuery<ReturnType>("storedProcedureName",
params);
}

Catel.Extensions.FluentValidation
The validation in Catel is extremely flexible, at this point you must already know it, but sometimes it is just not enough or you are forced to use
external validators.

Note that the FluentValidation extension can be used in combination with Catel.Core only, so it is not required to combine it with the
MVVM framework

FluentValidation is a small validation library for .NET that uses a fluent interface and lambda expressions for building validation rules for your
business objects. Catel provides an extension in order to use FluentValidation as a validation library.
The only thing you have to do is install an isolate package named Catel.Extensions.FluentValidation, available via NuGet, then you will be able to
write your view models validations using FluentValidation approach.

public class PersonViewModelValidator : AbstractValidator<PersonViewModel>


{
public PersonViewModelValidator()
{
RuleFor(person => person.FirstName).NotEmpty();
RuleFor(person => person.LastName).NotEmpty().WithMessage("Please specify the
last name");
}
}

In order to retrieve the right validators, you must register the FluentValidatorProvider:

ServiceLocator.Default.RegisterType<IValidatorProvider, FluentValidatorProvider>();

The FluentValidatorProvider will automatically retrieve the right validators associated with the view models.

How handle all Catel validation concepts with fluent validation classes?
Catel handle concepts like field or business rules errors and warnings . So, it's necessary map the fluent validation class to the specific Catel
validation using ValidationDescriptionAttribute.

[ValidatorDescription(Tag = "Person", ValidationResultType =


ValidationResultType.Error, ValidationType = ValidationType.Field)]
public class PersonViewModelValidator : AbstractValidator<PersonViewModel>
{
}

How FluentValidationProvider works?


FluentValidationProvider is an implementation of IValidationProvider (see: Validation via IValidator). It search all validators classes that
implements FluentValidation.IValidator interface, that also can validate the view model type.
A view model can have one or more validators, so FluentValidationProvider aggregates all validators in a single one using CompositeValidator
class. For performance reasons FluentValidationProvider only searches for validators on the assembly which the view model belongs to.
FluentValidationProvider do not use NamingConventions

FluentValidation is only available in NET40, NET45, Silverlight 4 and Silverlight 5

Catel.Extensions.Interception
Interception Extensions enables you to write code that is executed each time a matching method is invoked using a fluent API. It's suited for cross
cutting concerns, such as transactions, security and logging.
Method interception
Property interception
Interception provides the following advantages:
Strongly-typed syntax
Interception semantics are based on strongly-typed method definitions, which permit to develop aspects taking advantage of features like:
auto-completion, refactoring, compile-time errors, etc ;
No configuration
We tried to simplify AOP implementation by favoring convention over configuration. As a result, no configuration of any kind is ever
required to build aspects. However, some conventions take place to make this possible ;
Minimum learning-curve
In order to get started, no previous experience with this or any other AOP implementation is required. No need to know or understand
AOP terminology, which is not always very intuitive. By looking at some examples developers can figure out how to intercept calls and
modularize their own applications ;
Methods as first-class elements
Utilizing dynamic proxies to implement AOP typically results in having to model aspects as interceptors. Such interceptors are commonly
associated with objects no with methods. Therefore, the developer is responsible for providing the logic to break down object interception
into method interception;
Usage in combination with IoC
The interception mechanism in Catel is based on the registration of a type in the ServiceLocator and in addition of the interception
configuration, this way, you can fully use the advantages of IoC.
Initially, Interception extension support Methods and Properties members for the types you register in the ServiceLocator (internally, we create an
class proxy instance which is actually registered in ServiceLocator).
This extension is based on FluentAop

Method interception

There are many ways to configure method interception.


OnBefore callback
OnAfter callback
OnCatch and OnFinally callbacks
OnInvoke callback
OnReturn callback
Intercepting multiple method calls at once
Intercepting all members calls at once
Differentiating between overloaded methods
Stacking several methods on a single fluent instruction
Utilizing predicates to select multiple methods

OnBefore callback
It always runs before the target method execution.

var serviceLocator = ServiceLocator.Default;


serviceLocator.ConfigureInterceptionForType<ITestService, TestService>()
.InterceptMethod(service => service.Perform())
.OnBefore(() => Console.WriteLine("Called Before"));
var testService = serviceLocator.ResolveType<ITestService>();
testService.Perform();

The output will look like this:

Called Before
The actual call

OnAfter callback
It runs after the target method execution, but only if it does not throw an exception.

var serviceLocator = ServiceLocator.Default;


serviceLocator.ConfigureInterceptionForType<ITestService, TestService>()
.InterceptMethod(service => service.Perform())
.OnAfter(() => Console.WriteLine("Called After"));
var testService = serviceLocator.ResolveType<ITestService>();
testService.Perform();

The output will look like this:

The actual call


Called After

OnCatch and OnFinally callbacks


OnCatch callback runs after the target method execution, but only if it throws an exception. OnFinally callback runs after the target method
execution. But OnAfter and OnCatch callbacks always run first if they exist.

var serviceLocator = ServiceLocator.Default;


serviceLocator.ConfigureInterceptionForType<ITestService, TestService>()
.InterceptMethod(service => service.Fail())
.OnCatch(exception => Console.WriteLine("An error of
type '{0}' occurs with message : \n'{1}'", exception.GetType().Name,
exception.Message))
.OnFinally(() => Console.Write("You can dispose
resources here"));

var testService = serviceLocator.ResolveType<ITestService>();


testService.Fail();

The output will look like this:

An error of type 'TargetInvocationException' occurs with message:


'Exception has been thrown by the target of an invocation'
You can dispose resources here

OnInvoke callback
It runs instead of the target method execution.

var serviceLocator = ServiceLocator.Default;


serviceLocator.ConfigureInterceptionForType<ITestService, TestService>()
.InterceptMethod(service => service.Perform())
.OnInvoke(invocation => Console.Write("The original call
has been replaced by this"));
var testService = serviceLocator.ResolveType<ITestService>();
testService.Perform();

The output will look like this:

The original call has been replaced by this

OnReturn callback
It runs right before the proxy method execution is over. OnFinally callback runs first if it exist.

var serviceLocator = ServiceLocator.Default;


serviceLocator.ConfigureInterceptionForType<ITestService, TestService>()
.InterceptMethod(service => service.ReturnNull())
.OnReturn((invocation, returnedValue) => returnedValue ??
"This is a replaced value");
var testService = serviceLocator.ResolveType<ITestService>();
var result = testService.ReturnNull();
Console.WriteLine(result);

The output will look like this:

This is the replaced value

Intercepting multiple method calls at once


You can configure interception of multiple methods call at once just like this:

var serviceLocator = ServiceLocator.Default;


serviceLocator.ConfigureInterceptionForType<ITestService, TestService>()
.InterceptMethods
(
service => service.Perform(),
service => service.Perform(It.IsAny<string>()),
service => service.Return()
)
.OnBefore(() => Console.WriteLine("Called On Before"))
.OnAfter(() => Console.WriteLine("Called On After"));
var testService = serviceLocator.ResolveType<ITestService>();
testService.Perform();
testService.Perform("testValue");
testService.Return();

The output will look like this:

Called On Before
The actual call
Called On after
Called On Before
Called On After
Called On Before
Called On After

Intercepting all members calls at once


To intercept all member calls at once, use the following code:

var serviceLocator = ServiceLocator.Default;


serviceLocator.ConfigureInterceptionForType<ITestService, TestService>()
.InterceptAll()
.OnBefore(() => Console.WriteLine("Called On Before"))
.OnAfter(() => Console.WriteLine("Called On After"));
var testService = serviceLocator.ResolveType<ITestService>();
testService.Perform();
testService.Name = "testValue";
var value = testService.Name;

The output will look like this:

Called On Before
The actual call
Called On after
Called On Before
Called On After
Called On Before
Called On After

Exclude members
If you want to exclude some members using InterceptAll* methods, you can decorate your membre with the DoNotInterceptAttribute
in the interface type.

Differentiating between overloaded methods


To differentiate between overloaded methods, use the following code:

var serviceLocator = ServiceLocator.Default;


serviceLocator.ConfigureInterceptionForType<ITestService, TestService>()
.InterceptMethod(service =>
service.Perform(It.IsAny<string>()))
.OnBefore(invocation => invocation.Arguments[0] =
"Intercepted");
var testService = serviceLocator.ResolveType<ITestService>();
testService.Perform("testValue");
testService.Perform(45);

The output will look like this:

Intercepted
45

Stacking several methods on a single fluent instruction


Use the following code:

var serviceLocator = ServiceLocator.Default;


serviceLocator.ConfigureInterceptionForType<ITestService, TestService>()
.InterceptMethod(service => service.Perform())
.OnBefore(() => Console.WriteLine("1,2,3..."))
.OnAfter(() => Console.WriteLine("Excecution Succeeded"))
.And()
.InterceptMethod(service => service.Fail())
.OnCatch(exception => Console.WriteLine("Exception occurs: '{0}'",
exception.Message))
.OnFinally(() => Console.Write("Dispose Resources Here"))
.And()
.InterceptMethod(service => service.ReturnNull())
.OnReturn((invocation, returnedValue) => returnedValue ?? "Replace Any
Null Value Here");
var testService = serviceLocator.ResolveType<ITestService>();
testService.Perform();
testService.Fail();
testService.ReturnNull();

The output will look like this:

1,2,3...
The actual call
Execution Succeeded
Exception occurs: 'Exception has been thrown by the target of an invocation.'
Dispose Resources Here

Utilizing predicates to select multiple methods


Use the following code:

var serviceLocator = ServiceLocator.Default;


serviceLocator.ConfigureInterceptionForType<ITestService, TestService>()
.InterceptWhere(method => method.Name == "Perform")
.OnBefore(() => Console.WriteLine("Called before"))
.OnAfter(() => Console.WriteLine("Called after"));
var testService = serviceLocator.ResolveType<ITestService>();
testService.ReturnNull();
testService.Perform();

The output will look like this:

Called before
The actual call
Called after

Property interception
Intercept setters

Intercept getters

Intercept setters
Use the following code:

var serviceLocator = ServiceLocator.Default;


serviceLocator.ConfigureInterceptionForType<ITestService, TestService>()
.InterceptSetter(service => service.Name)
.OnBefore(() => Console.WriteLine("Setting Property Intercepted"));
var testService = serviceLocator.ResolveType<ITestService>();
testService.Name = "testValue";
var name = testService.Name;

The output will look like this:

Setting Property intercepted

Intercept getters
Use the following code:

var serviceLocator = ServiceLocator.Default;


serviceLocator.ConfigureInterceptionForType<ITestService, TestService>()
.InterceptGetter(service => service.Name)
.OnBefore(() => Console.WriteLine("Getting Property Intercepted"));
var testService = serviceLocator.ResolveType<ITestService>();
testService.Name = "testValue";
var name = testService.Name;

The output will look like this:

Getting Property intercepted

Catel.Extensions.Memento
Lots of real world applications need to implement undo/redo. However, most applications written in MVVM lack this feature because it is very hard
to implement. Luckily, Catel solves this issue by introducing the IMementoService. The IMementoService is a service that allows a developer to
register custom actions that should be undone. A few actions you can think of:
Property change of a model
Item is added or removed to/from a collection
A method is executed
One way to introduce the memento pattern is by creating a copy of the whole memory at each step (yes, some people actually do this), but in
Catel it is done a bit smarter. For each possible action type, there is an implementation of the UndoBase. This way, each action will know by itself
how to undo or redo. Catel offers the following default implementations:
PropertyChangeUndo
CollectionChangeUndo
ActionUndo
If there are more actions supported, it is possible to write a custom UndoBase implementation and add the specific action to the IMementoService

. It will automatically be added to the undo/redo action stack.


Memento and collections
Memento and methods
Memento and properties

Undo and redo support


The IMementoService supports both undo and redo actions. This means that an action that is undo-ed by a call to the Undo method, it is
automatically added to the redo stack when redo is supported.
To undo an action, use the code below:

var mementoService = ServiceLocator.Default.ResolveType<IMementoService>();


mementoService.Undo();

It is possible to check whether it is possible to undo actions by using the CanUndo property. This check is not required since the Undo method will
also check this internally.
To redo an action, use the code below:

var mementoService = ServiceLocator.Default.ResolveType<IMementoService>();


mementoService.Redo();

It is possible to check whether it is possible to redo actions by using the CanRedo property. This check is not required since the Redo method will
also check this internally.

Grouping actions in batches


The MementoService automatically wraps all actions in batches. Because each action is treated as a batch, it is easy to begin a batch and add
several actions to a single batch. Below is the code to create a batch:

var mementoService = ServiceLocator.Default.ResolveType<IMementoService>();


mementoService.BeginBatch("Batch title", "Batch description");
// All actions added to the memento service are added to the specified batch

Note that the Title and Description are optional. They are however a great way to represent the batches in the user interface

A batch can be ended in several ways:


1. A call to EndBatch
2. A call to BeginBatch
As soon as a batch is ended by one of the ways described below, it will be added to the undo stack.

Ignoring support for memento


Ignoring specific properties or methods for the IMementoService is very easy. Just decorate them with the IgnoreMementoSupportAttribute as
shown below:

[IgnoreMementoSupport]
public string IgnoredProperty { get; set; }

Memento and collections


Adding the ability to undo and redo collection changes on a collection is very simple using the CollectionChangeUndo class. This can be done
either automatically or manually.

Handling collection changes automatically


When a collection implements the INotifyCollectionChanged interface, it is possible to register the collection. The IMementoService will fully take
care of any collection changes by the collection and add these automatically to the undo/redo stack. Internally, the service will create an instance
of the CollectionObserver which will register the changes in the IMementoService.

var mementoService = ServiceLocator.Default.ResolveType<IMementoService>();


mementoService.RegisterCollection(myCollection);

Handling collection changes manually


When an object does not support the INotifyPropertyChanged interface or you want more control, it is possible to instantiate the CollectionChange
Undo yourself. See the example below:

public void AddPerson(IPerson person)


{
var newIndex = _internalCollection.Add(person);
var mementoService = ServiceLocator.Default.ResolveType<IMementoService>();
mementoService.Add(new CollectionChangeUndo(_internalCollection,
CollectionChangeType.Add, -1, newIndex, null, item));
}

Note that all actions should be implemented, such as adding, replacing, removing and resetting to fully support undo/redo

Removing a collection and its actions


When a collection goes out of scope, it is important that the IMementoService does not keep it in memory and keeps undoing the changes.
Therefore, one should also unregister the collection:

var mementoService = ServiceLocator.Default.ResolveType<IMementoService>();


mementoService.UnregisterCollection(myCollection);

Note that unregistering a collection will both cancel change notifications and remove the actions that belong to this collection from the
undo/redo stack

Memento and methods


Adding the ability to undo and redo methods is the most complex, because this cannot be done automatically. However, it is possible to use the A
ctionUndo class to make it as easy as possible.

Handling methods manually


An action can come in two flavors. One with only undo support, and one with redo support. It is always recommended to implement the one with
support for redo, but the choice is always yours. For this example, let's assume a simple class that will increase a value (for which we are building
undo/redo support):

public class SpecialNumberContainer()


{
private int _number = 5;
public int Number { get { return _number; } }
public int IncreaseNumber()
{
_number++;
}
}

As you can see in the example, it is not possible to use the PropertyChangeUndo because the property has no setter and no change notification.
So, we will create custom actions for undo/redo.
First, the class with only undo support:

public class SpecialNumberContainer()


{
private int _number = 5;
public int Number { get { return _number; } }
public int IncreaseNumber()
{
_number++;
var mementoService = ServiceLocator.Default.ResolveType<IMementoService>();
mementoService.Add(new ActionUndo(this, () => _number--));
}
}

The code above will add a new action to the undo stack every time the IncreaseNumber method is called. Then, it will not add it to the redo stack
because redo is not possible (we haven't provided a redo action).
Below is the same class, but now with redo support:

public class SpecialNumberContainer()


{
private int _number = 5;
public int Number { get { return _number; } }
public int IncreaseNumber()
{
_number++;
var mementoService = ServiceLocator.Default.ResolveType<IMementoService>();
mementoService.Add(new ActionUndo(this, () => _number--, () => _number++));
}
}

The code above will add a new action to the undo stack every time the IncreaseNumber method is called. Then, when an action is undo-ed, the
action is added to the redo stack and it is possible to redo the action because the redo action was provided as well.

Removing the actions from the undo/redo stack


When an action no longer has to be in the undo/redo stack of the IMementoService, one should call the Clear method with the instance of the
method as shown in the sample below:

var mementoService = ServiceLocator.Default.ResolveType<IMementoService>();


mementoService.Clear(myInstanceContainingTheMethod);

Memento and properties


Adding the ability to undo and redo property changes on an object is very simple using the PropertyChangeUndo class. This can be done either
automatically or manually.

Handling property changes automatically


When an object implements the INotifyPropertyChanged interface, it is possible to register the object. The IMementoService will fully take care of
any property changes by the object and add these automatically to the undo/redo stack. Internally, the service will create an instance of the Objec
tObserver which will register the changes in the IMementoService.

var mementoService = ServiceLocator.Default.ResolveType<IMementoService>();


mementoService.RegisterObject(myObject);

Handling property changes manually


When an object does not support the INotifyPropertyChanged interface or you want more control, it is possible to instantiate the PropertyChange
Undo yourself. See the example below:

public string Name


{
get { return _name; }
set
{
object oldValue = _name;
object newValue = value;
_name = value;
RaisePropertyChanged("Name");
var mementoService = ServiceLocator.Default.ResolveType<IMementoService>();
mementoService.Add(new PropertyChangeUndo(this, "Name", oldValue, newValue));
}
}

Removing an object and its actions


When a model goes out of scope, it is important that the IMementoService does not keep it in memory and keeps undoing the changes.
Therefore, one should also unregister the object:

var mementoService = ServiceLocator.Default.ResolveType<IMementoService>();


mementoService.UnregisterObject(myObject);

Note that unregistering an object will both cancel change notifications and remove the actions that belong to this object from the
undo/redo stack

Catel.Extensions.Prism
Table of contents:
Making the region manager available
Activating a view into a specific region
Dealing with more than one and only one shell
Deactivating a view
Deactivating a view automatically
More information:
Using the bootstrapper
Declaring modules
Module catalogs
Translating or customizing the initialization task messages
The latest version of the guidance, Prism, includes a feature named "User Interface Composition". Basically it allows build a mosaic like
application by loading multiple views that comes from different modules into an active regions exposed by a control, also know as the shell.

But all this is about view models. Therefore, the Catel team decide to introduce an extension that implements a good starting point in order create
a composite user interface without actually referencing any view. At this point, you must have heared about of the UIVisualizerService, and the
way it can resolve a view from an instance of a view model. So, we are please to introduce you the UICompositionService.

Making the region manager available


First of all, you must make available the region manager on the instance of ServiceLocator. A Prism based application uses MEF or Unity as
primary IoC contanier. Therefore, you must synchronize this container with the Catel one, overriding the ConfigureContainer method of the
application Bootstrapper class, using the following code:

protected override void ConfigureContainer()


{
base.ConfigureContainer();
if (ServiceLocator.Instance.IsExternalContainerSupported(this.Container))
{
ServiceLocator.Instance.RegisterExternalContainer(this.Container);
}
}

but if you use ServiceLocator primary IoC contanier, and your Bootstrapper class inherits from BootstrapperBase the region manager is actually
available and you don't have to write the synchronization container code.
Since Catel 3.2 ServiceLocator support Dependency injection, therefore now you are able write Prism base application without the
usage of a third party container.

Activating a view into a specific region


To activate a view into a specific region, use the following code:

var viewModel = new EmployeeViewModel();


var dependencyResolver = this.GetDependencyResolver();
var uiCompositionService = dependencyResolver.Resolve<IUCompositionService>();
uiCompositionService.Activate(viewModel, "MainRegion");

Since Catel 4.0 UICompositionService is available for Prism. Use this service instead UIVisualizerService extension methods.

But if the context allows you to know the instance of the view model of the view owner of the region where you will inject a view, is strongly
recommended use the Activate overload that allows you to specify the parent view-model. This call will enforce the view models parent-child
relationship:

uiCompositionService.Activate(viewModel, this, "MainRegion");

Assume that this references an instance of the view-model of a view with MainRegion region specified, so this is used as parent view
model reference in the previous call.

Dealing with more than one and only one shell


Actually you are able to inject views (referencing it's view models) in any window. Just like the previous example but in combination with the
experimental extension method Show:

var dependencyResolver = this.GetDependencyResolver();


var uiVisualizerService = dependencyResolver.Resolve<IUIVisualizerService>();
var uiCompositionService = dependencyResolver.Resolve<IUCompositionService>()
var windowViewModel = new WindowWithRegionViewModel();
uiVisualizerService.Show(windowViewModel, () => { uiCompositionService.Activate(new
EmployeeViewModel(), windowViewModel, "WindowMainRegion") });

Deactivating a view
To deactivate a view, use the following code:

uiCompositionService.Deactivate(viewModel);

If you keep your view model alive (see: Keeping view models alive), you can reactivate a deactivated the view using Activate method without
specify the region name.

Deactivating a view automatically


If you close the view model using SaveAndCloseViewModel or CancelAndCloseViewModel or CloseViewModel methods, the view that belongs to
this view model will be automatically deactivated from the region where it is activated.
In order to start using this feature, the only thing you have to do is install an isolated package named Catel.Extensions.Prism, available via NuGet.
User interface composition feature that comes with Prism extension is only available in NET40, NET45 and Silverlight 5

Using the bootstrapper


Catel offers a basic bootstrapper that uses the ServiceLocator as IoC container. This way, it is really simple to create a prism application using
Catel and prism.
The bootstrapper takes lots of work out of hands, and this way a developer can simply focus on what must be done in the bootstrapper (such as
registering the right module catalog).

Using the bootstrapper


This example shows how the bootstrapper is used to define both the shell and the module catalog that looks for modules in the Modules directory
of the application root.

/// <summary>
/// The bootstrapper that will create and run the shell.
/// </summary>
public class MyApplicationBootstrapper : BootstrapperBase
{
/// <summary>
/// Initializes a new instance of the <see cref="MyApplicationBootstrapper"/> class.
/// </summary>
public MyApplicationBootstrapper()
{
LogManager.RegisterDebugListener();
}
/// <summary>
/// Creates the <see cref="T:Microsoft.Practices.Prism.Modularity.IModuleCatalog"/>
used by Prism.
/// </summary>
/// <returns></returns>
protected override IModuleCatalog CreateModuleCatalog()
{
var moduleCatalog = new DirectoryModuleCatalog { ModulePath = @".\Modules"};
moduleCatalog.Initialize();
return moduleCatalog;
}
/// <summary>
/// Creates the shell or main window of the application.
/// </summary>
/// <returns>
/// The shell of the application.
/// </returns>
protected override DependencyObject CreateShell()
{
var shell = new MainWindow();
shell.Show();
return shell;
}
}

Using the bootstrapper with generic shell definition


Most of the time, the CreateShell method simple defines the main window, creates it and returns it. This can be automated using Catel as well by
using the generic bootstrapper. This way, the bootstrapper stays really small and can be kept very simple.

/// <summary>
/// The bootstrapper that will create and run the shell.
/// </summary>
public class MyApplicationBootstrapper : BootstrapperBase<MainWindow>
{
/// <summary>
/// Initializes a new instance of the <see cref="MyApplicationBootstrapper"/>
class.
/// </summary>
public MyApplicationBootstrapper()
{
LogManager.RegisterDebugListener();
}
/// <summary>
/// Creates the <see
cref="T:Microsoft.Practices.Prism.Modularity.IModuleCatalog"/> used by Prism.
/// </summary>
/// <returns></returns>
protected override IModuleCatalog CreateModuleCatalog()
{
var moduleCatalog = new DirectoryModuleCatalog { ModulePath = @".\Modules"};
moduleCatalog.Initialize();
return moduleCatalog;
}
}

Declaring modules
When developing a module in Prism, most of the time you need a base class for all the models that contain the IoC container, IRegionManager an
d more. To make development with prism and Catel as easy as possible, the ModuleBase is included with Catel. There are two versions of the Mo
duleBase available, which are described below.

Generic ModuleBase
The generic module base allows the end-developer to decide what IoC container is used. For example, the developer has the choice whether the
ServiceLocator or any other IoC container such as Unity or MEF is used.

Defining a module
Defining a module is very simple. Just create a new class with the ModuleBase as base class.

public class MyModule : ModuleBase<IServiceLocator>


{
public MyModule()
: base("My module", ServiceLocator.Instance.ResolveType<IModuleTracker>(),
ServiceLocator.Instance)
{
}
protected override T GetService<T>()
{
return Container.ResolveType<T>();
}
}

Handling code when the module is initialized


The ModuleBase contains convenience methods when the module is initialized. Simple override the OnInitializing or OnInitialized methods.

Non-generic ModuleBase
The non-generic base uses the ServiceLocator as default IoC container. This class derives from the generic module base and specifies the Servic
eLocator as IoC container.

Module catalogs
Catel ships with different module catalog implementations.
CompositeModuleCatalog
DownloadingModuleCatalog
NuGetBasedModuleCatalog
SafeDirectoryModuleCatalog

CompositeModuleCatalog
The CompositeModuleCatalog is a catalog that can combine different types of catalogs.
Initializing the catalog
Customizing the catalog

Initializing the catalog


Below is an example of the catalog in action:

protected override void ConfigureModuleCatalog()


{
base.ConfigureModuleCatalog();
ModuleCatalog.Add(new DirectoryModuleCatalog
{
ModulePath = @".\Modules"
});
ModuleCatalog.Add(new NuGetBasedModuleCatalog
{
PackageSource = @"C:\SomeDir\localNugetSource",
AllowPrereleaseVersions = true,
IgnoreDependencies = false
});
ModuleCatalog.Initialize();
}

Customizing the catalog


No customization options documented yet - feel free to contribute

DownloadingModuleCatalog
The DownloadingModuleCatalog allow the downloading of all modules dynamically based on the module info.
Initializing the catalog
Customizing the catalog

Initializing the catalog


protected override void ConfigureModuleCatalog()
{
base.ConfigureModuleCatalog();
}

Customizing the catalog


No customization options documented yet - feel free to contribute

NuGetBasedModuleCatalog
The NuGetBasedModuleCatalog allows a user to use a NuGet package source as a module source.
NuGetModuleCatalog is not supported into Silverlight

Note that the CompositeNuGetBasedModuleCatalog works the same but can combine multiple NuGet sources

Initializing the catalog


Initializing the composite catalog
Customizing the catalog
Changing the default initialization mode
Creating a module
Module vs. library dependencies
Expected package structure
Implementing a customized module catalog
Solving the loadFromRemoteSources exception

Initializing the catalog


The catalog has several options. Below is an example of a default customization:

protected override void ConfigureModuleCatalog()


{
base.ConfigureModuleCatalog();
ModuleCatalog.IgnoreDependencies = false;
ModuleCatalog.AllowPrereleaseVersions = true;
ModuleCatalog.PackageSource = @"https://www.nuget.org/api/v2/",
}

Initializing the composite catalog


The composite catalog can be initialized using the code below:

protected override void ConfigureModuleCatalog()


{
base.ConfigureModuleCatalog();
ModuleCatalog.Add(new NuGetBasedModuleCatalog
{
PackageSource = @"C:\SomeDirectory\localNugetSource",
AllowPrereleaseVersions = true,
IgnoreDependencies = false,
DefaultInitializationMode = InitializationMode.WhenAvailable
});
ModuleCatalog.Add(new NuGetBasedModuleCatalog
{
PackageSource = @"https://www.nuget.org/api/v2/",
AllowPrereleaseVersions = true,
IgnoreDependencies = false,
});
}

Customizing the catalog


There are several customization options.

Changing the default initialization mode


By default, the modules are loaded on demand to prevent a user downloading all the modules at once. To change this behavior, use the DefaultIn

itializationMode property.

ModuleCatalog.DefaultInitializationMode = InitializationMode.WhenAvailable;

Creating a module
To prevent the catalog to consider all packages on a source as a module, there is a naming convention required for the modules. In the nuspec fil
e, make sure to use the following description element:

<?xml version="1.0" encoding="utf-8"?>


<package xmlns="http://schemas.microsoft.com/packaging/2010/07/nuspec.xsd">
<metadata>
<id>TestModule</id>
<version>1.0.0</version>
<authors>[someauthor]</authors>
<requireLicenseAcceptance>false</requireLicenseAcceptance>
<description>ModuleName=<moduleName>;ModuleType=<moduleType>;DependsOn={
<moduleName>, <moduleName> }</description>
<dependencies>
<dependency id="<dependencyId>" version="<dependencyVersion>" />
</dependencies>
</metadata>
</package>

For example:

<?xml version="1.0" encoding="utf-8"?>


<package xmlns="http://schemas.microsoft.com/packaging/2010/07/nuspec.xsd">
<metadata>
<id>TestModule</id>
<version>1.0.0</version>
<authors>[someauthor]</authors>
<requireLicenseAcceptance>false</requireLicenseAcceptance>
<description>ModuleName=Catel.Examples.WPF.Prism.Modules.NuGetBasedModuleC.NuGetBasedM
oduleC;
ModuleType=Catel.Examples.WPF.Prism.Modules.NuGetBasedModuleC.NuGetBasedModuleC,
Catel.Examples.WPF.Prism.Modules.NuGetBasedModuleC; DependsOn={
Catel.Examples.WPF.Prism.Modules.NuGetBasedModuleB.NuGetBasedModuleB }</description>
<dependencies>
<dependency id="Newtonsoft.Json" version="6.0.8" />
</dependencies>
</metadata>
</package>

It is possible to manually add a module, then the naming convention is not required

Module vs. library dependencies


There a two kind of dependencies that you can declare in a module nuspec file.
Module dependencies in order to identify Prism like module dependencies using the key DependsOn at description tag.

<description>ModuleName=Catel.Examples.WPF.Prism.Modules.NuGetBasedModuleC.NuGetBasedM
oduleC;
ModuleType=Catel.Examples.WPF.Prism.Modules.NuGetBasedModuleC.NuGetBasedModuleC,
Catel.Examples.WPF.Prism.Modules.NuGetBasedModuleC; DependsOn={
Catel.Examples.WPF.Prism.Modules.NuGetBasedModuleB.NuGetBasedModuleB }<description>

Or you can specify libraries dependencies using the dependencies section just as regular nuspec file.

<dependencies>
<dependency id="Newtonsoft.Json" version="6.0.8" />
</dependencies>

Expected package structure


The package structure is like a regular nupkg file. It is recommended to locate the assemblies into the lib directory, specifically into the target
framework directory. Prism can run under v4.0 or v4.5 net framework version. So, an example of package structure is the follow:
lib/NET45/Catel.Examples.WPF.Prism.Modules.NuGetBasedModuleC.dll
lib/NET40/Catel.Examples.WPF.Prism.Modules.NuGetBasedModuleC.dll
But if the assembly doesn't found in the expected location - due by the running current platform - Catel will try to find the assembly into the
package lib directory recursively.

Implementing a customized module catalog


The NuGetBasedModuleCatalog is heavily customizable. For example, by default it uses the naming convention and uses OnDemand only for the
load behavior. Below is an example of an implementation that directly loads all available modules:

public class LoadImmediatelyNuGetBasedModuleCatalog : NuGetBasedModuleCatalog


{
// Override GetFilteredPackagedModules, GetPackageInitializationMode or
CreatePackageModule to create a fully customized catalog
}

Solving the loadFromRemoteSources exception


For some applications, the following exception might be thrown:

An attempt was made to load an assembly from a network


location which would have caused the assembly to be sandboxed in previous
versions of the .NET Framework. This release of the .NET Framework does not
enable CAS policy by default, so this load may be dangerous.

If this load is not intended to sandbox the assembly,


please enable the loadFromRemoteSources switch. See

http://go.microsoft.com/fwlink/?LinkId=155569
for more information

To solve this, add this to the app.config file:

<runtime>
<loadFromRemoteSources enabled="true"/>
</runtime>

SafeDirectoryModuleCatalog
The SafeDirectoryModuleCatalog is a safe implementation of the DirectoryModuleCatalog that ships with prism.
Initializing the catalog
Customizing the catalog

Initializing the catalog


protected override void ConfigureModuleCatalog()
{
base.ConfigureModuleCatalog();
ModulePath = @".\Modules"
}

Customizing the catalog


No customization options documented yet - feel free to contribute

Translating or customizing the initialization task messages


Starting with version 3.7, it is possible to fully customize the bootstrapper tasks. Catel now uses the IBootstrapperTaskFactory to create the tasks
instead of the bootstrapper itself. To customize the logic, one has to implement his/her own version of the IBootstrapperTaskFactory. The easiest
way to do this is to derive from the existing BootstrapperTaskFactory and register it in the service locator before the bootstrapper is created.

Customizing the messages


The example below customizes the messages that are shown during the initialization tasks.

public class TranslatedBootstrapperTaskFactory : BootstrapperTaskFactory


{
public override ITask CreateCreateLoggerTask(Action action)
{
return CreateCreateLoggerTask(action, "We are now creating the logger for
you");
}
}

Remember to register the TranslatedBootstrapperTaskFactory before the bootstrapper is created

Note that this example only customizes a single action. To customize all the actions, override all methods

Catel.Extensions.Wcf.Server
Documentation must be written here

Catel.Fody
Fody is an extensible tool for weaving .NET assemblies. For more information about Fody, see its official website.
Enabling Catel.Fody
Available functionality
Disabling weaving for specific types or properties
Configuring Catel.Fody

Enabling Catel.Fody
To enable Catel.Fody to weave assemblies, you need to perform the following steps:
Install the Catel.Fody NuGet package
Update FodyWeavers.xml and make sure it contains <Catel />

Note that the FodyWeavers.xml should be updated automatically when you install the package

Available functionality
Below are the several options available in Catel.Fody:
Weaving properties
Weaving argument checks
Exposing properties on view models
XmlSchema generation

Disabling weaving for specific types or properties


To disable the weaving of types or properties of a type, decorate it with the NoWeaving attribute as shown in the example below:

[NoWeaving]
public class MyClass : ModelBase
{
...
}

Configuring Catel.Fody
Though we recommend to leave the default settings (great for most people), it is possible to configure the weaver. Below is a list of options that
can be configured.
Property

WeaveProperties

Default
value
true

Description

Weave all regular properties on classes that inherit (directly or indirectly) from Catel.Data.ModelBase
into Catel properties.

WeaveExposedProperties

true

Weave all Catel properties decorated with both the Catel.MVVM.Model attribute and Fody.Expose att
ribute as automatic mappings.

WeaveArguments

true

Weave all Argument check attributes into actual argument checks.

WeaveLogging

true

Weave all calls to LogManager.GetCurrentClassLogger() into LogManager.GetLogger(typeof(classna


me)).

GenerateXmlSchemas

false

Generate xml schemas for all classes that inherit (directly or indirectly) from Catel.Data.ModelBase.

To configure an option, modify FodyWeavers.xml by adding the property and value to the Catel element. For example, the example below will
disable argument and logging weaving:

<Catel WeaveArguments="false" WeaveLogging="false" />

Weaving properties
Support for computed properties
Automatically excluded properties
Specifying default values for weaved properties
How to get automatic change notifications
The PropertyChanged.Fody plugin for Fody already supports Catel out of the box, but only for property change notifications. However, with the
Catel.Fody plugin, it is possible to automatically weave a simple property into a Catel property.
The following property definition:

public string Name { get; set; }

will be weaved into:

public string Name


{
get { return GetValue<string>(NameProperty); }
set { SetValue(NameProperty, value); }
}
public static readonly PropertyData NameProperty = RegisterProperty("Name",
typeof(string));

Support for computed properties


If a computed property like this one exists:

public string FullName


{
get { return string.Format("{0} {1}", FirstName, LastName).Trim(); }
}

the OnPropertyChanged method will be also weaved into

protected override void OnPropertyChanged(AdvancedPropertyChangedEventArgs e)


{
base.OnPropertyChanged(e);
if (e.PropertyName.Equals("FirstName"))
{
base.RaisePropertyChanged("FullName");
}
if (e.PropertyName.Equals("LastName"))
{
base.RaisePropertyChanged("FullName");
}
}

In the background, Catel.Fody will handle the following workflow:


Find all types in the assembly deriving from ModelBase (thus also ViewModelBase)
Check if the type has an automatic property backing field (only those properties are weaved)
Add the PropertyData field for the property
Instantiate the PropertyData field in the static constructor of the type
Replace the content of the getter and setter with the appropriate calls to GetValue and SetValue

Note that this feature is automatically disabled for classes that already override the OnPropertyChanged method. It is too complex to
determine where the logic should be added so the end-developer is responsible for implementing this feature when overriding OnProper
tyChanged

Automatically excluded properties


By default, Catel.Fody ignores the following properties and types by default because they shouldn't be weaved:
All properties of type ICommand
Properties without an automatically generated backing field

Specifying default values for weaved properties


By default, Catel uses null as default values for reference types. For value types, it will use default(T). To specify the default value of a weaved
property, use the DefaultValue attribute as shown in the example below:

public class Person : ModelBase


{
[DefaultValue("Geert")]
public string FirstName { get; set; }
public string LastName { get; set; }
}

This will be weaved into:

public class Person : ModelBase


{
public string FirstName
{
get { return GetValue<string>(FirstNameProperty); }
set { SetValue(FirstNameProperty, value); }
}
public static readonly PropertyData FirstNameProperty = RegisterProperty("FirstName",
typeof(string), "Geert");
public string LastName
{
get { return GetValue<string>(LastNameProperty); }
set { SetValue(LastNameProperty, value); }
}
public static readonly PropertyData LastNameProperty = RegisterProperty("LastName",
typeof(string), null);
}

How to get automatic change notifications


So, the Fody plugin for Catel automatically searches for the On[PropertyName]Changed methods. If a method is found, it will automatically be
called when the property has changed. For example, the OnNameChanged is automatically called when the Name property is changed in the
example below:

public string Name { get; set; }


private void OnNameChanged()
{
// this method is automatically called when the Name property changes
}

Weaving argument checks


With the Catel.Fody plugin, it is possible to automatically weave a method implementation with its own argument check operations declared via
attributes.
Automatic performance improvements
Usage example
Available argument check Catel.Fody attributes

Automatic performance improvements


The latest version of Catel.Fody automatically converts all expression argument checks to faster calls. For example, the code below:

Argument.IsNotNull(() => myString);

Will automatically be weaved into this:

Argument.IsNotNull("myString", myString);

This is much faster because the expression doesn't have to be parsed at runtime. This is a very noticeable performance boost if the expression
check is used more than 50 times per second.
When using the latest version of Catel.Fody, the team recommends using expressions above the regular argument checks (with name
and value specified separately) because it will result in cleaner code. With this feature, there is no longer a performance penalty for
using the expressions version

Usage example
The following method definition:

public void DoSomething([NotNullOrEmpty] string myString. [NotNull] object myObject)


{
}

Will be weaved into:

public void DoSomething(string myString, object myObject)


{
Argument.IsNotNullOrEmpty(myString, myString);
Argument.IsNotNull(myObject, myObject);
}

In the background, Catel.Fody will handle the following workflow:


1.
2.
3.
4.

Find all types in the assembly


Find all method of each type
Find all annotated method parameter of each method
Insert as first instructions of the method body the calls to Argument check corresponding methods.

Available argument check Catel.Fody attributes


The following table shows the available argument check attributes and its corresponding Argument class checks method:
Fody attribute

Argument method

NotNull

Argument.IsNotNull

NotNullOrEmptyArray

Argument.IsNotNullOrEmptyArray

NotNullOrEmpty

Argument.IsNotNullOrEmpty

NotNullOrWhitespace

Argument.IsNotNullOrWhitespace

Match

Argument.IsMatch

NotMatch

Argument.IsNotMatch

NotOutOfRange

Argument.IsNotOutOfRange

Maximum

Argument.IsMaximum

Minimal

Argument.IsMinimal

OfType

Argument.IsOfType

ImplementsInterface

Argument.ImplementsInterface

InheritsFromAttribute

Argument.InheritsFrom

Exposing properties on view models

The Catel version for WPF provides the Expose attribute. Starting with Catel 3.8, this feature has been moved to Fody to support all platforms
instead of just WPF. One of the features that already existed in Catel before is the ViewModelToModelAttribute. The goal of these attributes is to
easily map properties from a model to the view model so as much of the plumbing (setting/getting properties, rechecking validation, etc) is done
automatically for the developer.
Using the ViewModelToModelAttribute, this is the syntax to map properties automatically:

/// <summary>
/// Gets or sets the person.
/// </summary>
[Model]
public Person Person
{
get { return GetValue<Person>(PersonProperty); }
private set { SetValue(PersonProperty, value); }
}
/// <summary>
/// Register the Person property so it is known in the class.
/// </summary>
public static readonly PropertyData PersonProperty = RegisterProperty("Person",
typeof(Person));
/// <summary>
/// Gets or sets the first name.
/// </summary>
[ViewModelToModel("Person")]
public string FirstName
{
get { return GetValue<string>(FirstNameProperty); }
set { SetValue(FirstNameProperty, value); }
}
/// <summary>
/// Register the FirstName property so it is known in the class.
/// </summary>
public static readonly PropertyData FirstNameProperty = RegisterProperty("FirstName",
typeof(string));

However, if you only define the FirstName property just to protect your model, then why should you define the whole property? This is where the E
xposeAttribute property comes in very handy. This attribute internally registers a new dynamic property on the view model, and then uses the
same technique as the ViewModelToModelAttribute.
Below is the new way you can easily expose properties of a model and protect other properties of the model from the view:

/// <summary>
/// Gets or sets the person.
/// </summary>
[Model]
[Expose("FirstName")]
[Expose("MiddleName")]
[Expose("LastName")]
private Person Person
{
get { return GetValue<Person>(PersonProperty); }
set { SetValue(PersonProperty, value); }
}
/// <summary>
/// Register the Person property so it is known in the class.
/// </summary>
public static readonly PropertyData PersonProperty = RegisterProperty("Person",
typeof(Person));

This is a very cool feature that allows you to protect your model without having to re-define all the properties on the view model. Also, the
validation in the model is automatically synchronized with the view model when you use this attribute.

XmlSchema generation
The .NET framework supports XmlSchema attributes to allow static members to define a custom schema method required for WCF serialization.
Unfortunately this cannot be implemented in Catel itself because it would required too much reflection and the method is static. Therefore this
feature included in Catel.Fody.
Starting with Catel.Fody 2.0, this feature is disabled by default. To enabled it, use the following option in FodyWeavers.xml:

<Catel GenerateXmlSchemas="true" />

When the XmlSchemaProvider is available on the target platform where Catel is used, the changes will be made to classes deriving from ModelB
ase:
1. Decorate the class with XmlSchemaProvider attribute:

[XmlSchemaProvider("GetXmlSchemaForCatelFodyTestAssemblyInheritedClass")]
public class InheritedClass : BaseClass
{
// rest of the class definition
}

2. Implement the class specific GetXmlSchema method:

[CompilerGenerated]
public sta