Working with Data in Expression Blend 4

Element to Element Data Binding

In this section we are going to see how we can use data binding in Expression Blend. We will see how we can create sample data sources and how to use them in data binding.

Data binding is a functionality that both Silverlight and WPF have that helps us set the property of an element to an external data source. That data source can be xml if we are using WPF and can be any CLR object if we are using Silverlight or WPF. It could also be a sample data source. When we apply data binding to an element then that element does not get its value directly but it has to go to some other location for getting its value. This other location can be another element or a database or an xml.

  • Let’s have a look at the element to element data binding. Open Expression blend 4 and create a new Silverlight Project.
  • Now go to the tools pallet and select rectangle.
Expression Blend 4 : Rectangle

Expression Blend 4 : Rectangle

  • Now create a rectangle by pressing the left button of the mouse and dragging it on the artboard.

 

Expression Blend 4 : Rectangle

Expression Blend 4 : Rectangle

  • Now go to the properties of the rectangle and set the horizontal alignment to stretch and left and right margins to 0.

 

Expression Blend 4 : Rectangle Properties

Expression Blend 4 : Rectangle Properties

  • Let’s go back to the tools pane and grab a slider and drop it on the artboard.

 

Expression Blend 4 : Slider

Expression Blend 4 : Slider

  • If you have a look at the properties of the slider you would see values like Maximum (The maximum value of the slider), Minimum (the minimum value of a slider), SmallChange (the value that will change when user has focused the slider and uses the up and down arrow key to change the value of the slider), LargeChange (the value that will change when do a mouse click at any location on the slider track). Let’s set these properties as shown below.

 

Expression Blend 4 : Slider Properties

Expression Blend 4 : Slider Properties

  • Now let’s setup the data binding. There are two ways to set the data binding: one way or two way. In one way data binding only one property can change the other but not vice versa. In two way data binding both the properties can change each other. In this case we want only one way binding so that the width of the rectangle can change on the change in the slider. So let’s select the rectangle and go to the width property and click on the property marker next to it.
Expression Blend 4 : Rectangle Property Marker

Expression Blend 4 : Rectangle Property Marker

 

  • And select element property binding.

 

Expression Blend 4 : Element Property Binding

Expression Blend 4 : Element Property Binding

  • Now our cursor has been moved to the object picker mode so we need to point to the element with which we want to do the property binding. In this case we will move our cursor to the slider and click on the slider.

 

Expression Blend 4 : Element Property Binding

Expression Blend 4 : Element Property Binding

  • Once we will click on the slider we will get an option select which property of the slider we want to bind to and we will select value.

 

Expression Blend 4 : Element Property Binding

Expression Blend 4 : Element Property Binding

  • The moment we do this we see that the width of the rectangle is changed and the Width property has a yellow rectangle around it showing that this property is getting its value from some other location.
Expression Blend 4 : Element Property Binding

Expression Blend 4 : Element Property Binding

 

  • Now we can run the application and see that the width of the rectangle will change as we change the slider value.

 

Expression Blend 4 : Element Property Binding

Expression Blend 4 : Element Property Binding

Two Way Data Binding

In this section we will see how we can create two way data binding. Along with the Slider we will provide a textbox to modify the width of the rectangle.

  • Let’s drag out a textbox on to the artboard.

 

Expression Blend 4 : Element Property Binding Two Way

Expression Blend 4 : Element Property Binding Two Way

  • Now go to the text property of the textbox and click on the property marker and select Element Property Binding.

 

Expression Blend 4 : Element Property Binding Two Way

Expression Blend 4 : Element Property Binding Two Way

  • Select the slider control again and select its value property again as we did in the case of the rectangle. Also we will select the TwoWay Binding so that both the controls i.e. TextBox and Slider can change each other’s value.

 

Expression Blend 4 : Element Property Binding Two Way

Expression Blend 4 : Element Property Binding Two Way

  • Now we can run the application and change the value of the slider or textbox and we will see that the width of the rectangle is changing and the other control’s value is also updated.

Data Binding with Data Sources

 

In this section we will see how we can use data binding with data sources. Data sources can either be xml or any other CLR object. As we know that xml works only with WPF so for this demo we will have to use data binding with sample data. When we work on an actual project we have CLR objects in which data is stored and they definitely follow some schema. So we can build up sample data in Blend to represent that sample data. So let’s get started.

  • Create a new project in Blend. Navigate to the data tab in the right panel. If the data tab is not visible then goto the window menu of blend and select data.
Expression Blend 4 : Data

Expression Blend 4 : Data

  • Click on the Create Data Source.

 

Expression Blend 4 : Create Data Source

Expression Blend 4 : Create Data Source

  • And select New Sample Data. You will also see option to create Sample data using XML or Class. If we have those then we can use them. When we select any of those two options then blend will not exactly use those but take them as a basis for generating sample data.

 

Expression Blend 4 : Add new Sample Data

Expression Blend 4 : Add new Sample Data

  • Give the Sample Data Source some name and select the define in as project. We do want to enable sample data when application is running so keep It checked.
Expression Blend 4 : Add new Sample Data

Expression Blend 4 : Add new Sample Data

 

  • When we click ok we will see that the data source appears in the data tab at project level and we have a collection with properties in it.

 

Expression Blend 4 : Sample Data

Expression Blend 4 : Sample Data

  • We can also see that in the Projects that a new folder is added named SampleData. When we expand it we see that there is a xaml in it which will store all the data and an xsd which is the schema.

 

Expression Blend 4 : Sample Data Folder

Expression Blend 4 : Sample Data Folder

  • If we open the MyAddresses.xaml, we will see that we have some items already added in the data source. We modify their values or add new items.
Expression Blend 4 : Sample Data xaml

Expression Blend 4 : Sample Data xaml

 

  • Let’s go back to the data tab and click on Edit Sample Values as shown in the image below.
Expression Blend 4 : Edit Sample Data

Expression Blend 4 : Edit Sample Data

 

  • We will see something like below. We can edit the values or the types of these properties.

 

Expression Blend 4 : Edit Sample Data

Expression Blend 4 : Edit Sample Data

  • Let’s rename the properties as shown below. Also lets change the specification of the Address property as shown below.
Expression Blend 4 : Edit Sample Data Property Type and Format

