Binding the properties of View Model to View.
First and foremost thing is to create the object of PersonViewModel and set it as the DataContext for the Parent Grid in the View.
You can declare the instance of the PersonViewModel in the xaml file by adding reference to the namespace of the class in the xaml and create the object.
<Window x:Class="BegginersMVVM.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="MainWindow" Height="250" Width="300"
xmlns:vm="clr-namespace:BegginersMVVM"
>
<Window.Resources>
<vm:PersonViewModel x:Key="pvm"/>
</Window.Resources>
.
.
.
</Window>
|
And set the object created as the DataContext of the Grid.
<Grid DataContext="{StaticResource pvm}">
.
.
.
</Grid>
|
Now bind the properties of the ViewModel to the controls.
Remember to add "ValidatesOnDataErrors=True" property for the Textboxes in the binding for the validation to take effect.
<TextBox Text="{Binding Path=MyPerson.FName, ValidatesOnDataErrors=True, UpdateSourceTrigger=PropertyChanged}" Grid.Row="0" Grid.Column="1" />
|
Create style for our textboxes to display the ErrorMessage on mouse over.
<Style TargetType="{x:Type TextBox}">
<Setter Property="HorizontalAlignment" Value="Stretch"/>
<Setter Property="VerticalAlignment" Value="Center"/>
<Setter Property="Margin" Value="5"/>
<Style.Triggers>
<Trigger Property="Validation.HasError" Value="True">
<Setter Property="ToolTip" Value="{Binding Path=(Validation.Errors)[0].ErrorContent, RelativeSource={x:Static RelativeSource.Self}}" />
</Trigger>
</Style.Triggers>
</Style>
|
Our final xaml file would look like
<Window x:Class="BegginersMVVM.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="MainWindow" Height="250" Width="300"
xmlns:vm="clr-namespace:BegginersMVVM"
>
<Window.Resources>
<Style TargetType="{x:Type TextBlock}">
<Setter Property="HorizontalAlignment" Value="Right"/>
<Setter Property="VerticalAlignment" Value="Center"/>
<Setter Property="Margin" Value="5"/>
</Style>
<Style TargetType="{x:Type TextBox}">
<Setter Property="HorizontalAlignment" Value="Stretch"/>
<Setter Property="VerticalAlignment" Value="Center"/>
<Setter Property="Margin" Value="5"/>
<Style.Triggers>
<Trigger Property="Validation.HasError" Value="True">
<Setter Property="ToolTip" Value="{Binding Path=(Validation.Errors)[0].ErrorContent, RelativeSource={x:Static RelativeSource.Self}}" />
</Trigger>
</Style.Triggers>
</Style>
<vm:PersonViewModel x:Key="pvm"/>
</Window.Resources>
<Grid DataContext="{StaticResource pvm}">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="Auto" />
<ColumnDefinition Width="*" />
<ColumnDefinition Width="*" />
</Grid.ColumnDefinitions>
<Grid.RowDefinitions>
<RowDefinition Height="*" />
<RowDefinition Height="*" />
<RowDefinition Height="*" />
<RowDefinition Height="*" />
<RowDefinition Height="*" />
</Grid.RowDefinitions>
<TextBlock Text="First Name:" Grid.Row="0" Grid.Column="0"/>
<TextBlock Text="Last Name:" Grid.Row="1" Grid.Column="0"/>
<TextBlock Text="Age:" Grid.Row="2" Grid.Column="0"/>
<TextBlock Text="Citizenship:" Grid.Row="3" Grid.Column="0"/>
<TextBox Text="{Binding Path=MyPerson.FName, ValidatesOnDataErrors=True, UpdateSourceTrigger=PropertyChanged}" Grid.Row="0" Grid.Column="1" />
<TextBox Text="{Binding Path=MyPerson.LName}" Grid.Row="1" Grid.Column="1"/>
<TextBox Text="{Binding Path=MyPerson.Age, ValidatesOnDataErrors=True, UpdateSourceTrigger=PropertyChanged}" Grid.Row="2" Grid.Column="1"/>
<TextBox Text="{Binding Path=MyPerson.CitizenShip}" Grid.Row="3" Grid.Column="1"/>
<Button Content="Add" Grid.Row="4" Grid.Column="0" Width="60" Height="30" Grid.ColumnSpan="2"
Command="{Binding Path=AddCommand}"/>
<ListBox Grid.Column="2" Grid.RowSpan="4" Margin="5" Background="LightCyan"
ItemsSource="{Binding Path=Persons}" SelectedItem="{Binding Path=SelectedPerson}" DisplayMemberPath="FName" >
</ListBox>
<Button Content="Remove" Grid.Row="4" Grid.Column="2" Width="60" Height="30"
Command="{Binding Path=RemoveCommand}"
/>
</Grid>
</Window>
|
Points to remember:
1. Model class should not contain the instance of either ViewModel or View.
2. ViewModel should not contain the instance of View.
3. Try to eliminate the code from the codebehind files.