views:

86

answers:

3

I have a DataGridView that has MultiSelect turned on. When the SelectionChanged event is fired, I'd like to know what items were newly selected and which items were newly deselected. For instance, if you have multiple items selected (by Ctrl-clicking) and then you release the Ctrl key and select a single item, I'd like to know which items were deselected. I could keep track of the previous selected items collection, but I just wanted to make sure I wasn't thinking too hard.

+1  A: 

That information should be in the event arguments.

Use the RowStateChanged event. the DataGridViewRowStateChangedEventArgs will contain the row that was clicked. If a user selects/deselects multiple rows, the event will be called once for each row selected/deselected.

e.Row.Selected will yield whether the row is now selected or deselected.

md5sum
+1 I think this is the best solution
0A0D
+1  A: 

The event does not tell you exactly which things changed. If you need to know for some reason, you will have to keep track of the previous selection.

What are you trying to do in response to this event? There may be a much easier way to accomplish your real goal.

Auraseer
I wish there were an easier way. My business object needs to maintain selections of items. Binding would make things easier but unfortunately I haven't figured out how to bind what I have. My DataGridView is actually a custom TreeGridView which is a DataGridView behind the scenes. My TreeGridView contains 3 layers of collections, each of which are a different type. So I have reverted to refreshing the data in the grid in a more manual way.
bsh152s
Whoops, I appear to be wrong here. The control has another event that can give the information you want. See md5sum's answer about the RowStateChanged event.
Auraseer
A: 

This information is not inherently available for a DataGridView. However you could write a wrapper around the DataGridView which provides this information.

public static void OnSelectionChanged(
  this DataGridView view,
  Action<List<DataGridViewRow>,List<DataGridViewRow>> handler) {
  var oldSelection = view.SelecetedRows.Cast<DataGridViewRow>.ToList();
  view.SelectedChanged += (sender,e)  {
    var newSelection = view.SelectedRows.Cast<DataGridViewRow>.ToList();
    handler(oldSelection,newSelection);
    oldSelection = newSelection;
  };
}

Use Case

void HandleSelectionChanged(List<DataGridViewRow> oldRows, List<DataGridViewRow> newRows) {
  ..
}

void FormLoaded() {
  myDataGridView.OnSelectionChanged(HandleSelectionChanged);
}
JaredPar