Generic Methods: Find Controls by Type

Although this was originally part of my recent Generics presentation, I have received several requests to publish it separately.

The reason that I created this originally was that I found myself often-times wanting a strongly-typed list of all the checkboxes / buttons / etc in my code-behind/beside pages.  There is the Page.FindControl(string id), but that only allows you to get a control by id and it returns a Control.  I wanted something more specific, yet generic enough to use as a Utility.  This was screaming for Generic Methods, so below is what I came up with.

 

I use this constantly and hope that someone else gets some mileage out of it.  If you have improvements, please post them.  For example usage, download the full Generics presentation.

  1. using System;
  2. using System.Collections.Generic;
  3. using System.Windows.Controls;
  4.  
  5. namespace r2musings.Web.UI.WebControls
  6. {
  7.     public static class Utility
  8.     {
  9.         #region FindControlsByType
  10.         /// <summary>
  11.         ///   Returns a generic list of controls of a provided type starting at a
  12.         ///    a provided base control (works recursively)
  13.         ///    Example Usage:  
  14.         ///       List<Button> buttonList = Utility.FindControlsByType<Button>(testPanel);
  15.         ///       This would return a list of all Buttons contained anywhere within testPanel
  16.         /// </summary>
  17.         /// <typeparam name="T">Type of control</typeparam>
  18.         /// <param name="parentControl">Base control to start search</param>
  19.         /// <returns></returns>
  20.         public static List<T> FindControlsByType<T>(Control parentControl)
  21.                     where T: System.Web.UI.Control
  22.         {
  23.             // new up our return list
  24.             List<T> returnList = new List<T>();
  25.  
  26.             // loop through all controls and call internal recursion to
  27.             //   add all controls of type T to the returnList
  28.             foreach (Control childControl in parentControl.Controls)
  29.             {
  30.                 InternalFindControlsByType<T>(childControl, returnList);
  31.             }
  32.  
  33.             // return our List<T>
  34.             return returnList;
  35.         }
  36.         
  37.         #endregion
  38.  
  39.         #region Recursion Method
  40.         
  41.         /// <summary>
  42.         ///   Should NOT call this method directly
  43.         ///   This is for the internal recursion of FindControlsByType()  
  44.         /// </summary>
  45.         /// <typeparam name="T">Type of control</typeparam>
  46.         /// <param name="parentControl">Base control to start search</param>
  47.         /// <param name="returnList">List to add Controls</param>
  48.         private static void InternalFindControlsByType<T>(
  49.             Control parentControl, List<T> returnList)
  50.             where T: System.Web.UI.Control
  51.         {
  52.             if (returnList == null)
  53.                 throw new ArgumentNullException("Null List passed to InternalFindControlsByType");
  54.  
  55.             if (parentControl is T)
  56.             {
  57.                 returnList.Add((T) parentControl);
  58.             }
  59.  
  60.             foreach (Control childControl in parentControl.Controls)
  61.             {
  62.                 // call this method recursively to get all child controls
  63.                 InternalFindControlsByType(childControl, returnList);
  64.             }
  65.         }
  66.  
  67.         #endregion
  68.     }
  69. }

This entry was posted in Generics. Bookmark the permalink.

Comments are closed.