Make ResourceDitionary flat instead of nested MergedDictionaries

时间:2017-10-12 10:02:59

标签: c# .net wpf

In 'enterprise-level' application we are loading from externall assembly one big ResourceDictionary containing many merged dictionaries which contain another merged dictionaries and so on ... and then assign this one big loaded resource to Application.Current.Resources as a merged resource. As a result Application.Current.Resources contains one big merged resource with lots of nestig levels of another mergerd resources. The idea is to make it flat which means iterate throughout this one big resource and assign keys to Application.Current.Resources instead of adding it as a merged resource. Something like this:

var flattedKeyValues = new Dictionary<object, object>();
var alreadyFlattenedResources = new List<string>();

AddAllLevelKeysFromResource(loadedBigResource, flattedKeyValues, alreadyFlattenedResources);

foreach (var keyValue in flattedKeyValues)
{
    System.Windows.Application.Current.Resources.Add(keyValue.Key, keyValue.Value);
} 

where:

// recursive method
    private static void AddAllLevelKeysFromResource(ResourceDictionary rootResDictionary, Dictionary<object, object> keyValues, List<string> alreadyFlattenedResources)
    {
        if (alreadyFlattenedResources.Contains(rootResDictionary.Source.OriginalString))
        {
            return; //to not to unnecessary iterate twice already iterated resource
        }

        foreach (var resDictionary in rootResDictionary.MergedDictionaries)
        {
            AddAllLevelKeysFromResource(resDictionary, keyValues, alreadyFlattenedResources);
        }
        AddFirstLevelKeysFromResource(rootResDictionary, keyValues);

        alreadyFlattenedResources.Add(rootResDictionary.Source.OriginalString);
    }

and

private static void AddFirstLevelKeysFromResource(ResourceDictionary resDictionary, Dictionary<object, object> keyValues)
{
    foreach (var key in resDictionary.Keys)
    {
        if (keyValues.ContainsKey(key))
        {
            keyValues[key] = resDictionary[key]; // because later added key should override previous key
        }
        else
        {
            keyValues.Add(key, resDictionary[key]);
        }
    }
}

However it doesn't work because some of the styles/resources items are not set correctly. Is it possible to flat resource like this? Or maybe it is not enough to just copy the keys and values because each mergerd resource object contain some other required informations for his keys? (we mostly use DynamicResources)

0 个答案:

没有答案