Search code examples
c#wpfdatagridselecteditem

Unable to select multiple rows in a WPF DataGrid


Even though I've got SelectionMode="Extended" and SelectionUnit="FullRow" set, when I debug the SelectionChanged event, there's always only one selected item in SelectedItems.

This is my DataGrid:

<DataGrid Grid.Row="0" AutoGenerateColumns="False" Margin="5,5,5,0"
        Name="dgrMembersClub1" ItemsSource="{Binding .}" CanUserAddRows="False"
        SelectionMode="Extended" SelectionUnit="FullRow" SelectionChanged="Grid_SelectionChanged">
    <DataGrid.Columns>
        <DataGridTemplateColumn Header="Joining" >
            <DataGridTemplateColumn.CellTemplate>
                <DataTemplate>
                    <CheckBox IsChecked="{Binding IsSelected}"/>
                </DataTemplate>
            </DataGridTemplateColumn.CellTemplate>
        </DataGridTemplateColumn>
        <DataGridTextColumn IsReadOnly="True" Header="Surname" Binding="{Binding Surname}" />
        <DataGridTextColumn IsReadOnly="True" Header="Name" Binding="{Binding Name}" />
        <DataGridTextColumn IsReadOnly="True" Header="Club" Binding="{Binding Club_Id, Converter={StaticResource ClubName}}" />
        <DataGridTextColumn IsReadOnly="True" Header="City" Binding="{Binding City}" />
    </DataGrid.Columns>
</DataGrid>

And my Grid_SelectionChanged event:

private void Grid_SelectionChanged(object sender, SelectionChangedEventArgs e)
{
    DataGrid grid = (DataGrid)sender;
    var test = grid.SelectedItems; //Count == 1 (always)
}

I do have Triggers set (in App.xaml) that change the background and foreground brushes for selected and alternating rows. If that's relevant, please let me know and I'll add the code.

* EDIT *

While you're at it, I could use some help getting the checkbox in the cell template to work too. Pretty please :)


Solution

  • The SelectedItems property of the DataGrid contains a list of, well, selected items...

    private void DataGrid_SelectionChanged(object sender,
        SelectionChangedEventArgs e)
    {
        // ... Get SelectedItems from DataGrid.
        var grid = sender as DataGrid;
        var selected = grid.SelectedItems;
    
        foreach (var item in selected)
        {
            var dog = item as Dog;
        }
    }
    

    This indicative event handler gets the SelectedItems and loops through it.

    However, there's a caveat:

    "If the SelectionMode property is set to Single, the SelectedItems list will contain only the SelectedItem property value."

    Source: http://msdn.microsoft.com/en-us/library/system.windows.controls.datagrid.selecteditems(v=vs.95).aspx

    The SelectedItems property inherits from IList so it is possible to cast it and perform LINQ operations on it as well. It also works fine with non-contiguous selections.

    More tips at http://www.dotnetperls.com/datagrid