存储bindingexpression供以后使用

时间:2015-09-02 06:40:24

标签: c# wpf binding

我有一个使用IsEnabled绑定的应用程序。 我还需要在短时间内删除此绑定。

我创建了一个带有附加属性的ControlBehavior,用作临时存储空间。 ClearIsEnabledBinding将设置此附加属性中使用的绑定。 RestoreIsEnabeldBinding应该将绑定返回到原始位置。这不起作用。清除绑定后,附加属性也会被清除。

场景是这样的。我有一个文本框,带有IsEnabled的绑定到带有转换器的viewmodel。当我使用特定函数时,无论viewmodel中的值如何,所有IsEnabled都应为true。这很容易删除绑定并设置为true。但是当我从这个函数返回时,我需要恢复绑定到它与转换器的viewmodel的原始绑定。所以我需要在某个地方保存整个bindingexpression,然后" put"它回来了

我的课程如下:

对我做错的任何建议?

public partial class ControlBehavior
{
    public static readonly DependencyProperty IsEnabledBindingProperty = DependencyProperty.RegisterAttached(
         "IsEnabledBinding",
         typeof(BindingExpression),
         typeof(ControlBehavior),
         new PropertyMetadata(null));

    public static void SetIsEnabledBinding(DependencyObject element, BindingExpression value)
    {
        if (value != null)
        {
            element.SetValue(IsEnabledBindingProperty, value);
            SetIsEnabledBindingSet(element, true);
        }
    }

    public static BindingExpression GetIsEnabledBinding(DependencyObject element)
    {
        var obj = element.GetValue(IsEnabledBindingProperty);
        return (BindingExpression) obj;
    }

    public static readonly DependencyProperty IsEnabledBindingSetProperty = DependencyProperty.RegisterAttached(
        "IsEnabledBindingSet",
        typeof(bool),
        typeof(ControlBehavior),
        new PropertyMetadata(false));

    public static void SetIsEnabledBindingSet(DependencyObject element, bool value)
    {
        element.SetValue(IsEnabledBindingSetProperty, value);
    }

    public static bool GetIsEnabledBindingSet(DependencyObject element)
    {
        return (bool)element.GetValue(IsEnabledBindingSetProperty);
    }


    public static void ClearIsEnabledBinding(DependencyObject element)
    {
        SetIsEnabledBinding(element, ((Control)element).GetBindingExpression(UIElement.IsEnabledProperty));
        ((Control)element).SetBinding(UIElement.IsEnabledProperty, new Binding());
    }

    public static void RestoreIsEnabledBinding(DependencyObject element)
    {
        if (!GetIsEnabledBindingSet(element))
        {
            return;
        }
        ((Control)element).SetBinding(UIElement.IsEnabledProperty, GetIsEnabledBinding(element).ParentBindingBase);
    }
}

2 个答案:

答案 0 :(得分:0)

  

这种情况是这样的。我有一个文本框,带有IsEnabled的绑定到带有转换器的viewmodel。当我使用特定函数时,无论viewmodel中的值如何,所有IsEnabled都应为true。这很容易删除绑定并设置为true。但是当我从这个函数返回时,我需要恢复绑定到它与转换器的viewmodel的原始绑定

您可以暂时提供覆盖 IsEnabled值的机制,而不是处理绑定。我假设2个:1)你绑定某些东西(让我们称之为IsEnabled)2)你正在制作某种编辑模式,它应该暂时覆盖绑定值:

bool _isEditMode;
public bool IsEditMode
{
    get { return _isEditMode; }
    set
    {
        _isEditMode = value;
        OnPropertyChanged(nameof(IsEnabled)); // update IsEnabled when IsEditMode changed
    }
}

bool _isEnabled;
public bool IsEnabled
{
    get
    {
        return IsEditMode || _isEnabled; // return true if IsEditMode == true or actual value otherwise
    }
    set
    {
        _isEnabled = value;
        OnPropertyChanged();
    }
}

现在如果你绑定

<TextBox IsEnable="{Binding IsEnabled, Converter= ...}" ... />

然后,只要您设置IsEditMode = true,文本框就会启用。如果设置IsEditMode = false,则会再次启用或禁用文本框,具体取决于IsEnabled viewmodel属性的值。

答案 1 :(得分:0)

我们使用以下课程来做我认为你想要实现的目标:

/// <summary>
/// Utilities to be used with common data binding issues
/// </summary>
class DataBindingUtils

{

    private static readonly DependencyProperty DummyProperty = DependencyProperty.RegisterAttached(

          "Dummy",

          typeof(Object),

          typeof(DependencyObject),

          new UIPropertyMetadata(null));



    /// <summary>
    /// Get a binding expression source value (using the PropertyPath), from MSDN forums:
    /// "Yes, there is one (class to provide the value) inside WPF stack, but it's an internal class"
    /// Get source value of the expression by creating new expression with the same
    /// source and Path, attaching this expression to attached property of type object
    /// and finally getting the value of the attached property
    /// </summary>
    /// <param name="expression"></param>
    /// <returns></returns>
    public static Object Eval(BindingExpression expression)

    {

        // The path might be null in case of expression such as: MyProperty={Binding} - in such case the value we'll get

        // will be the DataContext

        string path = null;

        if (expression.ParentBinding != null && expression.ParentBinding.Path != null)

        {

            path = expression.ParentBinding.Path.Path;

        }



        Binding binding = new Binding(path);

        binding.Source = expression.DataItem;

        DependencyObject dummyDO = new DependencyObject();

        BindingOperations.SetBinding(dummyDO, DummyProperty, binding);

        object bindingSource = dummyDO.GetValue(DummyProperty);

        BindingOperations.ClearBinding(dummyDO, DummyProperty);

        return bindingSource;

    }

}