How to change a single datagrid row FontWeights to

2019-08-09 05:07发布

问题:

When a row is selected in my datagrid and a button is pressed, I want to change the FontWeight of the cells in that row to bold.

I've been looking for a way to do it, but all I can do is change the style of every columns, I can't find a way to get the selected row (or any rows for that matter).

There are no specific values that I can bind to from the ItemSource type, so a solution using XAML and a ValueConverter is unwanted due to the increased complexity. That is, unless it's the only way.

This is how I'm proceeding:

 <DataGrid Name="dgSessions" Width="200" Height="100" 
                          CanUserAddRows="False" CanUserDeleteRows="False" 
                          HeadersVisibility="None" GridLinesVisibility="None" AutoGenerateColumns="False"
                          SelectionMode="Single" Background="White">
                    <DataGrid.Columns>
                        <DataGridTextColumn Width="*" Binding="{Binding Path=Name}"></DataGridTextColumn>
                    </DataGrid.Columns>
                    <DataGrid.CellStyle>
                        <Style TargetType="{x:Type DataGridCell}">
                            <Style.Setters>
                                <Setter Property="FontWeight"
                                        Value="Normal"/>
                            </Style.Setters>
                        </Style>
                    </DataGrid.CellStyle>
  </DataGrid>


        private void btnConnect_Click(object sender, RoutedEventArgs e)
    {
        Style oldStyle = dgSessions.SelectedCells.First().Column.CellStyle;
        Setter setter = null;
        foreach (Setter item in oldStyle.Setters)
        {
            if (item.Property.Name == "FontWeight")
            {
                setter = new Setter(item.Property, FontWeights.Bold, item.TargetName);
                break;
            }
        }
        Style newStyle = new Style(oldStyle.TargetType);
        newStyle.Setters.Add(setter);
        dgSessions.SelectedCells.First().Column.CellStyle = newStyle;


    }

回答1:

You can define the DataGridRow style as below and on button click set the property to trigger a notification to apply the FontWeight on the Row

<Style x:Key="MyRowStyle" TargetType="DataGridRow">
    <Setter Property="FontWeight" Value="Normal"/>
    <Style.Triggers>
        <DataTrigger Binding="{Binding IsProcessed}" Value="True">
            <Setter Property="FontWeight" Value="Bold"/>
        </DataTrigger>
    </Style.Triggers>
</Style>

The DataGrid will be defined as

<DataGrid RowStyle="{StaticResource MyRowStyle}" ...... />

Now to integrate it, you have to define property in the model which is bound to ItemSource of DataGrid (The model should implement INotifyPropertyChanged interface). On button click, set the property defined in model and bound in DataTrigger

private void btnConnect_Click(object sender, RoutedEventArgs e)
{
     var dataContext = btnConnect.DataContext as <<Your Model>>;
     dataContext.IsProcessed = true;
}


回答2:

Turns out, you can get a row of a datagrid like that:

DataGridRow row = (DataGridRow)myDataGrid.ItemContainerGenerator.ContainerFromIndex(myIndex);

There is also a different method to get a row from an Item.

So I did the following to set the row I want in bold:

  1. Retrieve the index with int index = myObservableCollection.IndexOf(myObject) I don't think the index is always valid if you have a lot of rows and virtualization is enabled, but given my context, it's fine.

  2. Create my Setter

    Setter bold = new Setter(TextBlock.FontWeightProperty, FontWeights.Bold, null);
    
  3. Get my row:

    DataGridRow row = (DataGridRow)dgSessions.ItemContainerGenerator.ContainerFromIndex(index);
    
  4. Create Style and set it:

        Style newStyle = new Style(row.GetType());
    
        newStyle.Setters.Add(bold);
        row.Style = newStyle;