Sunday, September 18, 2011

NGTweet Part 13–Implicit Styles in Silverlight

In Part 12 of NGTweet learning series, I showed the use of Styles in Silverlight. The approach we used in applying style was to assign an identifier by means of a key and associate that key with the Style attribute of the control. This is an explicit way of styling the Silverlight controls. This approach works well when we have various combinations of visual styles that can be applied to a particular control. In this post I am going to demonstrate another mode of applying styles in Silverlight which is called Implicit Styling.

Need for implicit styling

Imagine a scenario where you want the same style applied to all instances of a control across the whole application. If we use the explicit styling approach, we’ll end up assigning the Style key for each instance of the control. This is bit tedious.  Also if you happen to change the name of the style from “ABC” to “XYZ”,, you’ll have to replace all those instances. It would be nice to specify the style for the control and let it be applied automatically in all places where the control is used. This is exactly what this post is all about (as you might have guessed from the title itself Smile).

How to apply implicit Styles

Many of the steps for implementing implicit style are similar to that of the explicit style. To get the right context lets look for a place where we can apply the implicit style within NGTweet application.

border with explicit style

If you observe carefully, I have added a white border around all the 3 column headings. This border has the same settings for all the three headings i.e. All Friends, Mentions and Compose. The markup applied to all 3 borders is as shown below

                <Border Margin="2"
                       Padding="3"
                       BorderBrush="White"
                       BorderThickness="1"
                       CornerRadius="5"
>

You can imagine what problem we’ll face if we have to change any of the setting like the border thickness from 1 to 2. We’ll have to change it in 3 places and may be even more if we add more columns later on to this application. So we refactor this piece of code to use the implicit style feature available in Silverlight.


Create a style for Targeted control


First step is to define a style in the common place. We had done a similar thing in the earlier post as well. We’ll use the same resource dictionary from the earlier posts. You could add this style to the ApplicationResorces dictionary if you don’t want to create a separate resource dictionary file.

    <Style TargetType="Border">
        <Setter Property="Margin"
               Value="2" />
        <Setter Property="Padding"
               Value="3" />
        <Setter Property="BorderBrush"
               Value="White" />
        <Setter Property="CornerRadius"
               Value="5" />
        <Setter Property="BorderThickness"
               Value="1" />
    </Style
>

Note that we have specified the TargetType as Border. We have not specified any Key here. This is very important. This results in the behaviour that we are trying to use. By not specifying any key we are instructing the parser to apply this style to all Border elements.


Merge Resource Dictionary with Application Resources


This step is similar to what we had done previously. If you are not aware, you can refer to the earlier post.


Remove inline styles


And finally we remove the inline style applied to border elements. So our final markup is

                <Border>
                    <TextBox Style="{StaticResource ReadOnlyHeaderTextBox}"
                            Text="Mentions" />
                </Border
>

You can see that we have specified only the Border element in the markup. The styles are applied implicitly to the Border element. It is very easy to override the properties defined in the implicit style for specific instances.


Style Gotcha’s


There are couple of Gotchas I came across while working on this post.


Gotcha 1 :


If you look at the code available in the attachment towards the end, you’ll find implicit style applied to border element for the column header’s borders. Also the border that appears for each Tweet within the list box has similar settings but is applied using explicit style. This is a gotcha in the Silverlight 4 as well as 5 versions. We cannot apply implicit styles for items within a data template. There is a work around which we have already implemented by means of explicit style. Hopefully this would be rectified in the future release of Silverlight.


Gotcha 2 :


I have been using the Expression Blend Dark Theme from Silverlight toolkit. This toolkit provides styles for many of the controls in Silverlight. All these Styles are implemented as implicit Styles. As a result we cannot create styles within the application which will extend the implicit styles easily. We can use explicit styles, but those will negate the styling of Expression Blend Dark theme. This is the reason the Listbox control has inline styles in some places.


Conclusion


As we saw in this post, it is very easy to apply styles across the application to visual elements using implicit styles. I haven’t tried it myself, but I came across some reading which suggested that WPF supports extending the implicit styles. As of now this feature is not available in Silverlight. Like with UpdateSourceTrigger for PropertyChanged, we can hope that the gap between WPF and Silverlight would be narrowed very soon.


As always the complete working solution is available for download at Dropbox.


Until next time Happy Programming Smile

No comments:

Post a Comment