Expression Blend 4 : Edit Sample Data Property Type and Format

 

  • Also similarly change the Format of name to Name. When we do that if you go back to Edit Values we will see that the data is has been populated according to the format selected.

 

Expression Blend 4 : Edit Sample Values

Expression Blend 4 : Edit Sample Values

  • Let’s add email, phone number  and CustomColor properties.Also modify the format accordingly
Expression Blend 4 : Edit Sample Values Format

Expression Blend 4 : Edit Sample Values Format

 

  • And we will see data something like below.

 

Expression Blend 4 : Add Properties in Sample Values

Expression Blend 4 : Add Properties in Sample Values

  • Now let’s start using this data that we have created. Drag and drop the Collection onto the artboard.
Expression Blend 4 : Create Databound ListBox

Expression Blend 4 : Create Databound ListBox

 

 

  • And a listbox will be automatically created. And each entry will show all the fields. Also the yellow rectangle around the datasource shows data binding.

 

Expression Blend 4 : Create Databound ListBox

Expression Blend 4 : Create Databound ListBox

  • Let’s improve the look of the List Box by the use of Data Template. Right Click the ListBox and Go to Edit Additional Template à Edit Generated Items (ItemTemplate) à Edit Current

 

Expression Blend 4 : Edit Generated Items

Expression Blend 4 : Edit Generated Items

  • We would something like this. Let’s delete the Color textblock as we do not want to display the color in this way. When we delete that textblock you would see that that textblock is deleted from each item and that’s the way templates work.

 

Expression Blend 4 : ListBox DataTemplate

Expression Blend 4 : ListBox DataTemplate

  • Now let’s select the listbox from the breadcrumb bar and stretch it.
Expression Blend 4 : ListBox DataTemplate

Expression Blend 4 : ListBox DataTemplate

 

  • Now let’s go back to the template and change the  orientation of the stackpanel to horizontal from vertical. And then build the solution. We will see something like below.

 

Expression Blend 4 : StackPanel Orientation

Expression Blend 4 : StackPanel Orientation

  • Lets give specific width to all the textblocks and we will see a clean layout.
Expression Blend 4 : StackPanel Orientation

Expression Blend 4 : StackPanel Orientation

 

  • Let’s delete all the textblocks except the Name TextBlock. Then let’s go back and select the listbox and reduce its width.

 

Expression Blend 4 : DataContext

Expression Blend 4 : DataContext

  • Now go to the data tab and select the view mode to details view.

 

Expression Blend 4 : DataContext

Expression Blend 4 : DataContext

  • Now let’s drag the Name field on to the art board. We will see that a grid is created along with textblock as its child. Now whenever we select the item in the listbox we will see that the content of the textblock in the grid is changing. This happens because the grid that got created has a concept called Data Context. The grid has its data context set to the list box. So as soon as an item is selected in listbox then the the value changes in the grid as the items in the grid have already specified what item of the listbox they want to display. We can other fields as well in the grid and see that their value change as the selection of the listbox changed.

 

Expression Blend 4 : DataContext

Expression Blend 4 : DataContext

  • When we run the application we will see something like below.

 

Expression Blend 4 : Run App with Sample Data

Expression Blend 4 : Run App with Sample Data

  • Lets go to the grid à Background à Property marker à Data Binding. We will a window like below.

 

Expression Blend 4 : Data Binding Background

Expression Blend 4 : Data Binding Background

  • Select Customcolor string and the background of the grid is bound to the color string of the selected item. The value conversion is going on in the background.

 

Expression Blend 4 : Data Binding Background

Expression Blend 4 : Data Binding Background

  • When we run the application we see something like below.

 

Expression Blend 4 : Data Binding Background

Expression Blend 4 : Data Binding Background

The code for this post can be found here.

 

Any questions, comments or feedback are welcome.

 

Microsoft has been offering data binding for all its user interface applications but it was an assumption that all the data binding that will happen will always be related to database. However WPF and Silverlight have a broader view assuming that the client side code is often not connected directly to the database. And Silverlight goes a step further by not providing the ADO.NET classes to connect to the database directly. This makes sense because Silverlight is used to design web pages and most organizations do not want to put their database onto the internet for obvious security reasons. So the way data comes into a Silverlight application is in the form of objects or xml. So the data biding framework in Silverlight focuses on objects. So the purpose of data binding is to connect the features of UI to the properties of the objects. Databinding can be used with nearly any property of any element.

Binding Expressions

To bind the property of a user interface element we use the binding markup extension. As you can see in below markup extensions are specified in the curly braces which are evaluated at runtime.

<TextBox Height=”23″ HorizontalAlignment=”Right” Margin=”0,95,22,0″

Name=”textBox2″ VerticalAlignment=”Top” Width=”240″

Text=”{Binding Path=Surname}”/>

 

