none
Dependency Property Value Changed does not fire when setting to same value

    Question

  • The situation: I have a custom user control which is used as a location picker, and it has two dependency properties: LocationType and LocationID.  Location Type specifies the type of location (e.g. company, region, district, or store) and LocationID specifies the specific location (according to the LocationType).  I have Value (i.e. Validation) Changed events set up on the two dependency properties (as shown in this article ), and every time the value changes on either of them, I record their previous value in the respective variables PreviousLocationType and PreviousLocationID.  If a user picks a location that they don't have security access for, I revert the selected location back to the previous value.

    The problem: The Value Changed event only fires if the value is actually changed; if it gets set to the same value then the event doesn't fire.  So my picker's PreviousLocationType/ID values are not always correct.  For example:

    Set Type/ID to 1/1 => Previous Type/ID gets set to -1/-1 (the default values)

    Set Type/ID to 2/2 => Previous Type/ID gets set to 1/1

    Set Type/ID to 2/3 => Previous Type stays at 1 (since Type was already set to 2 and the ValueChanged event didn't fire) and Previous ID get set to 2

    So then if the user chooses a location they don't have access to, the selection gets reverted back to 1/2 instead of 2/2.

    So is there any way to fire an event on a dependency property every time its value gets set, regardless of its current value?

     

    Actually, while writing this I came up with a solution to my specific problem; create a structure that holds both a Type and ID, so then if either of them changes the value of the structure will have changed, and the ValueChanged event will fire.  I am still interested to know if there is an event that fires *everytime* a dependency property is set though.  Thanks in advance!


    - Dan - "Can't never could do anything"
    Friday, December 03, 2010 1:29 AM

Answers

  • Hello,

    I ran into the same problem with some controls. You can register a CoerceValueCallBack function. Something like this:

     

    public static readonly DependencyProperty ExampleProperty = DependencyProperty.Register("Example", typeof(bool), typeof(SomeControl), new PropertyMetadata(false, null, ExampleCoerceValueCallBack));
    
    private static object ExampleCoerceValueCallBack(DependencyObject d, object value)
    {
    
     }
    

     

    This works, it is always triggered when the value of a property changes. Even if the value is equal. I'am not sure if this is the correct solution.

    • Marked as answer by deadlydog Monday, December 06, 2010 9:24 PM
    Sunday, December 05, 2010 2:58 PM
  • Yup, I tried using the CoerceValueCallBack instead of ValueChanged and it worked.  That event fires everytime the value is set, not just when it changes.  Thanks. :)
    - Dan - "Can't never could do anything"
    • Marked as answer by deadlydog Monday, December 06, 2010 9:24 PM
    Monday, December 06, 2010 9:23 PM

All replies

  • Ok, so while my proposed solution ideally would work for my problem, it won't work in my case.  Simply because it would involve too much refactoring, as there are way too many places in our current solution that bind directly to the LocationType and LocationID.  I originally thought that I would just be able to have properties (not dependency properties) on my location picker still called LocationType and LocationID that would just get/set the new dependeny property's (called CurrentSelection) Type and ID, but in order for binding to work LocationType and LocationID have to be dependency properties, not just regular class properties, in which case I am back to the same original problem where the ValueChanged event doesn't fire if it they get set to the same value.

    So back to my original question, is there any event that fires every time a dependency property's value is set (i.e. whenever SetValue() is called on the dependency property)?


    - Dan - "Can't never could do anything"
    Saturday, December 04, 2010 9:27 PM
  • Hello,

    I ran into the same problem with some controls. You can register a CoerceValueCallBack function. Something like this:

     

    public static readonly DependencyProperty ExampleProperty = DependencyProperty.Register("Example", typeof(bool), typeof(SomeControl), new PropertyMetadata(false, null, ExampleCoerceValueCallBack));
    
    private static object ExampleCoerceValueCallBack(DependencyObject d, object value)
    {
    
     }
    

     

    This works, it is always triggered when the value of a property changes. Even if the value is equal. I'am not sure if this is the correct solution.

    • Marked as answer by deadlydog Monday, December 06, 2010 9:24 PM
    Sunday, December 05, 2010 2:58 PM
  • Ok, I never actually tried using the CoerceValueCallBack event because on the article I posted above it says, "Coerce value callbacks do pass the specific DependencyObject instance for properties, as do PropertyChangedCallback implementations that are invoked by the property system whenever the value of a dependency property changes .".  So I just assumed that they only fired at the same time as the ValidationCallback.  I'll give it a shot on Monday and mark your post as the answer if it works.  Thanks :)

    - Dan - "Can't never could do anything"
    Sunday, December 05, 2010 4:31 PM
  • Yup, I tried using the CoerceValueCallBack instead of ValueChanged and it worked.  That event fires everytime the value is set, not just when it changes.  Thanks. :)
    - Dan - "Can't never could do anything"
    • Marked as answer by deadlydog Monday, December 06, 2010 9:24 PM
    Monday, December 06, 2010 9:23 PM