simple data binding
TRANSCRIPT
Data Binding in WPFData Binding in WPFData Binding, Binding PropertiesData Binding, Binding Properties
Doncho MinkovDoncho Minkov
Telerik School Telerik School AcademyAcademyhttp://schoolacademy.telerik.com
Technical TrainerTechnical Trainerhttp://www.minkov.it
Table of ContentsTable of Contents
1.1. Why We Need Data Binding?Why We Need Data Binding?
2.2. Simple BindingSimple Binding Binding a Control Property to Binding a Control Property to
Object Property Object Property
3.3. Data ContextsData Contexts
4.4. Binding Class and its PropertiesBinding Class and its Properties
5.5. Binding Control to Another ControlBinding Control to Another Control
2
Table of Contents (2)Table of Contents (2)
6.6. Value ConversionValue Conversion
7.7. Data ValidationData Validation
8.8. Binding Path SyntaxBinding Path Syntax
9.9. Using Relative SourcesUsing Relative Sources
10.10.Using Update Source TriggersUsing Update Source Triggers
3
Why We Need Data Why We Need Data Binding?Binding?
Why We Need Data Why We Need Data Binding?Binding?
The purpose of most applications is:The purpose of most applications is: Displaying data to usersDisplaying data to users Letting them edit that dataLetting them edit that data
Developers' job is:Developers' job is: Bring the data from a variety of sourcesBring the data from a variety of sources Expose the data in object, hierarchical, Expose the data in object, hierarchical,
or relational formator relational format With With WPF’sWPF’s data binding engine, you data binding engine, you
get more features with less codeget more features with less code
5
Why We Need Data Why We Need Data Binding? (2)Binding? (2)
Data binding is pulling information out of Data binding is pulling information out of an object into another object or propertyan object into another object or property Data binding means automatically change Data binding means automatically change
a property when another property is a property when another property is changedchanged
Many Windows applications are all about Many Windows applications are all about datadata
Data binding is a top concern in a user Data binding is a top concern in a user interface technologies like WPF or interface technologies like WPF or SilverlightSilverlight
WPF and Silverlight0 provide very WPF and Silverlight0 provide very powerful data binding mechanismspowerful data binding mechanisms
6
Simple Simple BBindinginding
Simple Simple BBindinginding
Simple binding in WPF Simple binding in WPF is the act of is the act of registering two properties with the registering two properties with the data binding engine data binding engine Letting the Letting the engine keep them engine keep them
synchronizedsynchronized The synchronization and The synchronization and
conversion are duties of the data conversion are duties of the data binding engine in WPFbinding engine in WPF
8
Simple Simple BBindinginding (2) (2) Binding a property to a data source Binding a property to a data source
property:property:
The shortcut binding syntax:The shortcut binding syntax:
Binding between the Binding between the TextText property of property of the the TextBoxTextBox and an object called and an object called SomeNameSomeName SomeNameSomeName is a property of some object to is a property of some object to
be named laterbe named later 9
<TextBox ...><TextBox ...> <TextBox.Text><TextBox.Text> <Binding Path="SomeName" /><Binding Path="SomeName" /> </TextBox.Text></TextBox.Text></TextBox></TextBox>
<TextBox Text="{Binding Path=SomeName}" /><TextBox Text="{Binding Path=SomeName}" />
Data ContextsData Contexts
Data ContextsData Contexts In WPF every In WPF every FrameworkElementFrameworkElement and and
every every FrameworkContentElementFrameworkContentElement has a has a DataContextDataContext property property DataContextDataContext is an object used as data is an object used as data
source during the binding, addressed source during the binding, addressed by binding by binding PathPath
If you don’t specify a If you don’t specify a SourceSource property property WPF searches up the element tree WPF searches up the element tree
starting at the current elementstarting at the current element Looking for a Looking for a DataContextDataContext property property
that has been setthat has been set11
Data Contexts (2)Data Contexts (2)
Two controls with a common logical Two controls with a common logical parent can bind to the same data parent can bind to the same data sourcesource
Providing a Providing a DataContextDataContext value for both value for both of the text box controlsof the text box controls
12
<!-- DataContextWindow.xaml --><!-- DataContextWindow.xaml --><Grid Name="GridMain"><Grid Name="GridMain"> … … <TextBlock …>Name: </TextBlock><TextBlock …>Name: </TextBlock> <TextBox Text="{Binding Path=Name}" … /><TextBox Text="{Binding Path=Name}" … /> <TextBlock …>Age:</TextBlock><TextBlock …>Age:</TextBlock> <TextBox Text="{Binding Path=Age}" … /><TextBox Text="{Binding Path=Age}" … /> <Button Name="ButtonBirthday Content="Birthday!" <Button Name="ButtonBirthday Content="Birthday!" … />… /></Grid></Grid>
Data Contexts (3)Data Contexts (3) Setting an object as a value of the Setting an object as a value of the
grid’s grid’s DataContextDataContext property in the property in the MainWindowMainWindow constructor:constructor:
13
public partial class MainWindow : Windowpublic partial class MainWindow : Window{{ Person person = new Person("Tom", 11); Person person = new Person("Tom", 11);
public MainWindow()public MainWindow() {{ InitializeComponent();InitializeComponent(); GridMain.DataContext = person;GridMain.DataContext = person; }} … …}}
Data ContextsData ContextsLive DemoLive Demo
Binding to Other Binding to Other ControlsControls
Binding to Other Binding to Other ControlsControls
WPF provides binding of one WPF provides binding of one element’s property to another element’s property to another element’s propertyelement’s property
The button’s foreground brush will The button’s foreground brush will always follow foreground brush’s always follow foreground brush’s color of the age color of the age TextBoxTextBox
16
<TextBox Name="ageTextBox" Foreground="Red" … <TextBox Name="ageTextBox" Foreground="Red" … />/><Button …<Button … Foreground="{Binding Foreground="{Binding ElementName=ageTextBox, ElementName=ageTextBox, Path=Foreground}" Content="Birthday" />Path=Foreground}" Content="Birthday" />
Binding to Other Binding to Other ControlsControlsLive DemoLive Demo
The The BindingBinding Class and Its Class and Its PropertiesProperties
BindingBinding Class Class A more full-featured binding exampleA more full-featured binding example
This features are represent in This features are represent in BindingBinding classclass ConverterConverter – convert values back and – convert values back and
forth from the data sourceforth from the data source ConverterParameterConverterParameter – parameter – parameter
passed to the passed to the IValueConverterIValueConverter methods during the conversionmethods during the conversion
19
<TextBox x:Name="TextBoxPerson" <TextBox x:Name="TextBoxPerson" Foreground="{Binding Path=Age, Foreground="{Binding Path=Age, Mode=OneWay,Mode=OneWay, Source={StaticResource Tom},Source={StaticResource Tom}, Converter={StaticResource ageConverter}}" Converter={StaticResource ageConverter}}" />/>
BindingBinding Class (2) Class (2)
More More BindingBinding class properties class properties ElementNameElementName – used when the source – used when the source
of the data is a UI element as well of the data is a UI element as well as the targetas the target
ModeMode – one of the – one of the BindingModeBindingMode values values TwoWayTwoWay, , OneWayOneWay, , OneTimeOneTime, , OneWayToSourceOneWayToSource, or , or DefaultDefault
PathPath – path to the data in the data – path to the data in the data source objectsource object
SourceSource – a reference to the data – a reference to the data sourcesource 20
BindingBinding Class (3) Class (3) The binding target can be any WPF The binding target can be any WPF
elementelement Only allowed to bind to the element’s Only allowed to bind to the element’s
dependency propertiesdependency properties
The The TextBoxTextBox control is the control is the binding binding targettarget
Object that provides the data is the Object that provides the data is the binding sourcebinding source 21
Value ConversionValue Conversion
Value ConversionValue Conversion
In the previous example we might In the previous example we might decide that anyone over age 25 is decide that anyone over age 25 is hothot Should be marked in the UI as redShould be marked in the UI as red
Binding to a non-Text propertyBinding to a non-Text property
Bound the age text box’s Bound the age text box’s TextText property to the property to the PersonPerson object’s object’s AgeAge propertyproperty 23
<TextBox<TextBox Text="{Binding Path=Age}"Text="{Binding Path=Age}" Foreground="{Binding Path=Age, …}" … />Foreground="{Binding Path=Age, …}" … />
Value Conversion (2)Value Conversion (2) How to bind the How to bind the ForegroundForeground property property
of the text box to of the text box to AgeAge property on property on the the PersonPerson object? object? The The AgeAge is of type is of type Int32Int32 and and ForegroundForeground is of type is of type BrushBrush
Mapping from Mapping from Int32Int32 to to BrushBrush needs to needs to be applied to the data binding from be applied to the data binding from AgeAge to to ForegroundForeground
That’s the job of a That’s the job of a ValueConverterValueConverter
24
Value Conversion (3)Value Conversion (3)
A value converterA value converter is an is an implementation of the implementation of the IValueConverterIValueConverter interface interface ConvertConvert()() – converting from the – converting from the
source data to the target UI datasource data to the target UI data ConvertBackConvertBack()() – convert back from – convert back from
the UI data to the source datathe UI data to the source data
25
Value Conversion (4)Value Conversion (4) Converter Converter Int32Int32 BrushBrush
26
public class AgeToForegroundConverter : public class AgeToForegroundConverter : IValueConverterIValueConverter{{ public object Convert(object value, public object Convert(object value, Type targetType, …)Type targetType, …) {{ if (targetType != typeof(Brush))if (targetType != typeof(Brush)) { { return null; return null; }} int age = int.Parse(value.ToString());int age = int.Parse(value.ToString()); return (age > 25 ? Brushes.Red : return (age > 25 ? Brushes.Red : Brushes.Black);Brushes.Black); }} … …}}
Value Conversion (4)Value Conversion (4) Creating an instance of the Creating an instance of the
converter class in the XAML:converter class in the XAML:
27
<Window … xmlns:local="clr-namespace:WithBinding"><Window … xmlns:local="clr-namespace:WithBinding"> <Window.Resources><Window.Resources> <local:Person x:Key="Tom" … /><local:Person x:Key="Tom" … /> <local:AgeToForegroundConverter <local:AgeToForegroundConverter x:Key="ageConverter"/>x:Key="ageConverter"/> </Window.Resources></Window.Resources> <Grid DataContext="{StaticResource Tom}"> …<Grid DataContext="{StaticResource Tom}"> … <TextBox<TextBox Text="{Binding Path=Age}"Text="{Binding Path=Age}" Foreground="{Binding Path=Age,Foreground="{Binding Path=Age, Converter={StaticResource ageConverter}}" … /> Converter={StaticResource ageConverter}}" … /> …… <Button … Foreground="{Binding Path=Foreground,<Button … Foreground="{Binding Path=Foreground, ElementName=ageTextBox}">Birthday</Button>ElementName=ageTextBox}">Birthday</Button> </Grid></Grid></Window></Window>
Value ConversionValue ConversionLive DemoLive Demo
Data ValidationData Validation
Data ValidationData Validation A A validation validation validates a piece of validates a piece of
data in the target when the data in the target when the binding occursbinding occurs Derives from the base Derives from the base ValidationRuleValidationRule class class
30
class EGNValidationRule : ValidationRuleclass EGNValidationRule : ValidationRule{{ public override ValidationResult Validate(public override ValidationResult Validate( object value, CultureInfo cultureInfo)object value, CultureInfo cultureInfo) {{ if (Regex.IsMatch((string)value, "\A\d{10}\Z"))if (Regex.IsMatch((string)value, "\A\d{10}\Z")) return new ValidationResult(true, null);return new ValidationResult(true, null); elseelse return new ValidationResult(false, "Invalid return new ValidationResult(false, "Invalid EGN");EGN"); }}}}
Data Validation (2)Data Validation (2)
When a validation result indicates When a validation result indicates invalid data, a invalid data, a ValidationErrorValidationError object is createdobject is created Checking for errors:Checking for errors:
Getting the error messages:Getting the error messages:
You can also listen to the You can also listen to the ValidationErrorValidationError attached event attached event
31
Validation.GetHasError(UIElement)Validation.GetHasError(UIElement)
var errors = Validation.GetErrors(UIElement);var errors = Validation.GetErrors(UIElement);string errorMsg = string errorMsg = (string)errors[0].ErrorContent;(string)errors[0].ErrorContent;
Data Validation (3)Data Validation (3)
32
<Window x:Class="BindingValidation.MainWindow"<Window x:Class="BindingValidation.MainWindow" … … xmlns:local="clr-xmlns:local="clr-namespace:BindingValidation" />namespace:BindingValidation" /> … … <TextBox Name="TextBoxEGN"><TextBox Name="TextBoxEGN"> <TextBox.Text><TextBox.Text> <Binding Path="EGN"><Binding Path="EGN"> <Binding.ValidationRules><Binding.ValidationRules> <local:EGNValidationRule /><local:EGNValidationRule /> </Binding.ValidationRules></Binding.ValidationRules> </Binding></Binding> </TextBox.Text></TextBox.Text> </TextBox></TextBox> … …</Window></Window>
Enabling validation rules in the Enabling validation rules in the XAML:XAML:
Data Validation (4)Data Validation (4)
33
<Window.Resources><Window.Resources> <Style TargetType="{x:Type TextBox}"><Style TargetType="{x:Type TextBox}"> <Setter Property="Validation.ErrorTemplate"><Setter Property="Validation.ErrorTemplate"> <Setter.Value><Setter.Value> <ControlTemplate><ControlTemplate> <WrapPanel><WrapPanel> <Border BorderBrush="Red"><Border BorderBrush="Red"> <AdornedElementPlaceholder/><AdornedElementPlaceholder/> </Border></Border> <TextBlock <TextBlock Foreground="Red">!</TextBlock>Foreground="Red">!</TextBlock> </WrapPanel></WrapPanel> </ControlTemplate></ControlTemplate> </Setter.Value></Setter.Value> </Setter></Setter> </Style></Style></Window.Resources></Window.Resources>
Styling the UI controls containing Styling the UI controls containing an error:an error:
Binding Path SyntaxBinding Path Syntax
Binding Path SyntaxBinding Path Syntax
When you use When you use Path=SomethingPath=Something in a in a BindingBinding statement, the statement, the SomethingSomething can be in a number of formatscan be in a number of formats Path=PropertyPath=Property – bind to the property – bind to the property
of the current object of the current object ((Path=AgePath=Age)) Path=(Path=(OwnerType.AttachedPropertyOwnerType.AttachedProperty))
– bind to an attached dependency – bind to an attached dependency property property ((Path=(Path=(Validation.HasErrorValidation.HasError))))
Path=Property.SubPropertyPath=Property.SubProperty – – bind to bind to a subproperty a subproperty ((Path=Name.LengthPath=Name.Length))
35
Binding Path Syntax (2)Binding Path Syntax (2) Other formatsOther formatsPath=Property[n]Path=Property[n] – bind to an indexer – bind to an indexer ((Path=Names[0]Path=Names[0]))
Path=Property/PropertyPath=Property/Property – – master-detail master-detail bindingbinding ((Path=Customers/OrdersPath=Customers/Orders))
Path=(OwnerType.AttachedProperty)Path=(OwnerType.AttachedProperty)[n].SubProperty[n].SubProperty – bind to a mixture of – bind to a mixture of properties, properties, subpropertiessubproperties, and indexers, and indexers Path=(Validation.Errors)Path=(Validation.Errors)[0].ErrorContent)[0].ErrorContent)
36
RRelative elative SSources ources
RRelative elative SSourcesources DDescribes the location of the escribes the location of the
binding source relative to the binding source relative to the position of the binding targetposition of the binding target
Relative sourcesRelative sources SelfSelf FindAncestorFindAncestor TemplatedParentTemplatedParent PreviousPrevious 38
<TextBox ...<TextBox ... ToolTip="{Binding RelativeSource={RelativeSource ToolTip="{Binding RelativeSource={RelativeSource Self},Self}, Path=(Validation.Errors)[0].ErrorContent}">Path=(Validation.Errors)[0].ErrorContent}">
UUpdate pdate SSource ource TTriggers riggers
UUpdate pdate SSource ource TTriggersriggers In previous example validation In previous example validation
doesn’t happen until the age text doesn’t happen until the age text box loses focusbox loses focus
Validation can happen immediately Validation can happen immediately when the control state changeswhen the control state changes
Using the Using the UpdateSourceTriggerUpdateSourceTrigger property on the property on the BindingBinding object object
40
<TextBox …><TextBox …> <TextBox.Text><TextBox.Text> <Binding Path="Age" <Binding Path="Age" UpdateSourceTrigger="PropertyChanged"> …UpdateSourceTrigger="PropertyChanged"> … </Binding></Binding> </TextBox.Text></TextBox.Text></TextBox></TextBox>
UUpdate pdate SSource ource TTriggersriggers
UpdateSourceTriggerUpdateSourceTrigger values values DefaultDefault – updates "naturally" based – updates "naturally" based
on the target controlon the target control PropertyChangedPropertyChanged – updates the – updates the
source immediatelysource immediately LostFocusLostFocus – updates the source – updates the source
when focus changeswhen focus changes ExplicitExplicit – when – when BindingExpression. BindingExpression. UpdateSourceUpdateSource()() is explicitly called is explicitly called
41
Simple Data BindingSimple Data Binding
Questions?Questions?
http://academy.telerik.com
ExercisesExercises1.1. Write a program that show a simple Write a program that show a simple
window, it contains two controls a window, it contains two controls a SliderSlider and a and a TextBlockTextBlock with a single line of text. If with a single line of text. If you pull the thumb in the slider to the right, you pull the thumb in the slider to the right, the font size of the text is increased the font size of the text is increased immediately. Add a label that shows the immediately. Add a label that shows the current font size. Use data binding.current font size. Use data binding.
2.2. Add to the previous exercise few buttons Add to the previous exercise few buttons each of which applies a preset value to the each of which applies a preset value to the slider. When you click the "Set to Large" slider. When you click the "Set to Large" button the code in button the code in ClickClick event sets the event sets the value of the slider, which in turn forces a value of the slider, which in turn forces a change to the font size of the text through change to the font size of the text through data binding.data binding.
43
Exercises (2)Exercises (2)
3.3. Write a program that shows a simple Write a program that shows a simple window, which contains a window, which contains a TextBlockTextBlock and and setup the setup the TextBlockTextBlock to draw its text from to draw its text from a a TextBoxTextBox and its current foreground and and its current foreground and background colors from separate lists of background colors from separate lists of colors.colors.
4.4. Create an application to enter person's Create an application to enter person's name and age. Bind the person's age name and age. Bind the person's age with a slider showing the range [1..100]. with a slider showing the range [1..100]. Add cAdd custom validation rulesustom validation rules to make sure to make sure that person’s age is within a the range that person’s age is within a the range ((derivederive from the from the ValidationRuleValidationRule class class and override the and override the Validate()Validate() method). method).
44