.net WPF:我可以通过样式定义/设置附加属性吗?

.net WPF:我可以通过样式定义/设置附加属性吗?,.net,wpf,silverlight,.net,Wpf,Silverlight,有没有办法通过样式设置附着的特性 例如,我有一个按钮,上面设置了交互内容(来自System.Windows.Interactive) ... 现在,我想创建一种样式,在其中设置Interaction.Triggers属性,从而通过在每个按钮实例上指定该属性来替换冗余。这在WPF中可能吗 <Style Target={x:Type Button}> <!-- ??? --> <Setter PropertyName="i.Interaction.Trigg

有没有办法通过样式设置附着的特性

例如,我有一个按钮,上面设置了交互内容(来自System.Windows.Interactive)


...
现在,我想创建一种样式,在其中设置Interaction.Triggers属性,从而通过在每个按钮实例上指定该属性来替换冗余。这在WPF中可能吗

<Style Target={x:Type Button}>
  <!-- ??? -->
  <Setter PropertyName="i.Interaction.Triggers">
  ...

...
不知怎的,我不知道怎么做,但我在网上看到过其他例子,在这些例子中,附加属性似乎可以从样式中访问

更新


所以基本上这是一个与交互有关的问题。触发器无法“设置”某些东西。如何重用一组交互定义?

这是只读集合属性的已知问题(InputBindings集合也是如此)。为了解决此问题,我创建了一个附加属性:

public static StyleTriggerCollection GetTriggers(DependencyObject obj) {
    return (StyleTriggerCollection)obj.GetValue(TriggersProperty);
}

public static void SetTriggers(DependencyObject obj, StyleTriggerCollection value) {
    obj.SetValue(TriggersProperty, value);
}

public static readonly DependencyProperty TriggersProperty =
    DependencyProperty.RegisterAttached("Triggers", typeof(StyleTriggerCollection), typeof(ControlExtensions), new UIPropertyMetadata(null, OnTriggersChanged));

static void OnTriggersChanged(DependencyObject d, DependencyPropertyChangedEventArgs e) {
    var triggers = (StyleTriggerCollection) e.NewValue;

    if (triggers != null) {
        var existingTriggers = Interaction.GetTriggers(d);

        foreach (var trigger in triggers) {
            existingTriggers.Add((TriggerBase)trigger.Clone());
        }
    }
}
此属性使用自定义StyleTriggerCollection,因为标准触发器集合没有公共构造函数:

public class StyleTriggerCollection : Collection<TriggerBase>
{
}
公共类StyleTriggerCollection:集合
{
}
在样式设置器中,您可以这样使用它:

<Setter Property="my:ControlExtensions.Triggers">
    <Setter.Value>
        <my:StyleTriggerCollection>
            <!-- Put your triggers here -->
        </my:StyleTriggerCollection>
    </Setter.Value>
</Setter>


可能重复:看起来很有希望,我一回到代码上就会看一看!这似乎有效,但我对在触发器中使用DataContext感到困惑。我似乎无法让RelativeSource、AncestorType等工作……您需要了解RelativeSource是如何工作的。它适用于可视树中的元素。在这种情况下,触发器不在可视化树中-触发器集合只是可视化树中某个元素的属性。数据上下文继承在本例中起作用的原因是触发器继承Freezable。你可以在这里读到它:我走了一条稍微不同的路线,因为我认为我已经做了所有必要的步骤来支持Freezable的功能,但它不起作用。无论如何,更多的努力应该会发现这很好,所以这对我来说是一个答案:)这对我来说非常有效。一个恼人问题的优雅解决方案+1.
<Setter Property="my:ControlExtensions.Triggers">
    <Setter.Value>
        <my:StyleTriggerCollection>
            <!-- Put your triggers here -->
        </my:StyleTriggerCollection>
    </Setter.Value>
</Setter>