Resources in WPF – Static and Dynamic Resource and Resource Dictionary

WPF Resources such as static or dynamic resources are file or objects which are not part of executable code. WPF provides binary and logical resources. While binary resources will be files, logical resources will be defined as part of XAML.

Using WPF Binary resource:

These are large files like videos, images or data files which can be compiled as part of application and later retrieved in the code. There few ways with with which you can access binary resource.

1. Embedding resource: You can add any file to project and set build action of that file to resource. To retrieve them in your code youcan use following ways

A. Use their path e.g Source=”folder/file.jpeg” in Image class. Image class will find the path for you.

B. Pack URIs pack://<Authority>/<Folder>/<FileName> . Generally authority is Application. e.g.

<Image Source=”pack://application:,,,/folder/myPic.jpeg” Name=”MyPic” />

C. To locate resource in other assembly you can use

pack://application:,,,/<AssemblyName>;component/<Folder>/<FileName>

If your file is changing frequently then its not fair to embed it in application. As every time it changes you have to recompile application.

So add such files by

D. Add to project, Set build type as Content and Set Copy to Output directory to always. Now you can retrieve it using relative URI.

E. To refer to loose files who change often you can also use siteOfOrigin in pack uri. This can give root of application folder if installed by windows installer or URI in case of ClickOnce deployment or host in case of XBAP applications.

e.g. <Image Source=”pack://siteOfOrigin:,,,/MyPic.jpeg”/>

wpf-resources-static-dynamic-resource

wpf-resources-static-dynamic-resource

If resource object do not support pack uri then you have to locate them by Application.GetResourceStream passing relative path. Which will return a StreamResourceInfo, which can be used to get stream for that object.

WPF Resource only dlls

If your resource files change often then group them into separate dll and compile them to create resource only dll. To make this resource only dll you can add all resource with embedded resource build action. Once you build dll then use reflection to access those resources in your application.

e.g

String[] resources = assembly.GetManifestResourceNames();
pictureBox1.Image = new System.Drawing.Bitmap(assembly.GetManifestResourceStream(resources[0]));

Logical resources

Logical resourcesĀ  are objects defined in form of XAML that are not part of the visual tree but are available for use by WPF elements in your user interface. E.g. a brush for all your background for application. This provides reusability as well as flexibility. You can define resources at

1. Application level <Application.Resources>

2. Window level <Window.Resources>

3. Element level <Grid.Resources>

4. Resource dictionary

Each logical resource is made accessible by either x:Key =”Name” or TargetType to some control. If key is specified then control must define thei key name while accessing this resource. For TargetType its automatically assigned to all targets.

Logical Resources can either be access by

{StaticResource name} : Retrieved once by the referencing element and used for the lifetime of the resource.

{DynamicResource name} : Acquired every time the referenced object is used.

Unless and until you want to use changed object underlying the resource its best practice to use static resources unless there is a specific reason for using a dynamic resource.

Creating WPF Resource dictionary

If you have many resource which you want to share between projects then you can assemble them into a resource dictionary. E.g. <ResourceDictionary xmlns=”http://schemas.microsoft.com/winfx/2006/xaml/presentation”
xmlns:x=”http://schemas.microsoft.com/winfx/2006/xaml”>
<SolidColorBrush x:Key=”myBrush” Color=”Blue” />
</ResourceDictionary>

Now if you want to use thisĀ  dictionary in your window then you just have to merge it with window resources and you are ready to go.

<Window.Resources>
<ResourceDictionary>
<ResourceDictionary.MergedDictionaries>
<ResourceDictionary Source=”Dictionary1.xaml” />
<ResourceDictionary Source=”Dictionary2.xaml” />
</ResourceDictionary.MergedDictionaries>
<SolidColorBrush x:Key=”MyBrush” Color=”Blue” />
</ResourceDictionary>
</Window.Resources>

To find a resource using code

You can use FindResource or TryFindResource

SolidColorBrush myBrush;
myBrush= (SolidColorBrush)Button1.FindResource(“MyBrush”);

That’s all you need to know about WPF Resources to use them in your application.

Leave a Reply

Your email address will not be published. Required fields are marked *