views:

26

answers:

1

I've set up a custom control in SL and I'm trying to get the default look of the control to behave properly. I feel (with the help of some smart folks on here) that I am getting pretty close to getting this, but I'm still not quite there yet.

When my control is first added to a panel in Blend, it shows up as I expect based on the template, and when I modify the dependency properties I've exposed, those work fine as well. The problem I'm having now is that when make a change through Blend and then "reset" that value using the options box, it resets the property under the Miscellaneous pane, but doesn't actually change the control itself in the design view unless I build the project again.

Here's the code I currently have:

    public enum SolidGlossTypes
    {
        Normal,
        Header,
        Footer,
        None
    }

    public SolidGlossTypes SolidGlossType
    {
        get
        {
            return (SolidGlossTypes)GetValue(SolidGlossTypeProperty);
        }
        set
        {
            SetValue(SolidGlossTypeProperty, value);
            switch (value)
            {
                case SolidGlossTypes.Header:
                    SolidGloss_Upper.Visibility = Visibility.Visible;
                    SolidGloss_Lower.Visibility = Visibility.Collapsed;
                    break;
                case SolidGlossTypes.Footer:
                    SolidGloss_Upper.Visibility = Visibility.Collapsed;
                    SolidGloss_Lower.Visibility = Visibility.Visible;
                    break;
                case SolidGlossTypes.None:
                    SolidGloss_Upper.Visibility = Visibility.Collapsed;
                    SolidGloss_Lower.Visibility = Visibility.Collapsed;
                    break;
                default:
                    SolidGloss_Upper.Visibility = Visibility.Visible;
                    SolidGloss_Lower.Visibility = Visibility.Visible;
                    break;
            }
        }
    }

    public static readonly DependencyProperty SolidGlossTypeProperty = DependencyProperty.Register("SolidGlossType", typeof(SolidGlossTypes), typeof(SolidGloss), new PropertyMetadata(SolidGlossTypes.Normal));

I've tried tinkering with a property changed callback but haven't had any success getting it to work.

Also, is it possible to set the default values of a dependency property to a style within generic.xaml and then bind to that from the template?

Thanks in advance,

E

+1  A: 

The problem is you've placed additional code in your Setter. When using Dependency properties the setter is not always called, for example when some other external code calls SetValue passing in SolidGlossTypeProperty and a new value, your setter is not called.

You sould use the property callback method to perform additional operations instead.

Edit

For example:-

public SolidGlossTypes SolidGlossType 
{ 
    get 
    { 
        return (SolidGlossTypes)GetValue(SolidGlossTypeProperty); 
    } 
    set 
    { 
        SetValue(SolidGlossTypeProperty, value);  
    } 
} 

public static readonly DependencyProperty SolidGlossTypeProperty = DependencyProperty.Register(
    "SolidGlossType",
    typeof(SolidGlossTypes),
    typeof(SolidGloss),
    new PropertyMetadata(SolidGlossTypes.Normal, OnSolidGlossTypePropertyChanged)); 


private static void OnSolidGlossTypePropertyChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
{
        SolidGloss source = d as SolidGloss;
        SolidGlossTypes value = (SolidGlossTypes)e.NewValue

        switch (value) 
        { 
            case SolidGlossTypes.Header: 
                source.SolidGloss_Upper.Visibility = Visibility.Visible; 
                source.SolidGloss_Lower.Visibility = Visibility.Collapsed; 
                break; 
            case SolidGlossTypes.Footer: 
                source.SolidGloss_Upper.Visibility = Visibility.Collapsed; 
                source.SolidGloss_Lower.Visibility = Visibility.Visible; 
                break; 
            case SolidGlossTypes.None: 
                source.SolidGloss_Upper.Visibility = Visibility.Collapsed; 
                source.SolidGloss_Lower.Visibility = Visibility.Collapsed; 
                break; 
            default: 
                source.SolidGloss_Upper.Visibility = Visibility.Visible; 
                source.SolidGloss_Lower.Visibility = Visibility.Visible; 
                break; 
        }
}

In this arrangement whenever the value of SolidGlossTypeProperty is changed by whatever means (the setter in your code, by animation or by other direct calls to SetValue) the callback property changed method will always be called.

AnthonyWJones
+1, also, you might want to consider making the enum a first class object and putting the associated values on that rather than in your set method
Alex Lo
Okay, I am lost as to how to use the property callback method (I can't figure out what to put in the switch statement instead of 'value'.
Eric
Alex: I don't understand what you mean.
Eric
@Eric: see my edit.
AnthonyWJones