Reputation: 4885
I have got a ResourceDictionary full of PathGeometry's for my Icons, is it possible I can give this ResourceDictionary a name so I can use some C# to view all of my Icons, and just to make things more grouped together?
So I would use one of the PathGeometry's like so for example
App.Current.Resources.Icons["refresh1"] as Geometry
or
App.Current.Resources["Icons"]["refresh1"] as Geometry
Currently I use App.Current.Resources["refresh1"] as Geometry
to use one of the PathGeometry's.
Edit: Unclear why this is, well, unclear. Poster below understood the question but was unclear in my reason for wanting to do this. However my reason isn't required, I just want an answer to what I'm asking, not a discussion on WHY do I want to do this.
Upvotes: 2
Views: 2075
Reputation: 16119
This is one of those very straightforward questions that people will spend more time arguing about than answering! :) People can argue the merit of it as much as they like but once you start doing things like dynamically loading ResourceDictionaries (say, from external plugin DLLs) topics like this suddenly become very relevant indeed!
To answer your question, yes, of course this is possible. The main caveat here is that if you just add ResourceDictionaries to your application resources dictionary then the XAML compiler will get confused about what you're trying to do. The trick here is to explicitly specify a single top-level ResourceDictionary and then add all your resources, including your key'd ResourceDictionaries, as the content of that:
<Application.Resources>
<ResourceDictionary xmlns:sys="clr-namespace:System;assembly=mscorlib">
<ResourceDictionary x:Key="Dictionary1">
<sys:String x:Key="str1a">String 1A</sys:String>
<sys:String x:Key="str1b">String 1B</sys:String>
<sys:String x:Key="str1c">String 1C</sys:String>
</ResourceDictionary>
<ResourceDictionary x:Key="Dictionary2">
<sys:String x:Key="str2a">String 2A</sys:String>
<sys:String x:Key="str2b">String 2B</sys:String>
<sys:String x:Key="str2c">String 2C</sys:String>
</ResourceDictionary>
<!-- All other application resources go here -->
</ResourceDictionary>
</Application.Resources>
Here's some XAML that statically binds to the dictionaries to show that this method works as intended:
<StackPanel>
<ListBox ItemsSource="{StaticResource Dictionary1}" DisplayMemberPath="Value" />
<ListBox ItemsSource="{StaticResource Dictionary2}" DisplayMemberPath="Value" />
</StackPanel>
Result:
If you want to access the resources in code then you'll need to cast the first array lookup to a ResourceDictionary, then index that by the actual item key:
var str = (App.Current.Resources["Dictionary1"] as ResourceDictionary)["str1a"].ToString();
If that's too messy then you can clean it up with a helper class like so:
public class Global
{
static Global _global = new Global();
public static Global Dictionaries { get { return _global; } }
public ResourceDictionary this[string index]
{
get { return App.Current.Resources[index] as ResourceDictionary; }
}
}
Which you would then use like this:
var str = (string)Global.Dictionaries["Dictionary1"]["str1a"];
Upvotes: 3