博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
WPF利用VisualTreeHelper遍历寻找对象的子级对象或者父级对象
阅读量:6997 次
发布时间:2019-06-27

本文共 3852 字,大约阅读时间需要 12 分钟。

原文:

简介

  本文将完整叙述我利用VisualTreeHelper实现题述功能的全部过程,想直接看函数实现的朋友可以跳到函数实现部分。

  或者直接在。
  
  在WPF中我们经常会遇到这种情况:当我们尝试着去寻找窗体或者页面中某个控件的子控件或者父控件的时候,我们只能寻找到它的第一级的逻辑子级对象或者父级对象。当我们想更深入的时候,就没有办法了。
  甚至在我们自定义的DataTemplate中的控件,我们都没办法对其访问。比如在ListView中自定义的控件,我们就没办法获取指定位置的控件了。相关例子可以参见我的博文:。
  本文将探讨解决方案。

VisualTreeHelper

  微软在类中,提供了一些实用工具方法,用于执行涉及可视化树中的节点的常规任务,VisualTreeHelper 类中的一些方法可以接受表示任意一种可视对象类型的 DependencyObject 值。

  这里我们将要用到两个方法分别是:VisualTreeHelper.GetChild()VisualTreeHelper.GetParent()

使用VisualTreeHelper

模拟场景搭建

  新建一个WPF工程,命名为VisualTreeHelperDemo。

  假设我们有如下如所示的一个主窗体,窗体的内容容器为一个name=”TopGrid”的Grid控件,它包含了上下两个子级Grid,每个子级Grid中各自包含了一个Button。
  这里写图片描述
  MainWindow.xaml代码如下:  

遍历寻找子级对象

  现在我们来寻找TopGrid所有Button子级对象,并输出它们的名称。

  打开MainWindow.xaml.cs文件,添加寻找子级对象的代码如下:

/// /// 利用visualtreehelper寻找对象的子级对象/// /// 
/// ///
List
FindVisualChild
(DependencyObject obj) where T : DependencyObject{ try { List
TList = new List
{ }; for (int i = 0; i < VisualTreeHelper.GetChildrenCount(obj); i++) { DependencyObject child = VisualTreeHelper.GetChild(obj, i); if (child != null && child is T) { TList.Add((T)child); List
childOfChildren = FindVisualChild
(child); if (childOfChildren != null) { TList.AddRange(childOfChildren); } } else { List
childOfChildren = FindVisualChild
(child); if (childOfChildren != null) { TList.AddRange(childOfChildren); } } } return TList; } catch (Exception ee) { MessageBox.Show(ee.Message); return null; }}

  在btn_One_Click事件里面书写代码如下:

/// /// 窗体加载事件/// /// /// private void btn_One_Click(object sender, RoutedEventArgs e){    string btnName = "";    List

  运行程序,点击Button1,结果如下图:

  
  这里写图片描述
  
  结果表明遍历成功。
  

遍历寻找父级对象

  现在我们来遍历Button2的父级对象,获得其所有父级对象的信息,并且展示。

  打开MainWindow.xaml.cs文件,添加寻找父级对象的代码如下:

/// /// 利用VisualTreeHelper寻找指定依赖对象的父级对象/// /// 
/// ///
public static List
FindVisualParent
(DependencyObject obj) where T : DependencyObject{ try { List
TList = new List
{ }; DependencyObject parent = VisualTreeHelper.GetParent(obj); if (parent != null && parent is T) { TList.Add((T)parent); List
parentOfParent = FindVisualParent
(parent); if (parentOfParent !=null) { TList.AddRange(parentOfParent); } } else if ( parent != null ) { List
parentOfParent = FindVisualParent
(parent); if (parentOfParent != null) { TList.AddRange(parentOfParent); } } return TList; } catch (Exception ee) { MessageBox.Show(ee.Message); return null; }}

  在btn_Two_Click中添加代码如下:

/// /// 遍历Button2父级对象信息/// /// /// private void btn_Two_Click(object sender, RoutedEventArgs e){    string parentName = "";    List
gridList = FindVisualParent
(btn_Two); foreach (Grid item in gridList) { parentName += string.IsNullOrEmpty(parentName) ? item.Name.ToString() : "," + item.Name.ToString(); } MessageBox.Show(string.Format(btn_Two.Name.ToString() + "共有{0}个逻辑父级,名称分别为{1}", gridList.Count, parentName));}

  运行程序,点击Button2,效果如下:

这里写图片描述
  结果表明遍历成功。

总结

  通过上述的方法我们就可以随心所欲地获取我们想要的控件对象,并对其进行操作,包括自定义的DataTemplate中的控件都可以获取。

转载地址:http://azpvl.baihongyu.com/

你可能感兴趣的文章