WPF、自定义控件和 style/theme 继承

WPF, custom controls, and style/theme inheritance

我正在处理一个已经存在的项目,我无法按照我想要的方式设置样式。

我从一个应用程序开始:

到目前为止,一切正常。


然后...

我正在构建一个派生自 Expander:

的自定义控件
internal partial class TestExpander : Expander

通过创建自定义控件,VStudio 已将 Theme 文件夹添加到项目中,其中包含通常的 Generic.xaml里面的文件。在这个文件中,我为自定义控件创建了样式:

<Style TargetType="{x:Type local:TestExpander}" BasedOn="{StaticResource {x:Type Expander}}">
    <Style.Resources>
        <BooleanToVisibilityConverter x:Key="BooleanToVisibility"/>
    </Style.Resources>

    <Setter Property="ExpandDirection" Value="Down"/>
    <Setter Property="IsExpanded" Value="{Binding IsExpanded, Mode=TwoWay}"/>
    <Setter Property="HorizontalAlignment" Value="Stretch"/>
    <Setter Property="VerticalAlignment" Value="Top"/>
    <Setter Property="Cursor" Value="Hand"/>
</Style>

显然在自定义控件的代码中我有:

static TestExpander()
        {
            DefaultStyleKeyProperty.OverrideMetadata(typeof(TestExpander), new FrameworkPropertyMetadata(typeof(TestExpander)));
        }

我期望我的 TestExpander 继承 WhistlerBlue.xaml[ 中定义的 Expander 样式=51=], 加上自己的个性风格, 从此过上了幸福的生活。

这没有发生。我哪里错了?

因此,当我们为各种事物创建继承架构时,很容易忘记事物接收其继承部分的顺序。因此,例如,当我们放置一个直接查看 x:Type 的 BasedOn 时,它就会按照它可用的继承顺序去寻找它,对吗?

当它正在寻找 x:Type 并且它不知道另一个字典中的覆盖时......他直接进入默认的原始字典。但是,如果我们注入包含您想要通过 ResourceDictionary.MergedDictionaries 继承的内容的字典,那么它知道在他返回框架默认值之前先看看他,世界上一切都很好。

附带说明一下,当您以这种方式合并字典以进行继承时,您必须注意自己的操作方式,否则可能会影响性能。因为说它是一个合并的字典....在运行时它会合并字典中的所有内容并将所有内容复制到新字典中。

所以对于这个例子......如果是我,我可能会忽略 generic.xaml 词典内容,如果它不是真的必要的话,并将该模板放在现有词典中,就在模板所在的位置下面寻找继承自放置。那么你就不会再复制一整本字典,它仍然会得到它的继承,生活应该是美好的。希望这可以帮助。 :)