So this markup binding extension binds the path property of the TextBox to property named Surname and the value of this TextBox text property is evaluated at runtime. Data binding will always connects 2 properties: the target property (generally the user interface property) and the source property (a dependency

Data Context

Now as we saw in the last section that we need to provide the data binding along with the source and target property. So if want to bind multiple targets then we do not need to write the source individually for each of the target property as multiple targets can use the same source for data binding. Let’s have a look at this with an example.

Let’s create a Person class in you user interface with the following Fields as shown below.

namespace DataBindingInSL

{

public class Person

{

public string GivenName { get; set; }

public string Surname { get; set; }

public double Age { get; set; }

}

}

 

Now we want to bind these properties in the User Interface. So lets add the following code in the code behind file of the view.

namespace DataBindingInSL

{

public partial class MainPage : UserControl

{

Person src = new Person { GivenName = “Max”, Surname = “Smith”, Age = 34 };

 

public MainPage()

{

InitializeComponent();

 

this.DataContext = src;

}

}

}

 

Now we are setting the DataContext of the User Interface as src.  By setting the DataContext property at the root element we have made the properties available at the all the elements in the tree as the DataContext in Silverlight cascades down the tree.  We could also set the datacontext on any panel as well and in that case the datacontext will apply only to the panel and its children. Once we have set this DataContext, it becomes the implicit source for all the user Interface elements. So in the View all we need to do is the property name in the binding path and the element will pick up the property from the source i.e. Data Context. Add the following code to the xaml of you SL app.

<Grid x:Name=”LayoutRoot” Background=”White”>

<sdk:Label Height=”23″ HorizontalAlignment=”Left” Margin=”12,38,0,0″ Name=”label1″ VerticalAlignment=”Top” Width=”120″ Content=”Name” />

<TextBox Height=”23″ HorizontalAlignment=”Right” Margin=”0,38,22,0″

Name=”textBox1″ VerticalAlignment=”Top” Width=”240″

Text=”{Binding Path=GivenName}” />

<sdk:Label Height=”23″ HorizontalAlignment=”Left” Margin=”12,95,0,0″ Name=”label2″ VerticalAlignment=”Top” Width=”120″ Content=”Last Name” />

<TextBox Height=”23″ HorizontalAlignment=”Right” Margin=”0,95,22,0″

Name=”textBox2″ VerticalAlignment=”Top” Width=”240″

Text=”{Binding Path=Surname}”/>

<sdk:Label Height=”23″ HorizontalAlignment=”Left” Margin=”12,153,0,0″ Name=”label3″ VerticalAlignment=”Top” Width=”120″ Content=”Age” />

<TextBox Height=”23″ HorizontalAlignment=”Right” Margin=”0,153,22,0″

Name=”textBox3″ VerticalAlignment=”Top” Width=”240″

Text=”{Binding Path=Age}”/>

</Grid>

 

When you run the application you would see that all the TextBox will display the values that are picked up from the bindings.

Data Context Silverlight 4

Data Context Silverlight 4

Right now the data is flowing in only one direction i.e. from src to the User Interface. If we want the data to flow in both the directions then we need to specify the mode as TwoWay in the Binding as shown below:

Text=”{Binding Path=Age, Mode=TwoWay}”

 

Binding Updates

As we saw in the last section that the User interface is updated with the values that are set in source at load time but when the values are updated at a later point in time then also the data binding model of Silverlight can reflect the in the source to the user interface when the data source raises change notification. The change notification can be raised after implementing the INotifyPropertyChanged.

So let’s implement the INotifyPropertyChanged interface in the data source so that whenever the source changes the User Interface is updated along with it as well. This interface has only one event which is raised whenever a property changes in the class. So change the code of the Person class as below along with the implementation of INotifyPropertyChanged.

public class Person : INotifyPropertyChanged

{

public string GivenName { get; set; }

public string Surname { get; set; }

private double _age;

 

public double Age

{

get { return _age; }

set

{

if (value != _age)

{

_age = value;

OnPropertyChanged(“Age”);

}

}

}

 

public event PropertyChangedEventHandler PropertyChanged;

 

private void OnPropertyChanged(string propertyName)

{

if (PropertyChanged != null)

{

PropertyChanged(this, new PropertyChangedEventArgs(propertyName));

}

}

}

 

Here after the implementation of INotifyPropetyChanged we change the code inside the set method of the Age property to call the OnPropertyChanged method which in turn raises the property changed event. So now when the Age property is changed the change will reflect in the User Interface as well. Change the code of the cs and xaml file to as shown below and you will be able to see the update in the property.

 

Silverlight 4 Binding Updates

Silverlight 4 Binding Updates

Data Template

We have seen the example of an adhoc binding in the previous section but Silverlight has a more structured way of defining the same using Data Template. A Data Template is similar to a Control Template. Just as the control Template determines how the Control should like, in a similar way a Data Template determines how the particular data would look like. Data Templates can be used by ItemsControls (ListBox, etc) and ContentControl (Buttons, etc). A Data Template will work at any place where a Content Model is in place.

Whenever there are custom properties in a class then it’s a good idea to define a Data Template in xaml so that the control knows how to display those types.  Let’s see this working in code.

<UserControl.Resources>

<DataTemplate x:Key=”dataTemplateBinding” >

<Grid>

<sdk:Label Height=”23″ HorizontalAlignment=”Left” Margin=”12,38,0,0″

Name=”label1″ VerticalAlignment=”Top” Width=”120″ Content=”Name” />

<sdk:Label Height=”23″ HorizontalAlignment=”Left” Margin=”12,95,0,0″

Name=”label2″ VerticalAlignment=”Top” Width=”120″ Content=”Last Name” />

<sdk:Label Height=”23″ HorizontalAlignment=”Left” Margin=”12,153,0,0″

Name=”label3″ VerticalAlignment=”Top” Width=”120″ Content=”Age” />

<TextBox Height=”23″ HorizontalAlignment=”Right” Margin=”0,38,22,0″

Name=”textBox1″ VerticalAlignment=”Top” Width=”240″

Text=”{Binding Path=GivenName, Mode=TwoWay}” />

<TextBox Height=”23″ HorizontalAlignment=”Right” Margin=”0,95,22,0″

Name=”textBox2″ VerticalAlignment=”Top” Width=”240″

Text=”{Binding Path=Surname, Mode=TwoWay}”/>

<TextBox Height=”23″ HorizontalAlignment=”Right” Margin=”0,153,22,0″

Name=”textBox3″ VerticalAlignment=”Top” Width=”240″

Text=”{Binding Path=Age, Mode=TwoWay}”/>

</Grid>

</DataTemplate>

</UserControl.Resources>

<Grid x:Name=”LayoutRoot” Background=”White”>

<ContentControl Content=”{Binding}”

ContentTemplate=”{StaticResource dataTemplateBinding}” />

<Button Content=”Older” Height=”23″ HorizontalAlignment=”Left” Margin=”43,242,0,0″

Name=”button1″ VerticalAlignment=”Top” Width=”75″ Click=”button1_Click” />

</Grid>

</UserControl>

Binding to Collections

Instead of binding to one instance we can bind a control to a collection. Let’s modify the MainPage as below to create a collection of Person.

public partial class MainPage : UserControl

{

Person src = new Person { GivenName = “Max”, Surname = “Smith”, Age = 34 };

List<Person> people = new List<Person>();

 

public MainPage()

{

InitializeComponent();

 

people.Add(src);

people.Add(new Person { GivenName = “Steve”, Surname=”Gaylon”, Age=44};

people.Add(new Person { GivenName = “John”, Surname=”Miller”, Age=14};

 

this.DataContext = people;

}

 

private void button1_Click(object sender, RoutedEventArgs e)

{

src.Age += 1;

}

}

 

Let’s change the xaml as below:

<UserControl.Resources>

<DataTemplate x:Key=”dataTemplateBinding” >

<Grid>

<sdk:Label Height=”23″ HorizontalAlignment=”Left” Margin=”12,38,0,0″

Name=”label1″ VerticalAlignment=”Top” Width=”120″ Content=”Name” />

<sdk:Label Height=”23″ HorizontalAlignment=”Left” Margin=”12,95,0,0″

Name=”label2″ VerticalAlignment=”Top” Width=”120″ Content=”Last Name” />

<sdk:Label Height=”23″ HorizontalAlignment=”Left” Margin=”12,153,0,0″

Name=”label3″ VerticalAlignment=”Top” Width=”120″ Content=”Age” />

<TextBox Height=”23″ HorizontalAlignment=”Right” Margin=”40,38,22,0″

Name=”textBox1″ VerticalAlignment=”Top” Width=”240″

Text=”{Binding Path=GivenName, Mode=TwoWay}” />

<TextBox Height=”23″ HorizontalAlignment=”Right” Margin=”40,95,22,0″

Name=”textBox2″ VerticalAlignment=”Top” Width=”240″

Text=”{Binding Path=Surname, Mode=TwoWay}”/>

<TextBox Height=”23″ HorizontalAlignment=”Right” Margin=”40,153,22,0″

Name=”textBox3″ VerticalAlignment=”Top” Width=”240″

Text=”{Binding Path=Age, Mode=TwoWay}”/>

</Grid>

</DataTemplate>

</UserControl.Resources>

<Grid x:Name=”LayoutRoot” Background=”White”>

<ListBox ItemsSource=”{Binding}”

ItemTemplate=”{StaticResource dataTemplateBinding}” />

<Button Content=”Older” Height=”23″ HorizontalAlignment=”Left” Margin=”43,242,0,0″

Name=”button1″ VerticalAlignment=”Top” Width=”75″ Click=”button1_Click” />

</Grid>

 

Collection Updates

The INotifyPropertyChange will work only when a property is changed but when a collection is changed we need to implement the INotifyColectionChanged. We can either use ObservalbeCollection<T> or implement this interface to get the update whenever a new item is added to the collection.

Let’s add a new button along with a new event handler to add a new item to the collection so we need to change the xaml and cs file to as below:

private void button2_Click(object sender, RoutedEventArgs e)

{

people.Add(new Person { GivenName = “Scott”, Surname = “D”, Age = 62 });

}

 

<Button Content=”Add Item” Height=”23″ HorizontalAlignment=”Left” Margin=”325,182,0,0″

Name=”button2″ VerticalAlignment=”Top” Width=”75″ Click=”button2_Click” />

 

Now replace the List<Person> with ObservableCollection<Person>.

ObservableCollection<Person> people = new ObservableCollection<Person>();

 

And that is it. Now whenever you click the Add Item button a new item will be added to the collection and also the ListBox will be updated.

 

Grouping

If we want to group the data based on some criteria then we can use the CollectionViewSource. This groups the items based on the property specified of the items.

<UserControl.Resources>
    <CollectionViewSource x:Key="mySource" Source="{Binding Path=RawItems}">
        <CollectionViewSource.GroupDiscussions>
            <PropertyGroupDiscription PropertyName="EventTrack" />
        </CollectionViewSource.GroupDiscussions>
    </CollectionViewSource>
</UserControl.Resources>

 

DataGrid internally understands grouping but the ItemsControl does not. So this is an advantage as by using the ItemsControl we can have our own custom visualizations.

 

Silverlight 4 Grouping

Silverlight 4 Grouping

When we wrap a collection in a collection view source, it provides a property known as groups.  Normally we can bind to a wrapper but we can bind to the groups property instead.

<ItemsControl ItemsSource="{Binding Path=Groups, Source={StaticResource groupSource}}">
    <ItemsControl.ItemTemplate>
            <DataTemplate>
                <ItemsControl ItemsSource="{Binding Path=Items}" />
            </DataTemplate>
        </ItemsControl.ItemTemplate>
</ItemsControl>

Silverlight 4 Grouping

Hierarchical Binding

The basic ability to bind with hierarchical controls is provided by the HeadedItemsControl class. HeadedItemsControl derive from ItemsControl so the binding works in nearly the same way. The difference is in the ItemTemplate property as need to refer to HieraricalDataTemplate instead of a normal DataTemplate. The Hierarchical Data Template has one feature. It too has a ItemsSource Property.

<sdk:HierarchicalDataTemplate ItemsSource="{Binding Path=Children}">
    <TextBlock Text="{Binding Path=Label}" />
</sdk:HierarchicalDataTemplate>

Silverlight 4 Hierarchical Binding

 

Find the source code ralated to this post here.

 

Any questions, comments and feedback are most welcome.

 

File Access Option

In Silverlight there are 3 main ways of accessing files:

  • OpenFileDialog and SaveFileDialog – This is the most flexible of all the file access options as this can be used by any Silverlight application running at any permission level. The user can select any file as long as the user has permissions for the same. The user will have to select the file to read and while saving the user has to specify the filename to override or save as. The code has no permission to know the location of the file and unless the code has elevated permissions the path of the file cannot be known rather only the filename is available. The ability to know the exact path or location is considered to be a security risk by Silverlight. Also these File dialogs are also not allowed until the code for these dialogs is being run in an event handler for user input.
  • FileStream, StreamWriter – The second way is to use the different classes in the System.IO namespace. Silverlight offers classes like File, FileInfo, Directory, DirectoryInfo, FileStream, StreamWriter, etc. In these operations user is not involved. This mode of operation is available only for the trusted application. Not all Silverlight applications can use unless the application is running under elevated privileges.
  • Isolated Storage – A Silverlight application can read or write files to the Isolated Storage without needing the user to be involved. The files can be read or written. The only catch is that the files are saved in the private storage which is under the user directory and the path is not available. So you can just use it as a private store of files where you can access the files. There is no access available for the user files and neither the user can look at the files that are saved unless the user looks into the most of the hidden folder and files under their directory. So the main purpose of Isolated Storage is to provide the application the fast and easy access of files store without user input or elevated trust. But this storage is not reliable as the user can always delete the files.

Let’s have a look at each of these File Access methods in detail:

SaveFileDialog

The SaveFileDialog uses the same file save dialog box supplied by the operating system. To use it we need to create an instance of the SaveFileDialog and call the ShowDialog method. It returns true or false depending on whether the user selected a file or not. The return type of ShowDialog method is nullable bool so we need to compare the return value of the ShowDialog method with true to proceed further with the file selected. However the ShowDialog never returns null but this is the way it is designed. As you can see in the image below once we verify that the user has a selected a filename we can open the file. We can get the filename of the file from the SaveFileName property but the path is not available. So the only way write data is to write the string returned by the dialog.

 

Silverlight 4 : Save File Dialog

Silverlight 4 : Save File Dialog

From the perspective of .Net this is only a string which we can put in a StremWriter to write text into it. If we want to write binary data into it then we can use the Stream Object directly. We can browse to the selected folder and have a look at the saved file.

OpenFileDialog

The OpenFileDialog is similar to the SaveFileDialog. The major difference being  that FileOpenDialog offers a property called multi select which when set to true the user can choose multiple files. So the OpenFileDialog being more complex does not offer a OpenFile method. So depending on whether the OpenFileDialog is in single file or multi file mode we need to use the File or Files property respectively. So as we see in the image below we call File.OpenRead as we are dealing with single file. In the multi select mode we would use the Files property which would return a collection of FileInfo object.

 

Silverlight 4 : Open File Dialog

Silverlight 4 : Open File Dialog

FileStream

The usage of FileStream is quite similar to the regular .NET File access using FileStream. However in Silverlight only application running in elevated trust are allowed to use this technique which is available only in Out of Browser mode. Another restriction in Silverlight is that the files only in specific folder location are available using FileStream. The accessible files are the ones which are in the Users Documents, Music, Pictures and Videos. The reason is because Silverlight runs on multiple platforms and the file system on these platforms might be different and location of these folders might be different on different platforms. We need to use the Enviorment.GetFolderPath method to access these folders. We can also inspect the directory structure beneath these folders using the Directory and DirectoryInfo class in System.IO.

Isolated Storage

It provides storage associated with the logged in user. The API presents data from the stream class from the System.IO namespace. This storage can be used to store either text or binary data. It’s called as Isolated as the storage is partitioned and the Silverlight application have access only to specific parts. Firstly, the storage is partitioned as per the user so that the apps do not have access to the storage space allocated to the other user of the machine. Secondly, the storage is partitioned as per the site and optionally as per the application in the site as well. The partition of the isolated storage depends on the xap files that the apps access. The isolated storage is not dependent on the hosting page. If the multiple pages of an application access the same xap then they will share the same isolated storage. This works for a multi-site website as well. So if multiple sites download the same xap file then the Silverlight supplication will have access to the same Silverlight application isolated store. The Silverlight application provides 1MB of space by default for each user. If the application has more space requirement then it can ask the user for it. Isolated storage is available across browsers on the same machine similar to sharing the cookies across all bowsers, it takes the cross platform support to whole new level.

 

You might be surprised to know that Silverlight is not the pioneer of isolated storage. It was introduced in Widows forms to store data from the web in the partial trust scenarios. Although the method of access is different and there is no way to access the full .Net framework featured Isolated storage.

Now let’s see how to Write to the Isolated storage. Add the following to your Silverlight application.

try

{

//Obtaining the isolated storage from the user

using (IsolatedStorageFile isoStore =

IsolatedStorageFile.GetUserStoreForApplication())

{

//Create new file

using (IsolatedStorageFileStream isoStream =

new IsolatedStorageFileStream(“MyData.txt”,

FileMode.Create, isoStore))

{

//write some content to the file

using (StreamWriter writer = new StreamWriter(isoStream))

{

//Writing line to the file

writer.WriteLine(“Isolated storage is a cool feature”);

}

}

}

}

catch { }

 

As you would see that we need to begin by asking the user specific store for the application. We can also get the user store shared by all the application on the site by calling GetUSerStoreForSite(). The method returns the directory. Then we create an IsolatedStorageFileStream and the constructor requires the IsolatedStorgaeFile as one of the inputs. So here we create a new file in the store but we do not know the location of it. Then we wrap the IsolatedStorageFileStream into a StreamWriter and we write to that file.

Reading from the Isolated storage is very similar with 3 changes. FileMode.Open instaed of FileMode.Create, StreamReader instead on StreamWriter and reader.ReadLine instead of writer.WriteLine.

 

try

{

//Obtaining the isolated storage from the user

using (IsolatedStorageFile isoStore =

IsolatedStorageFile.GetUserStoreForApplication())

{

//Create new file

using (IsolatedStorageFileStream isoStream =

new IsolatedStorageFileStream(“MyData.txt”,

FileMode.Open, isoStore))

{

//write some content to the file

using (StreamReader reader = new StreamReader(isoStream))

{

//Writing line to the file

String sb = reader.ReadLine();

_isolatedStorageReadText.Text = “Read from UserData.txt: ” + sb;

}

}

}

}

catch { }

 

Deleting from the Isolated Storage. To delete the file from the Isolated we do not need to wait on the user. We can use the code below to do that.

try

{

//obtain the Isolated Storage for the user

using (IsolatedStorageFile isoStore =

IsolatedStorageFile.GetUserStoreForApplication())

{

//Delete

isoStore.DeleteFile(“UserData.txt”);

}

}

catch { }

 

Increase the Quota for the Isolated Storage

There is an option for the application to ask for more Isolated Storage space from the user but its not necessary that this space will be provided as its up the user to provide that space. The additional space request should be made at some user input because if its made at any other time then Silverlight will automatically fail the request. This means the extra Quota is only available to the applications with which the user is interacting. The following code can be use to request for additional isolated storage space.

using (var store = IsolatedStorageFile.GetUserStoreForApplication())

{

Int64 spaceToAdd = 5242880;

Int64 curAvail = store.AvailableFreeSpace;

if (curAvail < spaceToAdd)

{

if (!store.IncreaseQuotaTo(store.Quota + spaceToAdd))

MessageBox.Show(“Increase rejected.”);

else

MessageBox.Show(“Increase approved”);

}

else

MessageBox.Show(curAvail.ToString() + “bytes is available”);

}

 

Silverlight 4 : Increase Quota Isolated Storage

Silverlight 4 : Increase Quota Isolated Storage

The users not have the option to wind the quota back as Silverlight does not know which file to trim to remove the quota.

You can download the source code for this file here.

 

Any comments, feedback and questions are most welcome.

 

Hey guys,

As you would all know that the building blocks of an application are controls but you need to know the layouts as well to know where and how you can place these controls? So we are going to talk about the layout panels in WPF, what are the common layout properties that are offered by WPF and we would also have a look on how to create a navigation application in WPF.

Before we go into what layout panels do WPF has to offer we need to have a look how the layout processing happens in WPF. Now it is obvious that WPF will redo the layout when the applications starts or when something changes on the layout. The layout occurs in two phases: measure and arrange.

In the measure phase WPF walks through the each element in the tree and finds out as how large each element would like to be by calling the method Measure() on each element and it also tries to provide the information as to how much space is likely to available. There are two types of layouts that gets formed: Constrained (when WPF is able to make a good guess of the space that might be available) and unconstrained (When WPF does not have a fair idea of the layout space available). Now elements are not supposed to ask about the space during the measure phase so they just return the preferred size. Also in the unconstrained phase where the size passed is infinity the elements are supposed to return the exact size they require. This sometimes also known as Size To Content.

In the arrange phase WPF calls the arrange method on each element as it now know how much space each element requires. WPF tries to accommodate each elements requirement and if the space provided is less than the controls asked then the controls will be scaled accordingly. But if the element is asking for impossible space then the elements will be cropped.

Declarative Layout

WPF wants us to specify what our requirements are and then in the background WPF does all the work to arrange the resources for it. The best part of it is that it is declarative and can be defined entirely in xaml which can be of course customized as well.

WPF layouts also have the special facilities like automatic resizing according to the space available for the layouts. It also supports dynamic changes that are made to the WPF applications like adaptations to data changes at runtime or locale changes at runtime.

Some of the common layout properties provided by all the layout controls in WPF as Margin, Padding, Horizontal Alignment, Vertical Alignment, Min/Max Width, Min/Max Height, Width, Height. These provide the consistency in the layouts in WPF.

Margin

The margin property helps us determine how much place is there around the space around the edges. Means if you do not want the control to take lesser space then it has been allocated to it so that it does just stick its border along with other controls you could use the margin.

We could specify the Margin as a single value and control will have uniform outer space around it. The unit for the margin is device independent pixels.

Margin in WPF

Margin in WPF

This means that the unit is 1/96th of an inch. So if the margin is specified as 96 pixels then the control will have a space of 1inch around it in theory but in actual this would happen if windows know the resolution of its output device, which is not the case in most cases as most of the windows pc end up in default configuration. If windows does not know the resolution then it will guesses it 96 for 1 inch across. But if windows is using large font sizes then the windows will guess that 120 pixels for 1 inch of the space. So now the WPF unit will be a little larger than the normal pixel. So this is confusing.

We could also specify the Left and Top margin or you could specify the left, top, right and bottom margin specifically.

 

Margin in WPF

Margin in WPF

Padding

The Padding property is similar to margin. As margin specifies the pace outside the control padding specifies the space between the border and content of the control. Padding is not available for all elements as it makes sense for controls that have content. Just like margin padding can be specified as a single number, left and top or explicitly for each left, top, right and bottom.

Alignment

Alignment comes into the picture when the space available for the control is more than required. We can specify the Vertical Alignment or Horizontal Alignment.

 

The default value of Vertical and Horizontal alignment is stretch. So if we specify the horizontal and vertical alignments other than stretch then the control would size to its content depending on the alignments specified.

Content Alignment

Horizontal and Vertical alignments specify how the controls uses the space provided by its container but Horizontal Content Alignment and Vertical Content Alignment determines how the content would align within the control.  Horizontal Content Alignment and Vertical Content Alignment have the same values as Horizontal Alignment and Vertical Alignment and behave quite similarly. The only difference is that it aligns the content instead of the control.

Explicit Height and Width

Most of the times the constrained or the unconstrained size provided to the element do not match your requirements so you could specify the explicit height and width for the control. If you do not want to specify the fixed width and height of then you specify the range by specifying the MinWidth and MinHeight and MaxWidth and MaxHeight.

Grid

WPF provides multiple styles of placing the controls by proving the multiple layout panels. The most flexible of these layouts is the grid. It derives from the panels and provides a row and column layout for placing the controls. For a constrained layouts we could provide the row and column to have autosize or for an unconstrained layout we can specify the specific row or column size values or have a proportional values.

Grid in WPF

Grid in WPF

You could see multiple things in the image above. The use of attached forperties in Button.

The Rows and columns are specified and the rows and columns are sized equally as we not specified any specific size which could be done by specifying the values.

We could also specify the specific height or width of a button and the grid row or columns will be resized accordingly if the space is available for the grid to incorporate the individual requirements for the controls.

 

Grid in WPF

Grid in WPF

We could also set the margin properties and see the effect of these properties within the grid.

 

Grid in WPF

Grid in WPF

You could see the star (*) values used for the height which is relative sizing use. We can have multiple elements in a grid and also elements can span multiple rows or columns. Grid is the default layout element when you create a new vs project.

GridSplitter

You can add a grid splitter to a cell and set the direction and it will resize the columns and rows when dragged.

DockPanel, StackPanel and WrapPanel

WPF also provides DockPanel, WrapPAnel and StcakPanel as a simpler layout panels to work with. There property values are shown in the image below:

 

A StackPanel provides horizontal or vertical stacking of elements whereas a dockpanel provides the alignment as Top, Bottom, Left, Fill and Right and a WrapPanel provides the stacking of elements from left to right and then to new line when the line space is finished.

Canvas

Canvas is the simplest panels. It just places the elements where to tell it to i.e. absolute positioning and will cause the elements to Size to Content. The positions are specified using the Canvas attached properties Top and Right. It can be used at places where you have something like drawing a which you do not want to resize.

ScrollViewer

Another layout control is ScrollViewer. It is not a Panel. It is a Content Control which allows putting control that won’t fit the screen. The Scroll Viewer performs an unconstraint layout and tells the control that it has as much space as it asked for. But this not the actual space, it is the virtual space and the scroll viewer performs the clip and translate transform to show the view of the content. The child does not need to know that it is being scrolled. It is sometimes useful use the scrolls. If you do not want to load the full virtual space initially as it might not be as Performatic. So if you want the control to participate in the scrolling process then if the child element inside the ScrollViewer implements IScrollInfo then the scrollviewer will stop pretending that virtual space is unlimited and will give the control to element for controlling the scrolling.

ViewBox

Like scrollviewer viewbox provides solution fit in content inside a constrained space. But unlike scrollviewer ViewBox scales the content to fit the ViewBox. ViewBox does this for any kind of content like vector graphics, bitmaps or WPF controls.

As you could see in the image below, the Canvas has fixed Width and Height. The reason is that the ViewBox needs to know whats the size of the content so that it can scale and resize it accordingly.

 

ViewBox in WPF

ViewBox in WPF

This works till do not set a stretch property on the ViewBox as it will start adding other behaviors in the ViewBox.

Windows

Window is the main compoanent of any WPF application. It is a Content Control. You can multiple styles in the Window like chrome, borderless or transparent.

There is also the Popup class that is used in Menus, DropDowns and ComboBox. It is also a content Control and can be put custom use.

The third type of Window is Navigation Window and it is slightly different form other windows. The model is quite similar to a web browser i.e. it can be used for navigation from one Page to another as it is built using the Page Class. It has back and forward buttons for navigation. If the Navigation application does not have a Window then the WPF will create the host window and host the page there and provide the navigation controls.

Windows in WPF

Windows in WPF

A frame in WPF is a control that will host the pages and provide the nested navigation area.

The code for this post can be downloaded here
Any questions, feedback and comments are most welcome.

 

Hey guys,

In this part 2 of learn WPF we are going to talk about Controls and see how these controls are different in WPF and what capabilities it provides you build a good WPF application. Also we would see how we can handle the user input using the events and commands.

Button

Let’s get started. You have already seen a Button in WPF. WPF also have a CheckBox and RadioButton. But as you could see in the image below

ButtonBase is the base class for the any button in WPF and ToggleButton is the base class for the CheckBox and RadioButton. Now its really interesting to know that the controls in WPF are divided into two namespaces : System.Windows.Controls (Contains Button, CheckBox, RadioButton) and System.Windows.Controls.Primitive (ButtonBase, ToggleButton, RepeatButton). Primitive controls are not designed in a way to be used individually but as a part of other controls. But you would see that the RepeatButton (A button that repeatedly raises its click event when it is pressed continiously) is part of the primitive namespace but still can be used individually. The reason because it is in the Primitive namespace is because in WPF it used as a part of other controls such as scrollbar.

RadioButtons are designed to be used in groups, so that only one of the RadioButton in the group is selected at a time. So when you assign the same group name for multiple radio buttons then only one of the radio buttons can be selected at a time. The grouping also works if you place all the radio buttons in one parent but if you assign a group name after that as well then then the groupname will override the parent grouping.

Content Model

As you might have seen in the Part 2 of Learn WPF that we could place just anything inside a button, like text, arbitrary content, data, etc. if type the below code into a WPF application you would see that you have placed multiple objects inside button.

 

Content Model WPF

Content Model WPF

This Content Model is available for any control in WPF. It not only supports the built in controls but also supports the custom controls that are made.

When you are adding just the text as content to the button you add an underscore before the letter which you want as the accelerated control for the button click.

 

Grouping Controls

Controls don’t have to be limited to a single piece of content, some controls have 2 content property. The base class for these controls is HeadedContentControl which has the both Header and Content property.

Expander and GroupBox derive from this Base Class. This allows them to have anything in the body and they can have anything in the header as well. To set anything as header we need to use the xaml property syntax which looks something like below:

 

XAML Property Syntax

XAML Property Syntax

This means I can place anything in header and anything in content. You can type the following code in a WPF application and see that header and content and have the same model but at the two different places.

 

Header and Content

Header and Content

Text Input

WPF has 3 controls for Text Input.

  • TextBox – This takes only input text as string and does not support any formatting.
  • RichTextBox – Allows formatting of text. Although you might be surprised to know that RichTextBox does not use the Rich Text Format internally. It uses WPF’s FlowDocument internally for formatting. This is actually good because you will find easier to work with WPF text model then to work with native RTF. Now you might think then why is it called as RichTextBox, the reason is that Windows call anything that supports rich text as RichTextBox. Also it supports RTF because whenever you copy any rich text from the clipboard to the RichTextBox it will treat it as rich text and vice versa as well i.e. when you copy text from RIchTextBox to Clipboard the formatting is not lost.

Both TextBox and RichTextBox derive from the same BaseClass which is TextBoxBase and hence support some common clipboard operations like copy, cut, paste.

  • PasswordBox – This textbox does not share the same base class as the other two. This is designed for editing password and the reason why it does not use the same base calss is that it does not want to offer some clipboard operations like copy, cut as these cause security risks.

 

The TextBox and RichTextBox both support spell check functionality. All you need to do is to set the SpellCheck.IsEnabled equals True and you would get spell check in the textbox. When you type a wrongly spelled work into the textbox you would see a red underlined in the misspelled word and also when you would right click on the misspelled word it will give you options to correct the spelling.

 

Spell Check

Spell Check

When xaml comes across the dot in SpellCheck.IsEnabled it treats the IsEnabled property as an attached property (An attached property is one which defined by a different class than the target object). So here the property is being used by the Textbox but the Property is defined in the class SpellCheck. This might seem a little odd to you at first but if you think about it, it’s an excellent idea to add properties to existing classes without modifying them.

The way a xaml compiler interprets this attached property is as below.

 

Spell Check in C#

Spell Check in C#

So the SpellCheck class uses these access methods like get and set to access the attached property and that’s the exact same way the mobile .NET property really do.

Now most the times we have a label in front of our textboxes and we might want to focus to the textbox using a keypress. Now if use the following code then we could achieve what we intend to.

 

Focus Targetting

Focus Targetting

I would say the main job of the label is focus targeting. If you want to just display some text then I would recommend a TextBlock. That’s what a Label uses internally. If you just want to display some text not use focus handling then using a label will be overkill.

Range Controls

Slider, ProgressBar and ScrollBar share a common base class named RangeBase. These share common properties that they define values within a range. Slider and Scrollbar provide you an option to drag and change the selected value where as in PrgressBar we cannot do so.

 

Items Controls

There are many items in WPF that can display multiple items like: ListBox, ListView, TreeView, ComboBox and they derive from a common base class which is ItemsControl. This class provides the Items property to hold the child items and also common sets of events along with the databinding support. As you see in the image below that except the TreeView all the other Items Controls derive from class selector which provide the provide the property to handle a selected item but you can still select items in the treeview as well. Actually the selector should have been named as an IndexedSeletor as it provides the indexed selection property. And as the Indexed selection property only makes sense for linear lists hence so those are the classes which are derived from the selector class.

Items Control WPF

Items Control WPF

You will also notice that the ListView is derived from a ListBox and the only difference between a ListBox and ListView is that ListBox does not have support or Column Headers. All the Items Controls have a Content Model which is similar to Button that we have already seen before and supports any number of child items.

If you put the code shown in the image in a WPF app then you would be able to realize how flexible the Items Control are.

 

Items Control WPF

Items Control WPF

As any items Control is very flexible this negates the need of a DataGrid which is not present in WPF.

Some other Items Controls are Menu, Tab Controls (Derive from the Selector class) and Toolbar. So we can generate the content of these controls as well from data binding.

 

Items Control WPF

Items Control WPF

Items Controls and Content Models

So now we have seen many Content Controls and Items Controls. As could see in the table below there are four content model classes from which the different controls derive

 

  • The Button and Label derive from Content Control class that support only a single content property. This is also the base class for Window as Window supports only one content.
  • Headerd Content Control which derives from the Content Control and is inherited by Exapander, GroupBox and TabItem. So you have a have a header along with content.
  • Items Control which provides the Multi Content Model. Each item in the list gets its own instance of it content model.
  • Headered Items Control which derives from the ItemsControl but adds an header just like the Headered Content Control. So this is used by Items Contols that have  children and also use a header like TreViewItems, Menu Items.

It’s also possible add new Content Model.

Items Containers

The way the Items Control provide Content Model to its children is that each child gets wrapped in its own nested control. So for every item we add to a a ListBox the ListBox adds it to the ListBox ItemsControl. Similarly ListView Wraps its children into lisview items control and so on. So these wrappers are called as Items Container and each ItemsControl Define its own Items Container. We can also define custom ItemsContainers. So we add the following code to a WPF UserControl we could see header, container,etc

 

Items Control in WPF

Items Control in WPF

 

Events

There are 3 types of Events in WPF

  • Tunneling Events – These events start from the Root Element and move down the child elements towards the Target Element. These represent the Preview Events.
  • Bubbling Events – These events start from the Target Element and route up towards the Root element. These represent the main events
  • Direct Events – These events do not route at all but just directs towards the target element and that’s all. These used at place where tunneling or bubbling does not make sense like mouseEnter and is only raised for target element.

 

Lets see an example. Add the code shown below in a WPF application

 

Events in WPF

Events in WPF

 

Events in WPF

Events in WPF

As you would see we have used MouseEnter and MouseDown Events handler. When we write the code like above and add handler using += then the code and xaml and very tightly coupled. The code makes assumptions about the xaml but the xaml does not have any assumptions about the code. But we add method names into the xaml we have xaml also making assumptions and there methods and handler are treated as attributes. Also when you used Visual Studio or Blend they add function names in the xaml and hence we wish to rely on these design tool s then we should utilize the xaml attributes approach.

If have a look at the output widow while running the application you would see that the mouse enter events are direct events and the mouse down events are bubbling up.

If we remove the background for border and the stackpanel then the white area which you see is the window and the same will be reflected by the Mouse Enter and Mouse Down events. Also if you change the background to transparent for stackpanel and border we would have the same look as no background but will behave the way there is a background.

Now if want the bubbling to stop then we can add e.Handled = “true” to the event handler where we want it to stop bubbling further.

Let’s add some more code to the cs file.

 

Events in WPF

Events in WPF

So when you click on a button the background will turn green. But we have not used event bubbling. So lets change the code a little bit to use event bubbling, so lets add the handler to the stackpanel to handle the button click.

 

Events in WPF

Events in WPF

 

When we run this we will get an invalid cast exception, so we need to change the code again a little bit. The event is not originating from Button, its originating from the element to which we have attached the event handler to.

 

Events in WPF

Events in WPF

Commands

Commands are the actions that the user would like the application to perform. WPF defines a lot of builtin commands. We could see some of them below:

 

But need to note here that these commands do not actually do anything. These commands are nothing more than a name unless you define as what these do would. But the controls in WPF have defined these commands in their implementations. Like the textbox has defined the implementation of the copy, cut and paste command. The pattern for the command is that commands on their own do not mean anything but they need to execute in the context of a particular control. So lets implement a command handler. Put the following code in a WPF application.

 

Commands in WPF

Commands in WPF

When you will run this app you will see that both the buttons have greyed out. This is because these do not know what to do with these commands. So let’s provide a handler for these commands to work. So add the following code in the code behind and you would see the commands working.

 

Commands in WPF

Commands in WPF

You could also use CanExecute property to decide at the runtime as to whether that property is available to run or not.

We could also bind the commands with the Menus. So we add built in commands to menus then the menu will be able to figure the shortcut key for each command and show it. It is able to do that becase each builtin command knows what its shortcut key is.

 

Also we don’t have to say ApplicationCommands.Copy. Also we have not specified the command objects text and so the menu looks up the display text for the commands and shows that. So the commands display the local language display text. But the access key is not available for the Menu items so if we want the menu items to have access key we need to specify the header. The reason that it is not done automatically is that commands are at application scope whereas the access keys are menu item scope for example in File Menu P would mean Print but in Edit menu P would mean Paste.

Now when you run the app you would see that the commands are working without writing any code that is because TextBox has registered the command binding for these commands.

 

Commands in WPF

Commands in WPF

If we do not wish to use commands we could input gestures to provide the keyboards shortcuts for these items.

 

The code for this post can be downloaded here

Any questions, comments and feedback are most welcome.