/// <summary> /// Retrieves all the logical descendents of a framework element using a /// breadth-first search. For performance reasons this method manually /// manages the stack instead of using recursion. /// </summary> /// <param name="parent">The parent framework element.</param> /// <returns>The logical children of the framework element.</returns> internal static IEnumerable <FrameworkElement> GetLogicalDescendents(this FrameworkElement parent) { Debug.Assert(parent != null, "The parent cannot be null."); return (FunctionalProgramming.TraverseBreadthFirst( parent, node => node.GetLogicalChildren(), node => true)); }
/// <summary> /// Retrieves the original source of a new DragOver event. Attempts to /// determine the original source by finding the the deepest element /// in the tree that the mouse is over. /// </summary> /// <param name="args">Information about the drag event.</param> /// <returns>The original source of a new DragOver event.</returns> private static UIElement GetDragOverOriginalSource(SW.DragEventArgs args) { UIElement originalSource = args.OriginalSource as UIElement; // Use the previous original source and go to its root. // Note: this won't work if a popup appears on top of the // original source but it will work if the previous original source // is inside of a popup. UIElement rootVisual = originalSource.GetVisualAncestors().OfType <UIElement>().LastOrDefault(); if (rootVisual != null) { // If the original source disappears (ex. a popup disappears), // use the root visual. rootVisual = Application.Current.RootVisual; originalSource = FunctionalProgramming.TraverseBreadthFirst( rootVisual, node => node.GetVisualChildren().OfType <UIElement>(), node => new Rect(new Point(0, 0), node.GetSize()).Contains(args.GetPosition(node))) .LastOrDefault(); } return(originalSource); }