0

I have a user control with a dependency property and i am using this control in a wpf window. When i change from the window view model the value of a property that is put as binding to that dependency property, i expect the callback method for that dependency property to be invoked, but nothing happens.

MainWindow.xaml

 <test:TestView Grid.Column="0" TestString="{Binding TestString, Mode=TwoWay}"></test:TestView>

MainWindow.xaml.cs

public MainWindow()
    {
        InitializeComponent();

        this.DataContext = new MainWindowViewModel();
    }

MainWindowViewModel.cs

 private string _testString;

    public string TestString
    {
        get { return _testString; }
        set
        {
            if (_testString!= value)
            {
                _testString= value;
                OnPropertyChanged();
            }
        }
    }

TestView.xaml.cs

public TestView()
    {
        InitializeComponent();
        this.DataContext = new TestViewModel();
    }

    public static readonly DependencyProperty TestStringProperty =
        DependencyProperty.Register("TestString", typeof(string), typeof(TestView), new PropertyMetadata(null, OnTestStringPropertyChanged));
    public string TestString
    {
        get { return (string)GetValue(TestStringProperty); }
        set
        {
            SetValue(TestStringProperty, value);
        }
    }

    private static void OnTestStringPropertyChanged(DependencyObject source,
    DependencyPropertyChangedEventArgs e)
    {
        TestView control = source as TestView;
        string time = (string)e.NewValue;
        // Put some update logic here...
        ((TestViewModel) control.DataContext).Merge();
    }

BaseViewModel.cs (I extend it in every ViewModel)

public class BaseViewModel : INotifyPropertyChanged
{
    public event PropertyChangedEventHandler PropertyChanged;

    [NotifyPropertyChangedInvocator]
    protected virtual void OnPropertyChanged([CallerMemberName] string propertyName = null)
    {
        PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
    }
}

What did i do wrong here or why my callback is never invoked?

XamWaZZ
  • 59
  • 2
  • 12
  • Can we see how you implemented `INotifyPropertyChanged` ? – scharette Jul 19 '18 at 12:13
  • 2
    Remove `this.DataContext = new TestViewModel();` from the UserControl's constructor. It breaks any DataContext-based Binding like `TestString="{Binding TestString, Mode=TwoWay}"`. A UserControl should never explicitly set its own DataContext. – Clemens Jul 19 '18 at 12:14
  • @scharette I edited the question and now you can see also the implementation if INotifyPropertyChanged – XamWaZZ Jul 19 '18 at 12:17
  • @Clemens, Yes, that was the problem. But where should i set this DataContext then? As i know there are 2 ways of working with user controls. The one that i used is to handle the View so in this case i understand that the View should create its own ViewModel. Am i wrong? – XamWaZZ Jul 19 '18 at 12:19
  • 1
    As said, a UserControl should *never* explicitly set its own DataContext. Neither to itself, nor some "private" view model. It should only expose dependency properties that are bound to properties of an externally supplied view model, i.e. one that is provided by the value inheritance of the DataContext property of the UserControl's parent element, e.g. a MainWindow. – Clemens Jul 19 '18 at 12:22
  • Ok, and if i have some logic for that user control i should implement it in the UserControl.xaml.cs? – XamWaZZ Jul 19 '18 at 13:07
  • 1
    That's exactly what you should do. – Clemens Jul 19 '18 at 13:32

0 Answers0