5
Reply

A gift from theLizard -

theLizard

theLizard

Jan 14 2011 9:17 PM
13.1k
How to set focus to any control in a control collection without writing specific code or using the TabIndex property!

The following code will set focus() to any control on any form with a single line of code in your keyDown event for the control but to get maximum benefit, set ALL your controls to the one keyDown event handler.

Set the Tag property of each control to the order you want, ie 1,2,3,4 or 1,3,2,4

eg...  download the project...

//FORM containg controls...

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
using theLizard;

namespace WindowsFormsApplication1
  {
  public partial class frmMain : Form
    {
    lizardHandler control = new lizardHandler();
    public frmMain()
      {
      InitializeComponent();
      }
    private void Form1_Load(object sender, EventArgs e)
        {

        }

    private void genericKeyDown(object sender, KeyEventArgs e)
      {
      if (e.KeyCode == Keys.Enter)
        {
        if (control.moveNext(sender)) //returned true, can move to next control
          {
          // ...  your code
          // ...
          }
        else //returned false, had no where else to go
          if (control.args.last_index == 2)
            button1.Focus();
        }
      }

   }
}

//The lizardHandler class this does all the work...

using System;
using System.Collections.Generic;
using System.Text;
using System.Windows.Forms;
using System.Reflection;
using System.Collections;


namespace theLizard
  {
  //a generic handler for any control on forms, panels, tab control pages etc...
  //uses the Tag property for the order of entry or which control to focus on after the enter key is pressed
  //this can be used on any form for any control with a key down event.

  //the key to how it works is casting the object to an appropriate control type, getting the current tag index then finding the next tag index

  //in its simplest form
 
  //if(nextObjectTagIndex == thisObjectTagIndex + 1) { object.Controls[whichObjectIndex].Focus(); }
 
  struct stats
    {
    public int last_index;
    //....
    //....
    }
  //-----------------------------------------------------------------------------------------
  class lizardHandler
    {
    int i = 0, next = -1, thisIndex = -1;
    Control.ControlCollection Ctrls = null;
    public stats args = new stats();
    //-----------------------------------------------------------------------------------------
    public bool moveNext(object o)
      {
      next = -1;
      //get the controls collection from the control parent....

     Edited:
 
     if((Ctrls = ownerControls(o)) == null)
         return(false); //nothing to do go back...


      Remove:
      //nothing to do go back
      //if (Ctrls.Count == 0)
      //  return (false);


      //get the tag property of the control
      if ((thisIndex = getTagIndex(o)) == -1) 
        return(false); 

      //have the controls collection of objects parent
      for (i = 0; i < Ctrls.Count; i++) 
        {
        //is there a control with 1 more than thisIndex in the parents control collection?
        if ((next = getTagIndex(Ctrls[i])) == thisIndex + 1)
          {
          Ctrls[i].Focus();
          args.last_index = next;
          return (true);
          }
        }
     
      //if it gets here, we have reached the end of the line, nothing more to do...
      return (false);
      }
    //-----------------------------------------------------------------------------------------
    internal int getTagIndex(object o)
      {
      //cast object to control type, get the tag and return as integer
      switch (o.GetType().Name)
        {
        case "TextBox":  
          return(int.Parse(((TextBox)o).Tag.ToString()));
        case "ComboBox":                               
          return (int.Parse(((ComboBox)o).Tag.ToString()));
        case "CheckBox":                               
          return (int.Parse(((CheckBox)o).Tag.ToString()));
        case "ListBox":                               
          return (int.Parse(((ListBox)o).Tag.ToString()));
        case "DateTimePicker":                        
          return (int.Parse(((DateTimePicker)o).Tag.ToString()));
        case "TreeView":                              
          return (int.Parse(((TreeView)o).Tag.ToString()));
        case "RichTextBox":                           
          return (int.Parse(((RichTextBox)o).Tag.ToString()));
        }

      //if it gets here, the control type has not been declared
      return (-1);
      }
    //-----------------------------------------------------------------------------------------
    internal Control.ControlCollection ownerControls(object o)
      {
      //get the type of control parsed by object o and return the controls collection of the controls parent;

      switch (o.GetType().Name)
        {
        case "TextBox":
          return (((TextBox)o).Parent.Controls);      
        case "ComboBox":
          return (((ComboBox)o).Parent.Controls);
        case "CheckBox":
          return (((CheckBox)o).Parent.Controls);
        case "ListBox":
          return (((ListBox)o).Parent.Controls);
        case "DateTimePicker":
          return (((DateTimePicker)o).Parent.Controls);
        case "TreeView":
          return (((TreeView)o).Parent.Controls);
        case "RichTextBox":
          return (((RichTextBox)o).Parent.Controls);
        }

      //return the owner of the control as an object
      return (null);
      }
    }
  }

Try this out tell me what you think... Do you understand what is going on?

Answers (5)