2013-03-06 10 views
0

Это приложение WPF.LogicalTree Control непосредственно под мышью нет VisualTree

Я пытаюсь получить контроль непосредственно под мышью, и это оказывается удивительной болью.

Mouse.DirectlyOver, InputHitTest и VisualTreeHelper.HitTest все ссылаются на дерево VISUAL. Я пытаюсь захватить сам контроль.

Пример: Если у меня есть TextBox и используйте любой из вышеперечисленных, он вернет TextBoxView, тогда как я хочу сам TextBox.

Это происходит внутри события PreviewLeftButtonDown. Отправитель не является вариантом, поскольку отправитель всегда является ListViewItem для меня. Если я проверяю e.OriginalSource, это все еще элемент VisualTree, а не фактический элемент управления.

Благодарим за разъяснение, если потребуется.

Благодаря

ответ

1

Я согласен с mdm20, что единственным способом добраться до Textbox является пересекаясь с родителем. Фактически, here is a link to the same question asked a couple of years ago, с тем же ответом. Если вы хотите ограничить ненужное обход дерева, вы можете прекратить поиск, как только вы нажмете ListViewItem, поскольку все, что находится выше этого пункта, не является тем, что вы ищете в любом случае.

Однако добавьте последнюю ссылку и this one together, и мне кажется, что у вас уже есть свой ответ. Если возвращается TextBoxView, вы знаете, что было поражено текстовое поле. Вы даже можете кэшировать входящий TextBox, который проходит через HitTestFilterCallBack потенциально, но это скорее теория и, возможно, склонность к ошибкам. Однако, спустившись по этому пути, вы можете просто проверить, находится ли TextBox, проходящий через фильтр, родительский элемент TextBoxView

+0

Это будет принятый ответ TextBoxView - это то, что я закончил с использованием. Спасибо – tronious

4

Вам просто нужно ходить вверх визуального дерева, пока не найдете нужный тип. Ниже приведен код link.

Вот код из этой ссылки

// walk up the visual tree to find object of type T, starting from initial object 
public static T FindUpVisualTree<T>(DependencyObject initial) where T : DependencyObject 
{ 
    DependencyObject current = initial; 

    while (current != null && current.GetType() != typeof(T)) 
    { 
     current = VisualTreeHelper.GetParent(current); 
    } 
    return current as T; 
} 
+0

Спасибо за ваш ответ. Это сработает, но мне не нравится ходить по дереву, поскольку это часто случается. Кроме того, я был бы обеспокоен нечаянно попав неправильный TextBox (что, если элемент управления шаблонный и есть mutliple Textboxes, ведущие к родителю. (=) В конце концов ответ JustinPihony в удовлетворяет мои потребности. – tronious

1

Подойдите визуальное дерево, пока не найти UIElement:

public UIElement FindUIElement(DependencyObject visualTreeNode) 
{ 
    UIElement elem; 
    while ((elem = (visualTreeNode as UIElement)) != null) 
     visualTreeNode = VisualTreeHelper.GetParent(visualTreeNode); 
    return elem; 
}