Windows Develop Bookmark and Share   
 index > Windows Forms Data Controls and Databinding > how restrict users from setting focus to multiple cells in DataGridView
 

how restrict users from setting focus to multiple cells in DataGridView

I read an article on Msdn about how to restrict users from setting focus to a specific cell in DataGridView , and I understood how it work , but what really I need to now is how to restrict users form set focus to a multiple cells and especially if two cells are exactly adjacent
for example if I have 4 columns in a DataGridView and and the columns to skip are 2nd and 3rd , so how can i do that
alladeen88  Saturday, August 29, 2009 2:48 PM
Hi alladeen88,

This is the FAQ answer about How do I restrict users from setting focus to a specific cell?:
http://social.msdn.microsoft.com/forums/en-US/winformsdatacontrols/thread/a44622c0-74e1-463b-97b9-27b87513747e/#Faq1.

This is the modified code snippetaccording to your request:
    public class CellSkipDataGridView : DataGridView
    {
        private int columnSkipStart = -1;
        private int columnSkipCount = 1;

        //The start column index we want to skip.
        public int ColumnSkipStart
        {
            get { return columnSkipStart; }
            set { columnSkipStart = value; }
        }

        //The column count we want to skip.
        public int ColumnSkipCount
        {
            get { return columnSkipCount; }
            set { columnSkipCount = value; }
        }

        protected override bool SetCurrentCellAddressCore(int columnIndex, int rowIndex,
            bool setAnchorCellAddress, bool validateCurrentCell, bool throughMouseClick)
        {
            if (this.columnSkipStart != -1 && columnIndex >= this.columnSkipStart
                && columnIndex < (this.columnSkipStart + this.columnSkipCount))
            {
                int columnIndexSkipTo = columnIndex + this.columnSkipCount;
                if (columnIndexSkipTo > this.ColumnCount - 1)
                {
                    return base.SetCurrentCellAddressCore(0, rowIndex + 1,
                        setAnchorCellAddress, validateCurrentCell, throughMouseClick);
                }
                else
                {
                    if (this.ColumnCount != 0)
                    {
                        return base.SetCurrentCellAddressCore(columnIndexSkipTo, rowIndex,
                            setAnchorCellAddress, validateCurrentCell, throughMouseClick);
                    }
                }
            }

            return base.SetCurrentCellAddressCore(columnIndex, rowIndex,
                setAnchorCellAddress, validateCurrentCell, throughMouseClick);

        }

        protected override void SetSelectedCellCore(int columnIndex, int rowIndex, bool selected)
        {
            if (this.columnSkipStart != -1 && columnIndex >= this.columnSkipStart
                && columnIndex < (this.columnSkipStart + this.columnSkipCount))
            {
                int columnIndexSkipTo = columnIndex + this.columnSkipCount;
                if (columnIndexSkipTo > this.ColumnCount - 1)
                {
                    base.SetSelectedCellCore(0, rowIndex + 1, selected);
                }
                else
                {
                    if (this.ColumnCount != 0)
                    {
                        base.SetSelectedCellCore(columnIndexSkipTo, rowIndex, selected);
                    }
                }
            }
            else
            {
                base.SetSelectedCellCore(columnIndex, rowIndex, selected);
            }
        }
    }
This is a example shows how to use it:
this.cellSkipDataGridView1.ColumnSkipStart = 1;
this.cellSkipDataGridView1.ColumnSkipCount = 2;

