Tech Tock

Time is of the essence.

No x:Type, No Problem

I had an interesting problem this week.  I needed to use a default template on a subclassed control.  Ordinarily, that would just be:

Style=”{StaticResource {x:Type BaseClass}}”

Of course in Silverlight, there is no x:Type.

The solution I used was to make an attached behavior that takes the class that has the style, finds the style in the resources and applies it.

The problem

Using a TextBox as an example, here’s some default styling that doesn’t get applied to the subclass:

    <UserControl.Resources>
        <StyleTargetType=“TextBox”>
            <SetterProperty=“Foreground”Value=“Red”/>
        </Style>
    </UserControl.Resources>
    <StackPanel>
        <TextBoxText=“Auto Styled”/>
        <local:TextBoxSubclass/>

It ends up looking like this:

image

The Solution

With an attached behavior, it can look like this (the bottom TextBoxSubclass has the default TextBox style applied):

    <StackPanel>image
        <TextBoxText=“Auto Styled”/>
        <local:TextBoxSubclass/>
        <local:TextBoxSubclass>
            <local:ApplyStyleBehavior.StyleTypeName>
                <TextBox/>
            </local:ApplyStyleBehavior.StyleTypeName>
        </local:TextBoxSubclass>
    </StackPanel>

The attached behavior is pretty simple:


        static void StyleTypeValueChanged(DependencyObject sender, DependencyPropertyChangedEventArgs e)
        {
            //need to be loaded so the visual tree can exist and be traversed
            (sender as FrameworkElement).Loaded += (sender1, args) =>
                {
                    (sender as Control).Style = (Style)FindResource(sender, e.NewValue.GetType());
               
                };
        }
        static objectFindResource(DependencyObject start, object resourceKey)
        {
            var nextUp = VisualTreeHelper.GetParent(start);
            while (nextUp != null)
            {
                var fe = nextUp as FrameworkElement;
                if (fe != null)
                {
                    var result = fe.Resources[resourceKey];
                    if (result != null)
                        return result;
                }
                nextUp = VisualTreeHelper.GetParent(nextUp);
            }
            return null;
       
        }

Conclusion

I think its exceedingly obvious how you could apply this universally as a default style on the subclass.  This looks like it has potential to be a pattern to compensate for other Silverlight omissions too.

You can download the full tiny demo on GitHub.

About these ads

November 28, 2011 - Posted by | Uncategorized |

No comments yet.

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s

Follow

Get every new post delivered to your Inbox.

%d bloggers like this: