In my application, I am generating a datagrid programatically and binding it with a list. I am able to see the data in the datagrid but when I edit the cell, the underlying item in the list does not get updated. Here is the code
Window dateChangeWindow = new Window();
dateChangeWindow.WindowStartupLocation = WindowStartupLocation.CenterOwner;
dateChangeWindow.Owner = Application.Current.MainWindow;
dateChangeWindow.SizeToContent = SizeToContent.WidthAndHeight;
dateChangeWindow.Title = "Date Change";
StackPanel stackPanel = new StackPanel();
stackPanel.Orientation = Orientation.Vertical;
DataGrid requestGrid = new DataGrid();
requestGrid.CanUserResizeColumns = false;
requestGrid.CanUserResizeRows = false;
requestGrid.CanUserReorderColumns = false;
requestGrid.CanUserSortColumns = true;
requestGrid.AutoGenerateColumns = false;
DataGridTextColumn requestIdColumn = new DataGridTextColumn();
requestIdColumn.Header = "Request Id";
Binding idBinding = new Binding("RequestId");
idBinding.Mode = BindingMode.OneWay;
requestIdColumn.Binding = idBinding;
requestGrid.Columns.Add(requestIdColumn);
DataGridTemplateColumn startDateColumn = new DataGridTemplateColumn();
startDateColumn.Header = "Start Date";
Binding startDateBinding = new Binding("StartDate");
startDateBinding.Mode = BindingMode.TwoWay;
FrameworkElementFactory startDateFactory = new FrameworkElementFactory(typeof(DatePicker));
startDateFactory.SetBinding(DatePicker.SelectedDateProperty, startDateBinding);
DataTemplate startDateTemplate = new DataTemplate();
startDateTemplate.VisualTree = startDateFactory;
startDateColumn.CellTemplate = startDateTemplate;
startDateColumn.CellEditingTemplate = startDateTemplate;
requestGrid.Columns.Add(startDateColumn);
DataGridTemplateColumn endDateColumn = new DataGridTemplateColumn();
endDateColumn.Header = "End Date";
Binding endDateBinding = new Binding("EndDate");
endDateBinding.Mode = BindingMode.TwoWay;
FrameworkElementFactory endDateFactory = new FrameworkElementFactory(typeof(DatePicker));
endDateFactory.SetBinding(DatePicker.SelectedDateProperty, endDateBinding);
DataTemplate endDateTemplate = new DataTemplate();
endDateTemplate.VisualTree = endDateFactory;
endDateColumn.CellTemplate = endDateTemplate;
endDateColumn.CellEditingTemplate = endDateTemplate;
requestGrid.Columns.Add(endDateColumn);
requestGrid.ItemsSource = requestList;
requestGrid.Margin = new Thickness(0, 10, 0, 0);
requestGrid.HorizontalAlignment = HorizontalAlignment.Center;
stackPanel.Children.Add(requestGrid);
Button changeDoneBtn = new Button();
changeDoneBtn.Content = "Submit";
changeDoneBtn.Click += new RoutedEventHandler(changeDone_Click);
changeDoneBtn.Margin = new Thickness(0, 20, 0, 10);
changeDoneBtn.HorizontalAlignment = HorizontalAlignment.Center;
stackPanel.Children.Add(changeDoneBtn);
dateChangeWindow.Content = stackPanel;
dateChangeWindow.ShowDialog();
The ItemsSource requestList is populated before the window creation. It is declared as
IList<DateChangeWrapper> requestList = new List<DateChangeWrapper>();
And the DateChangeWrapper class looks like this
public class DateChangeWrapper : INotifyPropertyChanged
{
public DateChangeWrapper(ResponseWrapper responseWrapper)
{
RequestId = responseWrapper.RequestId;
ParentRequestId = responseWrapper.ParentRequestId;
StartDate = responseWrapper.StartDate;
EndDate = responseWrapper.EndDate;
}
private DateTime startDate;
private DateTime endDate;
public int RequestId { get; private set; }
public int ParentRequestId { get; private set; }
public DateTime StartDate
{
get { return startDate; }
set
{
startDate = value;
OnPropertyChanged("StartDate");
}
}
public DateTime EndDate
{
get { return endDate; }
set
{
endDate = value;
OnPropertyChanged("EndDate");
}
}
public event PropertyChangedEventHandler PropertyChanged;
private void OnPropertyChanged(string propertyName)
{
PropertyChangedEventHandler handler = PropertyChanged;
if (handler != null)
{
var e = new PropertyChangedEventArgs(propertyName);
handler(this, e);
}
}
}
As you can see from the code, I have two columns StartDate and EndDate which are displayed as DatePickers . When I debug the code, the point where window.ShowDialog is called, I see the get accessor of the Dates getting called. But when I change the value in the datepicker, the setter does not get called and my list still has the old value.
Please help me
The problem was that the changed value was not getting updated back to the underlying source because of UpdateSourceTrigger. By default, this has the value of LostFocus. I changed it to PropertyChanged and it worked ! 🙂
I added the following line of code to my binding
and similarly for EndDate