附加行为的继承

时间:2011-05-10 09:28:11

标签: c# wpf

我想在WPF应用程序中实现一组类似的附加行为。 由于它们共享一大块样板代码,我不想为每一个代码重复,我想创建一个继承它的基本行为。 但由于附加行为中的所有内容都是静态的,我不知道该怎么做。

作为一个例子,采取这种行为,它在mousedown上执行一个方法(真正的行为当然会在事件处理程序中做一些事情):

public static class StupidBehavior
{
    public static bool GetIsEnabled(DependencyObject obj)
    {
        return (bool)obj.GetValue(IsEnabledProperty);
    }

    public static void SetIsEnabled(DependencyObject obj, bool value)
    {
        obj.SetValue(IsEnabledProperty, value);
    }

    // Using a DependencyProperty as the backing store for ChangeTooltip.  This enables animation, styling, binding, etc...
    public static readonly DependencyProperty IsEnabledProperty =
        DependencyProperty.RegisterAttached("IsEnabled", typeof(bool), typeof(StupidBehavior), new UIPropertyMetadata(false, IsEnabledChanged));


    private static void IsEnabledChanged(DependencyObject sender, DependencyPropertyChangedEventArgs args)
    {
        ((UIElement)sender).MouseDown += { (o,e) => MyMethod(); };
    }

    private static void MyMethod()
    {
        MessageBox.Show("Boo");
    }     
}

现在,我想创建一个新的行为,它应该具有不同的MyMethod实现,以及一些控制它的其他属性。该怎么做?

2 个答案:

答案 0 :(得分:2)

您可以创建另一个附加属性,其中包含主要行为作为子类替换调用的详细实现。属性保存的对象可以是非静态的,并且可以像state-object一样使用。

你可能也可以把它放到一个属性中,property == null意味着关闭

答案 1 :(得分:1)

您可以使用静态构造函数构建Dictionary<DependencyProperty,EventHandler>以将特定DP映射到特定处理程序并使用常见的DependencyPropertyChanged回调:

static StupidBehavior()
{
    handlerDictionary[IsEnabledProperty] = (o,e) => MyMethod();
    handlerDictionary[SomeOtherProperty] = (o,e) => SomeOtherMethod();
}

private static void CommonPropertyChanged(DependencyObject sender, DependencyPropertyChangedEventArgs args)
{
    var uie = sender as UIElement;
    if (uie != null)
    {
        //removing before possibly adding makes sure the multicast delegate only has 1 instance of this delegate
        sender.MouseDown -= handlerDictionary[args.Property];
        if (args.NewValue != null)
        {
            sender.MouseDown += handlerDictionary[args.Property];
        }
    }
}

或者只需在switch上执行args.Property即可。或介于两者之间的内容涉及基于DependencyProperty的常用方法和分支。

我不确定为什么您的IsEnabled属性会处理DependencyProperty类型的值,而不是像bool那样具有更多语义意义的内容。