Let me know ifthis helps.
Aland Li
Please mark the replies as answers if they help and unmark if they don't. This can be beneficial to other community members reading the thread.
Aland Li  Tuesday, September 01, 2009 10:47 AM
Thanks Aland Li
I take advatage from your code , but you assume that the Cells you want to pass over are exactly adjacent but this is not the case all times
since the Cells that I want to pass over will also be disabled I found a way to do that :
class MyDataGridView:DataGridView
   {       
       protected override bool ProcessDialogKey(Keys keyData)
       {        
           Keys key = (keyData & Keys.KeyCode);
                    
           if (key == Keys.Tab)
           {
               int col = this.CurrentCell.ColumnIndex + 1;
               for (; col < this.Columns.Count; col++)
               {
                   if (!this.Columns[col].ReadOnly)
                   { break; }
               }
               if (col < this.Columns.Count)
               {
                   this.CurrentCell = this.Rows[this.CurrentCell.RowIndex].Cells[col];
               }
               else
               {
                   if (this.CurrentCell.RowIndex != this.Rows.Count - 1)
                   {
                       for (col = 0; col <= this.CurrentCell.ColumnIndex; col++)
                       {
                           if (!this.Columns[col].ReadOnly)
                           {
                               break;
                           }
                       }
                       if (col <= this.CurrentCell.ColumnIndex)
                       {
                           this.CurrentCell = this.Rows[this.CurrentCell.RowIndex + 1].Cells[col];
                       }
                   }
               }
               return true;                  

           }
           return base.ProcessDialogKey(keyData);
       }
       protected override bool ProcessDataGridViewKey(KeyEventArgs e)
       {           
           if (e.KeyData == Keys.Tab)
           {
               int col = this.CurrentCell.ColumnIndex +1;
               for (; col < this.Columns.Count; col++)
               {
                   if (!this.Columns[col].ReadOnly)
                   { break; }
               }
               if (col < this.Columns.Count)
               {
                   this.CurrentCell = this.Rows[this.CurrentCell.RowIndex].Cells[col];
               }
               else
               {
                   if (this.CurrentCell.RowIndex != this.Rows.Count - 1)
                   {
                       for (col = 0; col <= this.CurrentCell.ColumnIndex; col++)
                       {
                           if (!this.Columns[col].ReadOnly)
                           {
                               break;
                           }
                       }
                       if (col <= this.CurrentCell.ColumnIndex)
                       {
                           this.CurrentCell = this.Rows[this.CurrentCell.RowIndex + 1].Cells[col];
                       }
                   }
               }
               return true; 
           }
           return base.ProcessDataGridViewKey(e);
       }       
   }

alladeen88  Sunday, September 06, 2009 10:03 PM
Hi alladeen88,

This is the FAQ answer about How do I restrict users from setting focus to a specific cell?:
http://social.msdn.microsoft.com/forums/en-US/winformsdatacontrols/thread/a44622c0-74e1-463b-97b9-27b87513747e/#Faq1.

This is the modified code snippetaccording to your request:
    public class CellSkipDataGridView : DataGridView
    {
        private int columnSkipStart = -1;
        private int columnSkipCount = 1;

        //The start column index we want to skip.
        public int ColumnSkipStart
        {
            get { return columnSkipStart; }
            set { columnSkipStart = value; }
        }

        //The column count we want to skip.
        public int ColumnSkipCount
        {
            get { return columnSkipCount; }
            set { columnSkipCount = value; }
        }

        protected override bool SetCurrentCellAddressCore(int columnIndex, int rowIndex,
            bool setAnchorCellAddress, bool validateCurrentCell, bool throughMouseClick)
        {
            if (this.columnSkipStart != -1 && columnIndex >= this.columnSkipStart
                && columnIndex < (this.columnSkipStart + this.columnSkipCount))
            {
                int columnIndexSkipTo = columnIndex + this.columnSkipCount;
                if (columnIndexSkipTo > this.ColumnCount - 1)
                {
                    return base.SetCurrentCellAddressCore(0, rowIndex + 1,
                        setAnchorCellAddress, validateCurrentCell, throughMouseClick);
                }
                else
                {
                    if (this.ColumnCount != 0)
                    {
                        return base.SetCurrentCellAddressCore(columnIndexSkipTo, rowIndex,
                            setAnchorCellAddress, validateCurrentCell, throughMouseClick);
                    }
                }
            }

            return base.SetCurrentCellAddressCore(columnIndex, rowIndex,
                setAnchorCellAddress, validateCurrentCell, throughMouseClick);

        }

        protected override void SetSelectedCellCore(int columnIndex, int rowIndex, bool selected)
        {
            if (this.columnSkipStart != -1 && columnIndex >= this.columnSkipStart
                && columnIndex < (this.columnSkipStart + this.columnSkipCount))
            {
                int columnIndexSkipTo = columnIndex + this.columnSkipCount;
                if (columnIndexSkipTo > this.ColumnCount - 1)
                {
                    base.SetSelectedCellCore(0, rowIndex + 1, selected);
                }
                else
                {
                    if (this.ColumnCount != 0)
                    {
                        base.SetSelectedCellCore(columnIndexSkipTo, rowIndex, selected);
                    }
                }
            }
            else
            {
                base.SetSelectedCellCore(columnIndex, rowIndex, selected);
            }
        }
    }
