views:

655

answers:

2

In VB .Net 3.5, is it possible to change the color of a DataGridViewCell (unbound) to a different color and have the cell visibly change before losing focus or leaving the cell? I have a timer that's running that queries with the data present and I'd like for the colors to change immediately instead of after the user leaves the cell.

I've tried DataGridView.Refresh and Me.Refresh and don't get results.

What am I doing wrong? (Below is the code I use to change the background)

''' <summary>
''' Sets or clears the passed cells background to Red
''' </summary>
''' <param name="ColumnNumber">Datagridview column index of the cell to be changed</param>
''' <param name="RowNumber">Datagridview row index of the cell to be changed</param>
''' <param name="Error">Indicate whether the cell should be red, <c>True</c>, or empty, <c>False</c></param>
Private Sub Error_Cell(ByVal ColumnNumber As Integer, ByVal RowNumber As Integer, ByVal [Error] As Boolean)
    If [Error] Then
        Me.dgvMain.Rows(RowNumber).Cells(ColumnNumber).Style.BackColor = Color.Red
    Else
        Me.dgvMain.Rows(RowNumber).Cells(ColumnNumber).Style.BackColor = Color.Empty
    End If
    Me.dgvMain.Refresh()
    Me.Refresh()
End Sub
A: 

First you have to explain yourself when the row will be painted with diferent color, for example in my case (when users clicks on a CheckBoxCell) Then, Try using diferents events like CellLeave or CellContentClick (as my example) : Last, play with code!

void updateCellStyle_DataGridViewCellEventArgs(object sender, DataGridViewCellEventArgs e){
int index = e.RowIndex;
if (index == -1)
 return;
else {
DataGridView dgv = sender as DataGridView;
int vCHK = e.ColumnIndex; //this is the checkbox column
if (vCHK != 0)
 return;
else {
 DataGridViewCheckBoxCell temp = (DataGridViewCheckBoxCell)dgv.Rows[index].Cells[0];
 if ((bool)temp.EditedFormattedValue == true) {
DataGridViewTextBoxCell xrow = (DataGridViewTextBoxCell)dgv.Rows[index].Cells[3];
xrow.OwningRow.DefaultCellStyle.BackColor = Color.Wheat;
 /*
 other operations 
 */
 }
 else {
 temp.OwningRow.DefaultCellStyle.BackColor = Color.White;
 /*
 other operations 
 */
 }
Angel Escobedo
I'm painting the row a different color when the user inputs an invalid part number. Before they move on to anything else, the cell should change colors to inform them that they aren't using the right part.I've been playing with this for a few days on and off, so I figured I'd ask you guys.
Stevoni
A: 

I decided that only the current cells background color need to change and began using the EditControl of the DataGridViewCell.

In order to capture this, I had to grab the EditControl (Type DataGridViewTextBoxEditingContorl) on the DataGridView event "EditControlShowing" and associate the cells EditControl with a local form variable, then add a handler to the TextChagned event (since the Cells TextChanged doesn't occur until after editing is complete). (First procedure).

After doing so, I'm able to change the color of the cell by changing the EditControls BackColor, which is changed immediately. (Second procedure)

I have to release the EditControl on the DataGridViews CellEndEdit event in order to re-use my private variable. (Third procedure)

I haven't tested attempting to change the row, due to a change in usage, but it seems to work just fine. I hope this helps anyone with a similar issue. If there are more efficient ways of doing this, please let me know!

Private EditingControl As DataGridViewTextBoxEditingControl

Private Sub dgvMain_EditingControlShowing(ByVal sender As Object, ByVal e As System.Windows.Forms.DataGridViewEditingControlShowingEventArgs) Handles dgvMain.EditingControlShowing
    If TypeOf (e.Control) Is DataGridViewTextBoxEditingControl Then
        EditingControl = DirectCast(e.Control, DataGridViewTextBoxEditingControl)
        If DirectCast(e.Control, DataGridViewTextBoxEditingControl).EditingControlDataGridView.CurrentCell.OwningColumn Is PartNumber Then
            AddHandler EditingControl.TextChanged, AddressOf EditingControl_TextChanged
        End If
    End If
End Sub

Private Sub Error_Cell(ByVal [Error] As Boolean)
    If [Error] Then
        If EditingControl IsNot Nothing Then EditingControl.BackColor = Color.Red
    Else
        If EditingControl IsNot Nothing Then EditingControl.BackColor = Color.Empty
    End If
    Me.dgvMain.Refresh()
End Sub



Private Sub dgvMain_CellEndEdit(ByVal sender As Object, ByVal e As System.Windows.Forms.DataGridViewCellEventArgs) Handles dgvMain.CellEndEdit
    If EditingControl IsNot Nothing Then
        RemoveHandler EditingControl.TextChanged, AddressOf EditingControl_TextChanged
    End If

    EditingControl = Nothing

End Sub

Note: A lot of the steps that I have inside of the If/Then's have been removed to protect the innocent, otherwise, they would be inline when possible.

Stevoni