I recently investigated a Silverlight performance problem in which XAML pages for child dialogs were taking several seconds to load. Fixing this uncovered the problem of Visual Studio designer and Blend not having access to shared resources when the resources are loaded in the top level application module and there are dynamically-loaded modules implemented in separate projects.
Each page was using a largish number of user controls and each of these was merging in a XAML file from a shared resources assembly, for example:
<UserControl.Resources> <ResourceDictionary> <ResourceDictionary.MergedDictionaries> <ResourceDictionary Source="/SharedAssembly;Component/styles.xaml" /> </ResourceDictionary.MergedDictionaries> </ResourceDictionary> </UserControl.Resources>
styles.xaml in turn merged in several other XAML files:
<ResourceDictionary xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"> <ResourceDictionary.MergedDictionaries> <ResourceDictionary Source="colors.xaml" /> <!-- ... several other resource dictionaries here --> </ResourceDictionary.MergedDictionaries> </ResourceDictionary>
The result was that each time a XAML page was loaded a huge amount of XAML was being loaded from resources and parsed multiple times.
The solution was to move the merging of the individual style files to the the Application class in App.xaml:
<Application xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"> <Application.Resources> <ResourceDictionary> <ResourceDictionary.MergedDictionaries> <ResourceDictionary Source="/SharedAssembly;component/colors.xaml" /> <!-- ... several other resource dictionaries here --> </ResourceDictionary.MergedDictionaries> </ResourceDictionary> </Application.Resources> </Application>
And the reference to styles.xaml in all the other XAML files was removed.
An obvious solution which should have been implemented in the first place, but moving the merged styles to App.xaml on the initially loaded component had a negative side-effect. The application uses a home-brewed MEF-like framework for runtime extensibility and Silverlight components are implemented in multiple projects in multiple solutions. Moving the merging of the XAML files out of individual pages and controls meant that these styles were no longer available when working in the Visual Studio designer or Blend which made it impossible to design pages effectively.
The workaround was based on the fact that Visual Studio designer and Blend both look for styles defined or merged in App.xaml. Instances of App.xaml and App.xaml.cs were added to each project, each App.xaml being the same as above (note that the build action of these App.xaml files must be manually set to ApplicationDefinition in the file's properties in Visual Studio). At runtime these additional instances of App.xaml are ignored and the modules have access to the resources in the top-level App.xaml.