In this article

Data Binding

Microsoft Silverlight will reach end of support after October 2021. Learn more.

Data binding provides a simple way for Silverlight-based applications to display and interact with data. The way data is displayed is separated from the management of the data. A connection, or binding, between the UI and a data object allows data to flow between the two. When a binding is established and the data changes, the UI elements that are bound to the data can reflect changes automatically. Similarly, changes made by the user in a UI element can be reflected in the data object. For example, if the user edits the value in a TextBox, the underlying data value is automatically updated to reflect that change.

Some common binding scenarios include binding a ListBox to a list of headlines, an input form's TextBox to a customer data object, or an Image to the current user's photo.

This topic contains the following sections:

Connecting User Interface Elements with Data

Direction of the Data Flow

Change Notification

Updating the Data Source

Binding to Collections

Data Validation

Data Conversions

Debugging Data Bindings

This topic uses simple code examples to illustrate data binding concepts. For more complex examples, see the topics listed at the end.

The following example shows how to bind the Foreground color of a TextBox to a SolidColorBrush in code and XAML. The binding source is a property of the MyColors class, which is described later in this topic.

' Create an instance of the MyColors class
' that implements INotifyPropertyChanged.
Dim textcolor As New MyColors()
' Brush1 is set to be a SolidColorBrush with the value Red.
textcolor.Brush1 = New SolidColorBrush(Colors.Red)
' Set the DataContext of the TextBox MyTextBox.
MyTextBox.DataContext = textcolor

// Create an instance of the MyColors class
// that implements INotifyPropertyChanged.
MyColors textcolor = new MyColors();
// Brush1 is set to be a SolidColorBrush with the value Red.
textcolor.Brush1 = new SolidColorBrush(Colors.Red);
// Set the DataContext of the TextBox MyTextBox.
MyTextBox.DataContext = textcolor;

Note:

This example uses the XAML attribute syntax for creating the binding. You could also use the object element syntax to create the binding in XAML. For more information, see XAML Overview and Property Path Syntax.

The binding is created in XAML using the {Binding ...} syntax. The source is set in code by setting the DataContext property for the TextBox.

Data context is inherited. If you set the data context on a parent element, all its children will use the same data context. A child element can override this behavior by setting the Source property on its binding object or by setting its DataContext, which will then apply to all its children.

Setting the data context is useful when you want to have multiple bindings that all use the same source. To set the source for a single binding, set the Source property on the Binding object. For more information, see How to: Create a Binding.

You can bind to a property of the source object by setting the Binding.Path property. The Path property supports a variety of syntax options for binding to nested properties, attached properties, string indexers. For more information, see Property Path Syntax.

Altogether, the preceding example causes the binding engine to create a binding, which is OneWay by default, connecting the Foreground property of the TextBox to the brush1 property of the TextColor object.

Direction of the Data Flow

Each binding has a Mode property, which determines how and when the data flows. Silverlight enables three types of bindings:

OneTime bindings update the target with the source data when the binding is created.

OneWay bindings update the target with the source data when the binding is created and anytime the data changes. This is the default mode.

TwoWay bindings update both the target and the source when either changes. Alternately, you can disable automatic source updates and update the source only at times of your choosing.

In order for automatic target updates to occur, the source object must implement the INotifyPropertyChanged interface, as described in the next section.

Change Notification

In order for changes to the source object to propagate to the target, the source must implement the INotifyPropertyChanged interface. INotifyPropertyChanged has the PropertyChanged event, which tells the binding engine that the source has changed so that the binding engine can update the target value.

' Create a class that implements INotifyPropertyChanged.
Public Class MyColors
Implements INotifyPropertyChanged
Private _Brush1 As SolidColorBrush
' Declare the PropertyChanged event.
Public Event PropertyChanged As PropertyChangedEventHandler _
Implements INotifyPropertyChanged.PropertyChanged
' Create the property that will be the source of the binding.
Public Property Brush1() As SolidColorBrush
Get
Return _Brush1
End Get
Set(ByVal value As SolidColorBrush)
_Brush1 = value
' Call NotifyPropertyChanged when the source property
' is updated.
NotifyPropertyChanged("Brush1")
End Set
End Property
' NotifyPropertyChanged will raise the PropertyChanged event,
' passing the source property that is being updated.
Public Sub NotifyPropertyChanged(ByVal propertyName As String)
RaiseEvent PropertyChanged(Me, _
New PropertyChangedEventArgs(propertyName))
End Sub
End Class

Updating the Data Source

In TwoWay bindings, changes to the target automatically update the source, except when binding to the Text property of a TextBox. In this case, the update occurs when the TextBox loses focus.

