using System.Windows; using System.Windows.Controls; using System.Windows.Media; namespace HKW.WPF.Extensions; public static partial class WPFExtensions { /// /// 判断是否是顶级元素, 它必须是 , , 中的一个 /// /// 元素 public static bool IsTopParent(this FrameworkElement element) { if (element is Window || element is Page || element is UserControl) return true; return false; } /// /// 寻找它的顶级元素, 它肯定是 , , 中的一个 /// /// 元素 public static FrameworkElement FindTopParent(this FrameworkElement element) { if (element.IsTopParent()) return element; var parent = element.Parent as FrameworkElement; while (parent is not null) { if (parent.IsTopParent()) return parent; parent = parent.Parent as FrameworkElement; } return null!; } /// /// 尝试寻找它的顶级元素, 它肯定是 , , 中的一个 /// /// 元素 /// 顶级元素 /// 成功为 失败为 public static bool TryFindTopParent( this FrameworkElement element, out FrameworkElement topParent ) { var result = element.FindTopParent(); if (result is null) { topParent = null; return false; } topParent = result; return true; } /// /// 在视觉树上寻找它的顶级元素, 它肯定是 , , 中的一个 /// /// 用于 无法获取到顶级元素的情况下使用, 此元素通常位于 中 /// /// /// 元素 public static FrameworkElement FindTopParentOnVisualTree(this FrameworkElement element) { if (element.TryFindTopParent(out var top)) return top; var temp = (DependencyObject)element; while ((temp = VisualTreeHelper.GetParent(temp)) is not null) { if (temp is FrameworkElement fe && fe.TryFindTopParent(out var topParent)) return topParent; } return null!; } /// /// 尝试在视觉树上寻找它的顶级元素, 它肯定是 , , 中的一个 /// /// 元素 /// 顶级元素 /// 成功为 失败为 public static bool FindTopParentOnVisualTree( this FrameworkElement element, out FrameworkElement topParent ) { var result = element.FindTopParentOnVisualTree(); if (result is null) { topParent = null; return false; } topParent = result; return true; } /// /// 寻找它的顶级元素, 它肯定是 , , 中的一个 /// /// 元素 public static TParent FindTopParent(this FrameworkElement element) where TParent : FrameworkElement { var type = typeof(TParent); if (type != typeof(Window) && type != typeof(Page) && type != typeof(UserControl)) throw new Exception("TParent type must be Window, Page or UserControl"); return (TParent)FindTopParent(element); } }