This is a example shows how to use it:
this.cellSkipDataGridView1.ColumnSkipStart = 1;
this.cellSkipDataGridView1.ColumnSkipCount = 2;

Let me know ifthis helps.
Aland Li
Please mark the replies as answers if they help and unmark if they don't. This can be beneficial to other community members reading the thread.
Aland Li  Tuesday, September 01, 2009 10:47 AM
Thanks Aland Li
I take advatage from your code , but you assume that the Cells you want to pass over are exactly adjacent but this is not the case all times
since the Cells that I want to pass over will also be disabled I found a way to do that :
class MyDataGridView:DataGridView
   {       
       protected override bool ProcessDialogKey(Keys keyData)
       {        
           Keys key = (keyData & Keys.KeyCode);
                    
           if (key == Keys.Tab)
           {
               int col = this.CurrentCell.ColumnIndex + 1;
               for (; col < this.Columns.Count; col++)
               {
                   if (!this.Columns[col].ReadOnly)
                   { break; }
               }
               if (col < this.Columns.Count)
               {
                   this.CurrentCell = this.Rows[this.CurrentCell.RowIndex].Cells[col];
               }
               else
               {
                   if (this.CurrentCell.RowIndex != this.Rows.Count - 1)
                   {
                       for (col = 0; col <= this.CurrentCell.ColumnIndex; col++)
                       {
                           if (!this.Columns[col].ReadOnly)
                           {
                               break;
                           }
                       }
                       if (col <= this.CurrentCell.ColumnIndex)
                       {
                           this.CurrentCell = this.Rows[this.CurrentCell.RowIndex + 1].Cells[col];
                       }
                   }
               }
               return true;                  

           }
           return base.ProcessDialogKey(keyData);
       }
       protected override bool ProcessDataGridViewKey(KeyEventArgs e)
       {           
           if (e.KeyData == Keys.Tab)
           {
               int col = this.CurrentCell.ColumnIndex +1;
               for (; col < this.Columns.Count; col++)
               {
                   if (!this.Columns[col].ReadOnly)
                   { break; }
               }
               if (col < this.Columns.Count)
               {
                   this.CurrentCell = this.Rows[this.CurrentCell.RowIndex].Cells[col];
               }
               else
               {
                   if (this.CurrentCell.RowIndex != this.Rows.Count - 1)
                   {
                       for (col = 0; col <= this.CurrentCell.ColumnIndex; col++)
                       {
                           if (!this.Columns[col].ReadOnly)
                           {
                               break;
                           }
                       }
                       if (col <= this.CurrentCell.ColumnIndex)
                       {
                           this.CurrentCell = this.Rows[this.CurrentCell.RowIndex + 1].Cells[col];
                       }
                   }
               }
               return true; 
           }
           return base.ProcessDataGridViewKey(e);
       }       
   }

alladeen88  Sunday, September 06, 2009 10:03 PM
hi Aland Li
I hope you to answer to my question that is availableon this forums
((Adding a new Row to the DataGridView programmatically (DataGridView.AllowUserToAddRow = false) and then Cancel adding by press ESC))

http://social.msdn.microsoft.com/Forums/en-US/winformsdatacontrols/thread/07c1732a-d8c7-4f01-bb8a-1a3aec642ce8?prof=required

Thanks
alladeen88  Monday, September 07, 2009 2:40 AM
Hi alladeen88,

I have taken it.

Regards,
Aland Li
Please mark the replies as answers if they help and unmark if they don't. This can be beneficial to other community members reading the thread.
Aland Li  Monday, September 07, 2009 2:43 AM

You can use google to search for other answers

Custom Search

More Threads

• How to Find Next ????
• Data grid binding
• DataGridView with Unbound Columns
• DataGridView_CellMouseDown Event
• Simulate Addnew Button
• File is being used error
• Datagridview optional display of decimal values
• DGV acting strange ; clearing my entries
• Connecting to a database in SQl2000, authentication error
• DataBinding to a ListBox at runtime?