[ACCEPTED]-WPF: Changing Resources (colors) from the App.xaml during runtime-app.xaml

Accepted answer
Score: 16

It looks like you're trying to do some sort 11 of skinning?

I'd recommend defining the resources 10 in a Resource Dictionary contained in a 9 separate file. Then in code (App.cs to load 8 a default, then elsewhere to change) you 7 can load the resources as so:

//using System.Windows
ResourceDictionary dict = new ResourceDictionary();
dict.Source = new Uri("MyResourceDictionary.xaml", UriKind.Relative);

Application.Current.Resources.MergedDictionaries.Add(dict);

You could also 6 define the default resource dictionary in 5 App.xaml and unload it in code just fine.

Use 4 the MergedDictionaries object to change 3 the dictionary you're using at runtime. Works 2 like a charm for changing an entire interface 1 quickly.

Score: 13

Changing application wide resources in runtime 11 is like:

Application.Current.Resources("MainBackgroundBrush") = Brsh

About the InvalidOperationException, i 10 guess WallStreet Programmer is right. Maybe 9 you should not try to modify an existing 8 brush, but instead create a new brush in 7 code with all the gradientstops you need, and 6 then assign this new brush in application 5 resources.

Another Approach on changing 4 the color of some GradientStops is to define 3 those colors as DynamicResource references 2 to Application Wide SolidColorBrushes like:

<LinearGradientBrush x:Key="MainBrush" StartPoint="0, 0.5" EndPoint="1, 0.5" >
<GradientBrush.GradientStops>
    <GradientStop Color="{DynamicResource FirstColor}" Offset="0" />
    <GradientStop Color="{DynamicResource SecondColor}" Offset="1" />
</GradientBrush.GradientStops>

and 1 then use

Application.Current.Resources["FirstColor"] = NewFirstColorBrsh
Application.Current.Resources["SecondColor"] = NewSecondColorBrsh

HTH

Score: 3

Use the Clone() method to make a deep copy of the 5 brush (or any other freezable object like 4 Storyboard) and then use it:

LinearGradientBrush myBrush = FindResource("MainBrush") as LinearGradientBrush;
myBrush = myBrush.Clone();
myBrush.GradientStops[0].Color = Colors.Red;

@WallstreetProgrammer 3 is right - all application level resources 2 are frozen by default.

Thats why you need 1 to clone the object first.

Score: 2

You get an exception because you are trying 5 to modify a frozen object. All application 4 level resources are automatically frozen 3 if they are freezable and LinearGradientBrush 2 is. If you add it on a lower level like 1 window level it will work.

More Related questions