Conditional Row Background Color – DataGridView

I spend 3 or 4 hours trying to figure out the best way to implement conditional row background colors in DataGridView, so I thought I would share my findings.

Background:

I have an application that uses DataGridView. I want to be able change the BackColor property of a row, based the status of an Item; New, Match or Neither. I also have a few columns that have their own unique BackColor. I want to preserve the column BackColor when an Item is neither New or Match. This turned out to be the hard part of the problem. When an Item changed from New to Neither, all the columns would work correctly execpt for the columns that had their own BackColor.

Considerations:

  1. Where/When do we assign the row color? When an item changes? When the row is painted? I decided to assign a BackColor when the row is painted (RowPrePaint event). I have large datasets that change in large chunks. Changing when the item changes really made the screen flicker.
  2. How do we preserve the column background color when we “unhighlight” the row? It took me a while to figure this one out. It turns out that if you assign the Row.DefaultCellStyle.BackColor to Color.Empty then the orginal column colors will be displayed correctly.

Problems:

  1. Under specific conditions the screen will still flicker while items are updating. I have not found away around this problem yet.
  2. Calcuations are preformed everytime a row is painted. This does not seem to be a problem in my application, but it might be a source of concern in another.

Here is a look at the code in am currently using to complete this task. If anyone has a better way of solving this problem, please let me know.
Code that implements conditional row background color.

Advertisements

5 Responses

  1. Here’s a potentially easier-to-understand way:

    private void OnDataCellFormatting(object sender, DataGridViewCellFormattingEventArgs e)
    {
    int row = e.RowIndex;
    if (row == 3) //

  2. Are you saying to use the OnDataCellFormatting event?

    If so, I will have to try that and see what the pros /cons are for that approach.

  3. I don’t know if it will work in your case but I’m doing something like this for custom coloring:

    protected override void OnCellFormatting (DataGridViewCellFormattingEventArgs e)
    {
    base.OnCellFormatting(e);

    e.CellStyle.ForeColor = Color.Red;
    e.FormattingApplied = true;
    }

    Don’t forget to do the “e.FormatApplied” thing. I spent hours to discover that.

  4. private void dataGrid_CellFormatting(object sender, DataGridViewCellFormattingEventArgs e)
    {
    int rowIndex = e.RowIndex;
    DataGridViewRow theRow = dataGrid.Rows[rowIndex];

    double cellValue = (double)theRow.Cells[“Quantity”].Value;
    if (cellValue > 50)
    {
    theRow.DefaultCellStyle.BackColor = Color.Red;
    }
    else
    {
    // theRow.DefaultCellStyle.BackColor = Color.Blue;
    }
    }

  5. Hi, I think you can use
    this.datagrid1.RowsAdded += new System.Windows.Forms.DataGridViewRowsAddedEventHandler

    event hendler. so it will be only once. dataGrid_CellFormatting gets called for each cell and every time when you datagrid gets painted.
    that may be performance issue if you have so many rows.

    I suggest take decision while you are adding row.

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s