Search code examples
c#wpfmvvmcaliburn

Caliburn - PropertyChanged for child ViewModel


I'm using Caliburn and the MVVM pattern in a WPF application, and am trying to use as many conventions as possible. One issue I'm running into is when I have to wire-up some property-changed notifications on an imported class.

Say I have a ViewModel like so:

class ViewModelA
{
    private readonly IViewModelB _b;

    public ViewModelA(IViewModelB b)
    {
        _b = b;
    }

    public bool CanGo
    {
        get { return _b.MyBoolProperty; }
    }

    public void Go()
    {
        //Does something here
    }
}

What is the recommended (correct) way to call NotifyOfPropertyChange(() => CanGo) when the PropertyChanged event for MyBoolProperty is fired off ViewModelB?

In the past I've used a PropertyObserver type class to manage this.

Or am I designing this scenario completely wrong?


Solution

  • If your "sub"-model is exposed with a public property, you could use DependenciesAttribute to track changes:

     
    class ViewModelA
    {
        public IViewModelB B {get; private set;}
    
        public ViewModelA(IViewModelB b)
        {
            B = b;
        }
    
        public bool CanGo
        {
            get { return B.MyBoolProperty; }
        }
    
        [Dependencies("B.MyBoolProperty")]
        public void Go()
        {
            //Does something here
        }
    }
    

    To work properly, the whole property path should be composed of notifying objects. You can also put a final "*"

    [Dependencies("B.*")]
    

    to indicate that all properties of B should cause the precondition re-evaluation; note that "*" only acts on the end of the proprerty path and just for one level of depth (it doesn't track changes on sub-models of B).