You can disable automatic source updates and update the source at times of your choosing. For example, you can do this to validate user input from multiple controls before you update the bound data sources.

Binding to Collections

A binding source object can be treated either as a single object whose properties contain data or as a collection of objects. For example, you might want to display a list of items, such as monthly credit card bills. To do this, use an ItemsControl and use a DataTemplate to display each item in a collection. For more information on data templates, see How to: Customize Data Display with Data Templates.

You can enumerate over any collection that implements IEnumerable. If you want the target to update the ItemsSource when the collection changes, implement INotifyCollectionChanged. For more information on change notification, see the Change Notification section earlier in this topic.

You can also bind to instances of the CollectionViewSource class, which provides sorting, grouping, filtering, and currency support for other data sources. The CollectionViewSource enables you to display multiple views of data that stay synchronized with user selection changes.

The PagedCollectionView class provides another way to apply sorting, grouping, and filtering to another data source. This class also includes paging and editing, and provides a data source for controls such as DataPager.

For information about encapsulating a generic list in an object so that you can bind a control to it, see the first code examples for List<T> and Dictionary<TKey, TValue>.

The binding object implements INotifyDataErrorInfo and its GetErrors method returns a value that is not null. The GetErrors return value can change as a result of the completion of asynchronous validation operations.

Silverlight provides visual feedback for validation errors in the following cases:

To receive notification that a validation error has occurred or has been resolved, you must set the NotifyOnValidationError property to true on the binding object. This tells the binding engine to raise the BindingValidationError event when a validation error is added to or removed from the Validation.Errors collection. For example, you can handle the error event to log the error or provide additional visual feedback.

The source object throws an exception in the set accessor if the value is negative.

Public Class Bills
Private _Amount As Double
Public Property Amount() As Double
Get
Return _Amount
End Get
Set(ByVal value As Double)
If value < 0 Then
Throw New Exception("Amount must be greater than zero.")
End If
_Amount = value
End Set
End Property
End Class

After the sample starts, type in letters instead of numbers to get an error caused by the type converter. Type in a negative number to get an error from the source object's set accessor. Type in a positive number to resolve the validation error. TextBox target-to-source updates occur only when the TextBox loses focus. The button is provided to change the focus. If you prefer, you can update the source manually in response to the button click, as described earlier in the Updating the Data Source section.

In Silverlight 4, you can also display a friendly default value for null backing values by setting the TargetNullValue property.

You can also set a converter on any binding. The converter is customized for each scenario by creating a class and implementing the IValueConverter interface. The following example shows how to implement IValueConverter.

The binding engine calls the Convert and ConvertBack methods if the Converter parameter is defined for the binding. When data is passed from the source, the binding engine calls Convert and passes the returned data to the target. When data is passed from the target, the binding engine calls ConvertBack and passes the returned data to the source. The following example shows how to set the Converter parameter.

The converter also has optional parameters: ConverterCulture, which allows specifying the culture to be used in the conversion, and ConverterParameter, which allows passing a parameter for the conversion logic. For an example using these parameters, see IValueConverter.

If there is an error in the conversion, do not throw an exception. Instead, return DependencyProperty.UnsetValue, which will stop the data transfer.

In Silverlight 4, to display a default value that appears whenever the binding source cannot be resolved, set the FallbackValue property. This is useful to handle conversion and formatting errors. It is also useful to bind to source properties that might not exist on all objects in a bound collection.

Debugging Data Bindings

Starting with Silverlight 5, you can debug data bindings by setting breakpoints on bindings in XAML. This helps you track down issues that might otherwise be hard to isolate. For example, when a binding behaves incorrectly, the issue could be anything from an incorrect property path to an exception thrown during value conversion.

By default, your program will break on a binding breakpoint whenever the binding system transfers a value between the data source and target. This can occur because of user input or programmatic manipulation of the binding or the bound objects. When a breakpoint is hit, you can use the Locals window to examine every aspect of the current binding state.

The binding state is represented in the Locals window by a run time property called BindingState, which is of type BindingDebugState. This property provides access to information such as the current Binding, BindingExpression, and data source objects, the value at each completed stage of binding resolution, and any errors that have occurred.

You can also set breakpoint conditions in order to break only when the binding is in a particular state. To use the BindingState property in the condition statement, you must cast it to a BindingDebugState instance. You must also fully qualify all type names, as shown in the following example code.

Data binding debugging imposes a performance penalty while debugging. For this reason, it is useful to disable this feature after you have finished debugging your bindings. You can do this by setting the static Binding.IsDebuggingEnabled field to false in the constructor of your application class.