如何根据targetTypes修改遗留命名样式以获得不同的setter?

时间:2013-01-09 10:21:40

标签: wpf xaml styles

我有这个命名的风格

<Style x:Key="validationSupport" TargetType="{x:Type Control}">
    <Setter Property="Margin" Value="5,2,14,2" />
    ...OMISSIS...
    <Style.Triggers>
        ...OMISSIS...
        <DataTrigger Binding="{Binding DataContext.ActiveWorkspace.Editable, RelativeSource={RelativeSource  AncestorType=Window}}" Value="False">
            <Setter Property="IsEnabled" Value="False" />
        </DataTrigger>
    </Style.Triggers>

</Style>

我广泛用于TextBoxes,ComboBoxes,DatePickers等,因此我将TargetType用作所有这些元素的超类Control。

现在我想使用'Control'没有的特定属性来区分dataTrigger中的setter。看来我必须创建具有不同名称的不同样式,每个样式对应我想要区分的每个targetType,但是这样我必须在使用它的所有元素中更改样式名称。有没有更聪明的方法来实现这一目标?我不想要修改我拥有的每个xaml文件。

第一次回答后更新

我试图将以下setter放在datatrigger中:

<Setter Property="Background" Value="#FFECECF8" />
<Setter Property="CheckBox.IsEnabled" Value="False" />
<Setter Property="DatePicker.IsEnabled" Value="False" />
<Setter Property="ComboBox.IsEnabled" Value="False" />
<Setter Property="TextBox.IsReadOnly" Value="True" /> 

不幸的是,测试给出了奇怪的结果。尽管前缀应该将其应用程序限制为CheckBoxes,DatePickers和ComboBox,但 IsEnabled 属性也是为TextBoxes设置的。

我最后的需求是使一些控制内容不可更改,避免与禁用控件相关的难以阅读的颜色。从以前的研究中我了解到,改变“禁用”控件的颜色并不是一件容易的事,而是涉及重新定义控件模板。所以我想应用IsReadOnly和Background的组合,但它不适用于上述问题。事实上CheckBoxes,DatePickers和ComboBoxes只能使用 IsEnabled 属性不可更改。 我错过了什么吗?

1 个答案:

答案 0 :(得分:0)

有一种方法,但我必须警告你 - 这远非最佳做法,应该避免

WPF允许您使用所需的类型作为属性的前缀。这样,如果将样式应用于不从前缀类型继承的控件 - 将忽略setter。

<Style x:Key="validationSupport" TargetType="{x:Type Control}">
    <Setter Property="Margin" Value="5,2,14,2" />
    ...OMISSIS...
    <Style.Triggers>
        ...OMISSIS...
        <DataTrigger Binding="{Binding DataContext.ActiveWorkspace.Editable, RelativeSource={RelativeSource  AncestorType=Window}}" Value="False">
            <Setter Property="IsEnabled" Value="False" />
            <Setter Property="Button.Background" Value="Red" />
        </DataTrigger>
    </Style.Triggers>
</Style>

[广泛测试,因为我怀疑它可能会造成内存泄漏。]