在合并字典中共享静态资源

12

我目前正在努力实现样式和模板的字典,以便可以动态应用到我的应用程序中。在实现这种新的动态行为之前,我有几个资源字典,每个控件都有一个,我将它们合并在App.xaml中:

<Application.Resources>
    <ResourceDictionary>
        <ResourceDictionary.MergedDictionaries>
            <ResourceDictionary Source="ColorsDictionary.xaml"/>
            <ResourceDictionary Source="ControlsTemplatesDictionary.xaml"/>
        </ResourceDictionary.MergedDictionaries>
    </ResourceDictionary>
</Application.Resources>

现在,我希望我的应用程序有样式,所以我决定将之前所有的资源合并为一个名为"MyFirstTemplates"的新资源,并将仅此字典添加到App.xaml。

新的字典"MyFirstTemplates.xaml":

<ResourceDictionary xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
                xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml">"
    <ResourceDictionary.MergedDictionaries>
        <ResourceDictionary Source="ColorsDictionary.xaml"/>
        <ResourceDictionary Source="ControlsTemplatesDictionary.xaml"/>
    </ResourceDictionary.MergedDictionaries>
</ResourceDictionary>

新的 App.xaml 文件:

<Application.Resources>
    <ResourceDictionary>
        <ResourceDictionary.MergedDictionaries>
            <ResourceDictionary Source="MyFirstTemplates.xaml"/>
        </ResourceDictionary.MergedDictionaries>
        <Style TargetType="{x:Type Window}"/>
    </ResourceDictionary>
</Application.Resources>
注意: Window 的默认样式是为了修复 WPF 4 的错误,请参见添加合并字典到一个合并字典中
现在我已经做出了这个改变,我不能再像以前那样在“ControlsTemplateDictionary.xaml”中使用“ColorsDictionary.xaml”中的颜色资源作为StaticResource。如果我改回将这些文件合并在 app.xaml 中,一切正常。为了让它工作,我必须将这些StaticResource 改为 DynamicResource。你有任何想法为什么这不再起作用吗?
谢谢 :-)
2个回答

10
通过将字典从 App.xaml 中移出,每个字典的资源在加载 MyFirstTemplates.xaml 期间不会出现在另一个字典的资源树中。您原始的设置首先加载 ColorsDictionary,然后通过 App 资源提供给 ControlsTemplatesDictionary,同时进行加载。在您的新设置中,为了使颜色资源在 App 资源中可用,它需要通过 MyFirstTemplates 进行加载,这反过来需要加载两个字典,这又需要访问颜色资源... 所以它是一种无法在静态上下文中解决的引用的无限循环。DynamicResource 可以等待所有内容加载完成,然后无问题地访问颜色。
要修复此问题,请使用 DynamicResource 或直接将 ColorsDictionary 合并到 ControlsTemplatesDictionary 中。

2
伟大的答案,John解释了这个问题发生的原因。问题在于,在合并的字典中使用合并的字典时,内部字典无法将彼此作为静态资源“使用”。
基本解决方案:
- 使用DynamicResource - 当使用StaticResource时,只使用来自App.xaml的单个层次结构
这两种解决方案都存在问题。DynamicResource存在性能问题。第二种解决方案限制了您如何组织XAML资源。
替代解决方案:
我创建了一个小程序(在GitHub中提供),它将作为预构建事件运行,并将文件夹中的XAML文件合并为一个长的.XAML文件。好吧,它们需要具有不同的扩展名(.txaml),否则它们将被编译。
这样可以以任何你想要的方式结构化资源文件夹和文件,而不受WPF的限制。StaticResource和设计师始终可以正常工作。
GitHub中的代码 包含了一个简单的解决方案,其中包含合并程序。它将2个文件夹合并为2个文件。一个用于App.xaml资源,另一个用于Generic.xaml资源。在一个“控件”项目中的.xaml文件(还有“主”项目)。”
博客文章解释了这个。”

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接