Hi there,

I have a question regarding datagridview in C#. I have done the validateion for the datagridview in the cellvalidating event. And for the error message to display in the specific cell that the validation is done I have to click on another place for the error message to display.
How can I make it when the datagridview value cell value is selected and then the error message display and the cursor is focused in to the same cell.

How can I do this…
thnxxxxxx

I must agree with you on how the Validation events operate. I also do not like that the user must begin to move away from the control before validation occurs.

However, you can block the move so the focus remains on the current control (cell) by setting the Cancel property to True on the CancelEventArg parameter. That said, I prefer to use the ValueChanged event (CellValueChanged for DGV) to do my validation.

If I need the user to have time to complete the entry, then I sometimes include a timer that is (re-)started on each ValueChanged and executes the validation a short time later.

DataGridCell validationCell;
        private void dataGridView1_CellValueChanged(object sender, DataGridViewCellEventArgs e)
        {
            switch (e.ColumnIndex)
            {
                case 1:
                    // col 1 validation
                    break;
                case 2:
                case 3: // column 2 and 3 require manual entry 
                    // capture changed cell
                    validationCell = dataGridView1[e.ColumnIndex, e.RowIndex];
                    // give user time to finish entry before validating
                    timer1.Enabled = true;
                    break;
                default:
                    break;
            }
        }

        // validation timer set to (250 ms ish)
        private void timer1_Tick(object sender, EventArgs e)
        {
            if (validationCell != null)
            { 
                // do cell validation here
                validationCell = null;
            }
            timer1.Enabled = false;
        }

I generally prefer to prevent the user from entering an invalid value by always using Combos, UpDown number thingies with max min set, etc. so there is never any chance of an invalid entry in the first place. (Not always possible with DGV however).
Hope this helps. :)

Edited 6 Years Ago by nick.crane: Made timer start stop consisant

I must agree with you on how the Validation events operate. I also do not like that the user must begin to move away from the control before validation occurs.

However, you can block the move so the focus remains on the current control (cell) by setting the Cancel property to True on the CancelEventArg parameter. That said, I prefer to use the ValueChanged event (CellValueChanged for DGV) to do my validation.

If I need the user to have time to complete the entry, then I sometimes include a timer that is (re-)started on each ValueChanged and executes the validation a short time later.

DataGridCell validationCell;
        private void dataGridView1_CellValueChanged(object sender, DataGridViewCellEventArgs e)
        {
            switch (e.ColumnIndex)
            {
                case 1:
                    // col 1 validation
                    break;
                case 2:
                case 3: // column 2 and 3 require manual entry 
                    // capture changed cell
                    validationCell = dataGridView1[e.ColumnIndex, e.RowIndex];
                    // give user time to finish entry before validating
                    timer1.Enabled = true;
                    break;
                default:
                    break;
            }
        }

        // validation timer set to (250 ms ish)
        private void timer1_Tick(object sender, EventArgs e)
        {
            if (validationCell != null)
            { 
                // do cell validation here
                validationCell = null;
            }
            timer1.Enabled = false;
        }

I generally prefer to prevent the user from entering an invalid value by always using Combos, UpDown number thingies with max min set, etc. so there is never any chance of an invalid entry in the first place. (Not always possible with DGV however).
Hope this helps. :)

hey,

i am validating the calender column in the datagridview cell.how can i make it so that the user can't select a date that has passed???

like in the datetime picker as " dpSdate.MinDate = DateTime.Today;"

is there any way for this in the datagridview cell fro the calender column

thanxxxxxx

I know you have been looking at this for ages and asked for a solution more than once so I am just going to give you the code.:)
OK. You can capture the editing control in the EditingControlShowing event and set the max and min properties there.

private void dataGridView1_EditingControlShowing(object sender, DataGridViewEditingControlShowingEventArgs e)
        {
            if (dataGridView1.CurrentCell.RowIndex > 2) // or some other condition (eg ColumnIndex == 3)
            {
                CalendarEditingControl ctrl = e.Control as CalendarEditingControl;
                if (ctrl != null)
                {
                    // set limits for date - note this will force Value to limits if invalid.
                    ctrl.MaxDate = someMaxDate; // set required value for max
                    ctrl.MinDate = someMinDate; // set required value for min
                }
            }
        }

However I found that if I set different limits for each row then an error sometimes occurs when moving to edit another row.:confused:
You will also need to modify the CalendarCell.InitializeEditingControl. Add the following before the if (this.Value == null)

ctl.MaxDate = DateTimePicker.MaximumDateTime;
            ctl.MinDate = DateTimePicker.MinimumDateTime;

This is to ensure the limits are OK before the value is set and prevents an ArgumentOutOfRange error.

Hope this helps.

I know you have been looking at this for ages and asked for a solution more than once so I am just going to give you the code.:)
OK. You can capture the editing control in the EditingControlShowing event and set the max and min properties there.

private void dataGridView1_EditingControlShowing(object sender, DataGridViewEditingControlShowingEventArgs e)
        {
            if (dataGridView1.CurrentCell.RowIndex > 2) // or some other condition (eg ColumnIndex == 3)
            {
                CalendarEditingControl ctrl = e.Control as CalendarEditingControl;
                if (ctrl != null)
                {
                    // set limits for date - note this will force Value to limits if invalid.
                    ctrl.MaxDate = someMaxDate; // set required value for max
                    ctrl.MinDate = someMinDate; // set required value for min
                }
            }
        }

However I found that if I set different limits for each row then an error sometimes occurs when moving to edit another row.:confused:
You will also need to modify the CalendarCell.InitializeEditingControl. Add the following before the if (this.Value == null)

ctl.MaxDate = DateTimePicker.MaximumDateTime;
            ctl.MinDate = DateTimePicker.MinimumDateTime;

This is to ensure the limits are OK before the value is set and prevents an ArgumentOutOfRange error.

Hope this helps.

hey i didn't understand what u where saying in the lasy bit which is quoted below

"

However I found that if I set different limits for each row then an error sometimes occurs when moving to edit another row.
You will also need to modify the CalendarCell.InitializeEditingControl. Add the following before the if (this.Value == null)
C# Syntax (Toggle Plain Text)

   1.
      ctl.MaxDate = DateTimePicker.MaximumDateTime;
   2.
      ctl.MinDate = DateTimePicker.MinimumDateTime;

ctl.MaxDate = DateTimePicker.MaximumDateTime; ctl.MinDate = DateTimePicker.MinimumDateTime;
This is to ensure the limits are OK before the value is set and prevents an ArgumentOutOfRange error.

"

Take a look at the DGV CalendarColumn code.
In there is a class called CalendarCell.
In this class is a method called InitialiseEditingControl.
In this method there is line that is if (this.Value == null) .
Add the two new lines of code before this if statement.

This article has been dead for over six months. Start a new discussion instead.