Свойство зависимости - обновление источника - PullRequest
8 голосов
/ 01 сентября 2011

Я схожу с ума с пользовательским свойством зависимости.Я уже проверил множество потоков здесь, но пока не нашел решения.То, что я хочу сделать, это заменить значение свойства, если источник предоставляет конкретное значение (ноль для данного примера).Что бы я ни пытался, значение свойства в источнике остается нулевым и никогда не обновляется.

Вот мой пользовательский элемент управления:

public class TextBoxEx : TextBox
{
    public TextBoxEx()
    {
        TrueValue = 0;
        this.TextChanged += (s, e) =>
        {
            TrueValue = Text.Length;
            SetCurrentValue(MyPropertyProperty, TrueValue);
            var x = BindingOperations.GetBindingExpression(this, MyPropertyProperty);
            if (x != null)
            {
                x.UpdateSource();
            }
        };
    }

    public int? TrueValue { get; set; }

    public int? MyProperty
    {
        get { return (int?)GetValue(MyPropertyProperty); }
        set { SetValue(MyPropertyProperty, value); }
    }

    public static readonly DependencyProperty MyPropertyProperty =
        DependencyProperty.Register("MyProperty", typeof(int?), typeof(TextBoxEx), new PropertyMetadata(null, PropertyChangedCallback));

    private static void PropertyChangedCallback(DependencyObject d, DependencyPropertyChangedEventArgs e)
    {
        if (e.NewValue == null)
        {
            d.SetCurrentValue(MyPropertyProperty, (d as TextBoxEx).TrueValue);
        }
    }
}

Вот DataContext, который я связываю:

public class VM : INotifyPropertyChanged
{
    private int? _Bar = null;

    public int? Bar
    {
        get { return _Bar; }
        set
        {
            _Bar = value;
            OnPropertyChanged("Bar");
        }
    }

    public event PropertyChangedEventHandler PropertyChanged;

    protected void OnPropertyChanged(string propertyName)
    {
        if (PropertyChanged != null)
        {
            PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
        }
    }
}

Моя привязка выглядит следующим образом:

<local:TextBoxEx MyProperty="{Binding Bar, UpdateSourceTrigger=PropertyChanged}"/>

Помните: мне нужна привязка TwoWay, поэтому OneWayToSource у меня не работает.

Любая идея, чем я не являюсьздесь?

Ответы [ 2 ]

7 голосов
/ 01 сентября 2011

Вам просто нужно установить двухстороннюю привязку, и она будет работать.Но так как это должно быть по умолчанию, вы можете зарегистрировать свойство соответствующим образом, используя следующие метаданные:

... new FrameworkPropertyMetadata(null,
                                  FrameworkPropertyMetadataOptions.BindsTwoWayByDefault,
                                  PropertyChangedCallback)

Получение выражения в обработчике TextChanged и обновление источника вручную не требуется, поэтому я бы удалил этот код.


Если вы явно не установите режим для привязки, будет использоваться значение по умолчанию, из документации :

По умолчанию: Использует значение по умолчанию Mode значение цели привязки.Значение по умолчанию варьируется для каждого свойства зависимости.В общем случае редактируемые пользователем свойства элемента управления, такие как свойства текстовых полей и флажков, по умолчанию имеют двустороннюю привязку, в то время как большинство других свойств по умолчанию используют одностороннюю привязку.Программный способ определить, является ли свойство зависимости односторонним или двусторонним по умолчанию, состоит в том, чтобы получить метаданные свойства для свойства с помощью GetMetadata , а затем проверить логическое значение BindsTwoWayByDefault собственность.

0 голосов
/ 01 сентября 2011

Как вы писали: «Помните: мне нужен двухсторонний переплет», поэтому:

<local:TextBoxEx MyProperty="{Binding Bar, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"/>
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...