Creating simple WPF MVVM application
I am taking example of Address book application.
Create View, Model and ViewModel folders in WPF project.
Let’s start with Model, here I am adding AddressBook Model which
inherits INotifyPropertyChanged Interface.
Also I have added required implementation for INotifyPropertyChanged
Interface in AddressBook Model. You can see complete AddressBookModel code
below.
Next, create properties. Properties like Name, PhoneNumber
and Email Property are created. You can see complete code below.
public class AddressBookModel:INotifyPropertyChanged
{
public event PropertyChangedEventHandler PropertyChanged;
protected void OnPropertyChanged(string propName)
{
if (PropertyChanged != null)
{
PropertyChanged(this, new PropertyChangedEventArgs(propName));
}
}
private string name = string.Empty;
private string phoneNumber = string.Empty;
private string email = string.Empty;
public string Name
{
get
{
return name;
}
set
{
name = value;
OnPropertyChanged("Name");
}
}
public string PhoneNumber
{
get
{
return phoneNumber;
}
set
{
phoneNumber = value;
OnPropertyChanged("PhoneNumber");
}
}
public string Email
{
get
{
return email;
}
set
{
email = value;
OnPropertyChanged("Email");
}
}
}
One more class is created called ViewModelBase. In that some
common functionality is implemented this can be reused later. This class
inherits INotifyPropertyChanged interface.
Further I have created ViewModel inside which
AddressBookViewModel is created.
public class ViewModelBase:INotifyPropertyChanged
{
public event PropertyChangedEventHandler PropertyChanged;
protected void OnPropertyChanged(string propName)
{
if(PropertyChanged!=null)
{
PropertyChanged(this, new PropertyChangedEventArgs(propName));
}
}
}
ViewModelBase class is inherited in AddressBookViewModel
class to reuse PropertyChanged functionality notification
Note: Same
ViewModelBase class can be used in Model Class.
Properties are created in ViewModelBase class to bind view
UI elements.
Next create new Window in view folder. Name it as AddressBookView.
In this view some simple design is created.
<Window x:Class="SimpleWPFApplicaiton.View.AddressBookView"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="Address
Book" Height="300" Width="300">
<Grid Background="AliceBlue">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="100*"/>
<ColumnDefinition Width="100*"/>
</Grid.ColumnDefinitions>
<Grid.RowDefinitions>
<RowDefinition Height="40"/>
<RowDefinition Height="40"/>
<RowDefinition Height="40"/>
<RowDefinition Height="40"/>
<RowDefinition Height="40*"/>
</Grid.RowDefinitions>
<TextBlock Grid.Column="0" Grid.Row="0">Name</TextBlock>
<TextBlock Grid.Column="0" Grid.Row="1">Email</TextBlock>
<TextBlock Grid.Column="0" Grid.Row="2">Phone
Number</TextBlock>
<TextBox Grid.Column="1" Grid.Row="0" Margin="5"></TextBox>
<TextBox Grid.Column="1" Grid.Row="1" Margin="5"></TextBox>
<TextBox Grid.Column="1" Grid.Row="2" Margin="5"></TextBox>
<Button Grid.Column="1" Grid.Row="3" Margin="5" Width="100"
HorizontalAlignment="Right">Add</Button>
</Grid>
</Window>
Here I am using MVVM approach,
to do loosely couple binding
for events.
Create custom command class. Let’s name it as RelayCommand and place this in
new folder called Helpers. This class inherits ICommand interface to get
ICommand feature implementation.
Complete code of RelayCommand as follows.
public class RelayCommand:ICommand
{
readonly Action<object> _execute;
readonly Predicate<object> _canExecute;
public RelayCommand(Action<object> execute)
: this(execute, null)
{
}
public RelayCommand(Action<object> execute, Predicate<object> canExecute)
{
if (execute == null)
throw new ArgumentNullException("execute");
_execute = execute;
_canExecute = canExecute;
}
public bool CanExecute(object parameter)
{
return _canExecute == null ? true : _canExecute(parameter);
}
public event EventHandler CanExecuteChanged
{
add { CommandManager.RequerySuggested += value; }
remove { CommandManager.RequerySuggested -= value; }
}
public void Execute(object parameter)
{
_execute(parameter);
}
}
Again go to AddressBookViewModel class. You can write
commands. In my sample application I have created AddCommand.
public class AddressBookViewModel : ViewModelBase
{
private RelayCommand addCommand;
private string name = string.Empty;
private string phoneNumber = string.Empty;
private string email = string.Empty;
public ICommand AddCommand
{
get
{
if (addCommand == null)
{
addCommand = new RelayCommand(Add);
}
return addCommand;
}
}
private void Add(object obj)
{
//Logic
here to add records
}
public string Name
{
get
{
return name;
}
set
{
name = value;
OnPropertyChanged("Name");
}
}
public string PhoneNumber
{
get
{
return phoneNumber;
}
set
{
phoneNumber = value;
OnPropertyChanged("PhoneNumber");
}
}
public string Email
{
get
{
return email;
}
set
{
email = value;
OnPropertyChanged("Email");
}
}
}
Further we need to bind this ModelView to View.
Using below line we will get reference of view model
xmlns:viewModel="clr-namespace:SimpleWPFApplicaiton.ViewModel"
Next, create key to get access to above view model. By this
key you can bind to UI elements.
In below code you can see few changes related to binding.
<Window x:Class="SimpleWPFApplicaiton.View.AddressBookView"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:viewModel="clr-namespace:SimpleWPFApplicaiton.ViewModel"
Title="Address
Book" Height="300" Width="300">
<Window.Resources>
<viewModel:AddressBookViewModel x:Key="AddressBookVM"/>
</Window.Resources>
<Grid Background="AliceBlue"
DataContext="{StaticResource AddressBookVM}">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="100*"/>
<ColumnDefinition Width="100*"/>
</Grid.ColumnDefinitions>
<Grid.RowDefinitions>
<RowDefinition Height="40"/>
<RowDefinition Height="40"/>
<RowDefinition Height="40"/>
<RowDefinition Height="40"/>
<RowDefinition Height="40*"/>
</Grid.RowDefinitions>
<TextBlock Grid.Column="0" Grid.Row="0">Name</TextBlock>
<TextBlock Grid.Column="0" Grid.Row="1">Email</TextBlock>
<TextBlock Grid.Column="0" Grid.Row="2">Phone
Number</TextBlock>
<TextBox Grid.Column="1" Grid.Row="0" Margin="5" Text="{Binding Name}" ></TextBox>
<TextBox Grid.Column="1" Grid.Row="1" Margin="5" Text="{Binding Email}" ></TextBox>
<TextBox Grid.Column="1" Grid.Row="2" Margin="5" Text="{Binding PhoneNumber}"
></TextBox>
<Button Grid.Column="1" Grid.Row="3" Margin="5" Width="100"
HorizontalAlignment="Right" Command="{Binding AddCommand}" >Add</Button>
</Grid>
</Window>
Now inside ViewModel, in Add method you can implement logic
which you required.
Before running the application set start of window to AddressBookView.
Hope this will help you...:)
Comments and suggestions are welcome J