VisualTreeHelper Extensions for Windows Store Apps

Preface

The VisualTreeHelperprovides utility methods that can be used to traverse object relationships (along child-object or parent-object axes) in the visual tree of your app.

In this post I will show two extensions to VisualTreeHelper. Since you cannot create an instance of VisualTreeHelper, these are not extension methods from a technical point of view. But they do extend the functionality, so I call them extensions here.

FindChildByName Extension

This extension searches a child element in the visual tree by its name. Of course, there are other ways to find a control by its name, e.g. FrameworkElement.FindName.

I needed to find a control that was created during runtime. I had a ListView with an ItemsSource bound to an ObservableCollection<T>. An ItemTemplate was defined, containing several controls. And I needed to access one particular control inside of this generated ListViewItem. FrameworkElement.FindName did not found it, even though a x:Name was defined in the DataTemplate.

This lead to the first extension.

// Implemented by VisualTreeHelperExtensions
/// <summary>
/// Searches a child element in the visual tree by its name.
/// </summary>
/// <param name="parent">
/// The parent of the element.
/// </param>
/// <param name="name">
/// The name of the child to search for.
/// </param>
/// <param name="child">
/// Set to the child if found, otherwise <c>null</c>.
/// </param>
/// <returns>
/// <c>true</c> if the child was found, otherwise <c>false</c>.
/// </returns>
/// <remarks>
/// This method walks the visual tree recursively!
/// </remarks>
public static bool FindChildByName
  (
  DependencyObject parent,
  string name,
  out FrameworkElement child
  )
{
  // [Input parameter validation omitted]
  // Set the output first
  child = null;

  // Walk the tree
  int childrenCount = VisualTreeHelper.GetChildrenCount(parent);

  for (int childIndex = 0; childIndex < childrenCount; ++childIndex)
  {
    // Get the child
    DependencyObject childObject 
      = VisualTreeHelper.GetChild(parent, childIndex);

    // Convert it into a framework element
    FrameworkElement childElement 
      = childObject as FrameworkElement;

    // if successfull, check the name
    if (childElement != null
      && childElement.Name.Equals(name))
    {
      // We found it
      child = childElement;
      // get out
      return (true);
    }

    // If the child contains the element, get out
    if (VisualTreeHelperExtensions
        .FindChildByName(childObject, name, out child))
    {
      return (true);
    }
  }

  // if we got here, we hadn't found the child
  return (false);
}

As you can see from the code, the class that implements this method is called VisualTreeHelperExtensions. In case you like to use this extension too, make sure to give your extension class the same name. In case you want to give it another name, please change the call of VisualTreeHelperExtensions.FindChildByName at the end of the method to TheNameOfYourClass.FindChildByName.

FindFirstChildByType Extension

In another scenario, I needed to find the first child of a given type, independent from its name.

// Implemented by VisualTreeHelperExtensions
/// <summary>
/// Searches the first child element in the visual tree by its type.
/// </summary>
/// <param name="parent">
/// The parent of the element.
/// </param>
/// <param name="type">
/// The type of the child to search for.
/// </param>
/// <param name="child">
/// Set to the child if found, otherwise <c>null</c>.
/// </param>
/// <returns>
/// <c>true</c> if the child was found, otherwise <c>false</c>.
/// </returns>
/// <remarks>
/// This method walks the visual tree recursively!
/// </remarks>
public static bool FindFirstChildByType
  (
  DependencyObject parent,
  Type type,
  out FrameworkElement child
  )
{
  // [Input parameter validation omitted]
  // Set the output first
  child = null;

  // Walk the tree
  int childrenCount 
    = VisualTreeHelper.GetChildrenCount(parent);

  for (int childIndex = 0; childIndex < childrenCount; ++childIndex)
  {
    // Get the child
    DependencyObject childObject 
      = VisualTreeHelper.GetChild(parent, childIndex);

    // Convert it into a framework element
    FrameworkElement childElement 
      = childObject as FrameworkElement;

    // if successfull, check the type
    if (childElement != null
      && childElement.GetType() == type)
    {
      // We found it
      child = childElement;
      // get out
      return (true);
    }

    // If the child contains the element, get out
    if (VisualTreeHelperExtensions
      .FindFirstChildByType(childObject, type, out child))
    {
      return (true);
    }
  }

  // if we got here, we hadn't found the child
  return (false);
}

As said above, the class that implements this method is called VisualTreeHelperExtensions. In case you like to use this extension too, make sure to give your extension class the same name. In case you want to give it another name, please change the call of VisualTreeHelperExtensions.FindChildByName at the end of the method to TheNameOfYourClass.FindFirstChildByType.

Links

VisualTreeHelper class

Extension Methods (C# Programming Guide)

FrameworkElement.FindName