触发器与依赖关系属性优先级

时间:2015-06-09 12:19:09

标签: c# .net wpf triggers dependency-properties

我对依赖属性值的优先性有疑问。 我的.xaml看起来如下:

<Window x:Class="WpfTests.MainWindow"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:local ="clr-namespace:WpfTests"
    Title="MainWindow" Height="350" Width="525">
<Window.Style>
    <Style>
        <!--<Setter Property="Canvas.Background" Value="Gray"/>-->
        <Style.Triggers>
            <Trigger Property="local:MainWindow.IsMouseOver" Value="True">
                <!--<Setter Property="local:LeistenPfeil.Symbolfarbe" Value="Red"/>-->
                <Setter Property="local:MainWindow.Cursor" Value="Hand" />
                <Setter Property="local:MainWindow.BG" Value="Blue"/>
            </Trigger>
        </Style.Triggers>
    </Style>
</Window.Style>

<Grid Background="{Binding BG,Mode=TwoWay}">
    <Button Content="ChangeBG" HorizontalAlignment="Center" VerticalAlignment="Center" Click="OnClick"/>
</Grid>

在我的Codebehind中,我创建了依赖属性&#39; BG&#39;像:

public partial class MainWindow : Window
{
    public Brush BG
    {
        get { return (Brush)GetValue(BGProperty); }
        set { SetValue(BGProperty, value); }
    }

    // Using a DependencyProperty as the backing store for BG.  This enables animation, styling, binding, etc...
    public static readonly DependencyProperty BGProperty =
        DependencyProperty.Register("BG", typeof(Brush), typeof(MainWindow), new PropertyMetadata(Brushes.Black));


    public MainWindow()
    {
        InitializeComponent();
        this.DataContext = this;
    }

    private void OnClick(object sender, RoutedEventArgs e)
    {
        BG = Brushes.Green;
    }
}

因此,在启动时,背景设置为黑色(DP的默认值)。当鼠标悬停在背景上时变为蓝色。当我在代码隐藏中更改BG属性时,触发器确实有效,但它对网格背景的影响消失了。 我已经在MSDN上阅读了这篇文章: https://msdn.microsoft.com/en-us/library/ms743230%28v=vs.110%29.aspx

我的理解中的问题是:为什么触发器在BG属性具有其默认值时起作用,而在代码变更后却没有? =&GT;背景的最高优先级是网格的本地背景绑定,那么触发器为什么会起作用呢?

如果在代码后面改变BG属性后,如何让触发器再次工作?

2 个答案:

答案 0 :(得分:1)

您的代码更改实际上被视为本地更改。从MSDN上的链接页面:

  

本地价值。可以通过&#34;包装器&#34;的便利设置本地值。 property,也等同于在XAML中设置为属性或属性元素,或通过使用特定实例的属性调用SetValue API。如果使用绑定或资源设置本地值,则每个都在优先级中操作,就像设置了直接值一样。

我已经突出显示了相关部分,其中声明您(通过SetValue CLR属性)调用BG将导致本地更改。由于本地更改的优先级高于Trigger,因此它会取代Trigger值。

答案 1 :(得分:1)

而不是

BG = Brushes.Green;

设置本地值的优先级高于触发器,你可以编写

SetCurrentValue(BGProperty, Brushes.Green);

来自MSDN

  

... SetCurrentValue方法更改了有效值   属性,但现有的触发器,数据绑定和样式将   继续工作。