views:

154

answers:

3

Hello,

I have a class with 3 dependency properties A,B,C. The values of these properties are set by the constructor and every time one of the properties A, B or C changes, the method recalculate() is called. Now during execution of the constructor these method is called 3 times, because the 3 properties A, B, C are changed. Hoewever this isn't necessary as the method recalculate() can't do anything really useful without all 3 properties set. So what's the best way for property change notification but circumventing this change notification in the constructor? I thought about adding the property changed notification in the constructor, but then each object of the DPChangeSample class would always add more and more change notifications. Thanks for any hint!

class DPChangeSample : DependencyObject
{                  
    public static DependencyProperty AProperty = DependencyProperty.Register("A", typeof(int), typeof(DPChangeSample), new PropertyMetadata(propertyChanged));
    public static DependencyProperty BProperty = DependencyProperty.Register("B", typeof(int), typeof(DPChangeSample), new PropertyMetadata(propertyChanged));
    public static DependencyProperty CProperty = DependencyProperty.Register("C", typeof(int), typeof(DPChangeSample), new PropertyMetadata(propertyChanged));


    private static void propertyChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
    {
        ((DPChangeSample)d).recalculate();
    }


    private void recalculate()
    {
        // Using A, B, C do some cpu intensive calculations
    }


    public DPChangeSample(int a, int b, int c)
    {
        SetValue(AProperty, a);
        SetValue(BProperty, b);
        SetValue(CProperty, c);
    }
}
+1  A: 

Use DependencyObject.SetValueBase. This bypasses any Metadata specified, so your propertyChanged won't be called. See msdn.

Femaref
thank you very much for your reply, this looks promising, but don't have this method in intellisense, only SetValue ? (Using VS 2010, . NET 4)
stefan.at.wpf
Hm, this seems to be in System.Workflow.DependencyObject. So probably the wrong direction :/ meh.
Femaref
A: 

Hi Stefan, you don't want to execute recalculate() unless all three properties are set, but in the it gets called from the constructor when setting a, b and c? is this correct?

if so, can you not just put a check in the recalculate near the top to check that all three properties are set and decide if you want to execute or not....

This will work because you mentions that

as the method recalculate() can't do anything really useful without all 3 properties set.

VoodooChild
thanks VoodooChild, this would indeed work, however I was wondeirng if there is a better solution / pattern for this. Femaref answer looks like the perfect solution, I just don't get it how to be able to use SetValueBase.
stefan.at.wpf
+1  A: 

Can you try this?

private bool SupressCalculation = false;
private void recalculate() 
{ 
    if(SupressCalculation)
        return;
    // Using A, B, C do some cpu intensive caluclations 
} 


public DPChangeSample(int a, int b, int c) 
{
    SupressCalculation = true; 
    SetValue(AProperty, a); 
    SetValue(BProperty, b); 
    SupressCalculation = false;
    SetValue(CProperty, c); 
} 
Akash Kava
Thank you very much, proved to be the best answer (together with VoodooChilds answer, I just accepted this one as it includes a code sample).
stefan.at.wpf