Tuesday, 19 June 2012

WPF DataGrid change cell style based on underlying data object

XAML

<Window x:Class="DataGridCellBackground.MainWindow"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" 
    xmlns:DataGridCellBackground="clr-namespace:DataGridCellBackground"
    Title="MainWindow" Height="350" Width="525"
    DataContext="{Binding RelativeSource={RelativeSource Self}}">
  <Window.Resources>
    <DataGridCellBackground:DataGridCellBackgroundConverter x:Key="dataGridCellBackgroundConverter"/>
  </Window.Resources>
  <Grid>    
    <DataGrid ItemsSource="{Binding Data}" Width="400" Height="200">
      <DataGrid.CellStyle>
        <Style TargetType="{x:Type DataGridCell}">
          <Setter Property="Background">
            <Setter.Value>
              <MultiBinding Converter="{StaticResource dataGridCellBackgroundConverter}" >
                <MultiBinding.Bindings>
                  <Binding RelativeSource="{RelativeSource Self}"></Binding>
                  <Binding Path="Row"></Binding>
                </MultiBinding.Bindings>
              </MultiBinding>
            </Setter.Value>
          </Setter>
        </Style>
      </DataGrid.CellStyle>
    </DataGrid>    
  </Grid>
</Window>

Code Behind

namespace DataGridCellBackground
{
  public partial class MainWindow : Window
  {
    public MainWindow()
    {           
      InitializeComponent();      
    }
    public DataTable Data { 
    get{
      var data = new DataTable();
      data.Columns.Add("Text", typeof(string));
      data.Columns.Add("Value", typeof(ComplexValue));
      var row = data.NewRow();
      row["Text"] = "First";
      row["Value"] = new ComplexValue() { Value = 1, Checked = true };
      data.Rows.Add(row);
      row = data.NewRow();
      row["Text"] = "Second";
      row["Value"] = new ComplexValue() { Value = 2, Checked = false };
      data.Rows.Add(row);
      row = data.NewRow();
      row["Text"] = "Third";
      row["Value"] = new ComplexValue() { Value = 3, Checked = true };
      data.Rows.Add(row);
      return data;
    }
    } 
    public class ComplexValue
    {
    public int Value { get; set; }
    public bool Checked { get; set; }
    //required for default template
    public override string ToString()
    {
      return Value.ToString();
    }
    }
  }
  public class DataGridCellBackgroundConverter : IMultiValueConverter
  {
    public object Convert(object[] values, Type targetType, object parameter, CultureInfo culture)
    {
    if (values[1] is DataRow)
    {                
      var cell = (DataGridCell)values[0];
      var row = (DataRow)values[1];
      var columnName = cell.Column.SortMemberPath;
      var value = row[columnName];
      if (value is MainWindow.ComplexValue)
      {
      if((value as MainWindow.ComplexValue).Checked)
      {
        return new SolidColorBrush(Colors.LightGreen);
      }
      }
    }
    return SystemColors.AppWorkspaceColor;
    }
    public object[] ConvertBack(object value, Type[] targetTypes, object parameter, CultureInfo culture)
    {
    throw new System.NotImplementedException();
    }
  }
}

No comments:

Post a Comment