WPF: Получение составляющих элементов управления TreeViewItem
Как я могу получить составляющие элементы управления, составляющие TreeViewItem в коде, если они находятся внутри иерархической таблицы данных?
<HierarchicalDataTemplate DataType="{x:Type local:Module}" ItemsSource="{Binding Children}">
<StackPanel Orientation="Horizontal">
<Image Width="16" Height="16" Margin="3,0" Source="Images\module.ico" />
<local:RenamingNode Name="RenamableNode" Text="{Binding Name}" VstaObject="{Binding BindsDirectlyToSource=True}" OnRename="OnRenameOccured" />
</StackPanel>
</HierarchicalDataTemplate>
Поэтому программно, когда я получаю событие с TreeViewItem в качестве источника, я хочу иметь возможность получить local:RenamingNode, но я не могу получить потомков TreeViewItem.
Спасибо,
Илья
4 ответа
Это сработало для меня. Несомненно, есть лучший способ, как всегда, и вы, несомненно, добавите дополнительные проверки, такие как проверка количества дочерних элементов (ий) и / или получение / проверка типа / имени дочерних элементов в цикле и т. Д., Но основной метод работает, хорошо это сделал в моем приложении, хотя у меня есть сетка вместо StackPanel.
private object FindContentTemplatePart(TreeViewItem treeViewItem)
{
if (treeViewItem != null)
{
var header = (ContentPresenter)treeViewItem.Template.FindName("PART_Header", treeViewItem);
if (header != null)
{
StackPanel stackPanel = (StackPanel)VisualTreeHelper.GetChild(header,0);
return stackPanel.Children[2];
}
}
return null;
}
Я предполагаю, что это будет то же самое в WPF, что и Silverlight (это версия Silverlight)
(treeViewItem.HeaderTemplate.LoadContent() as StackPanel).FindName("RenamableNode")
Вы можете использовать FrameworkTemplate.FindName, чтобы найти предъявителя содержимого заголовка в шаблоне элемента управления TreeView, а затем снова найти нужную часть в шаблоне данных.
private object FindContentTemplatePart(TreeViewItem treeViewItem)
{
if (treeViewItem != null)
{
var header = treeViewItem.Template.FindName("PART_Header", treeViewItem) as ContentPresenter;
if (header != null)
{
return header.ContentTemplate.FindName("RenamableNode", header);
}
}
return null;
}
Вы также можете пройтись по визуальному дереву вручную с помощью методов VisualTreeHelper.
Ни одно из вышеперечисленных решений не работает в Silverlight, но, похоже, это работает.
<common:HierarchicalDataTemplate x:Key="myHierarchicalTemplate" ItemsSource="{Binding Children}" >
<StackPanel x:Name="spTreeItem" Height="23" Margin="0,0,0,0" HorizontalAlignment="Stretch" Orientation="Horizontal">
</StackPanel>
</common:HierarchicalDataTemplate>
После кода
TreeViewItem item = TreeViewWorkarounds.ContainerFromItem(trtFolders, trtFolders.SelectedItem);
Grid ItemGrid = (Grid) VisualTreeHelper.GetChild(item, 0);
Button ItemGridButton = (Button)VisualTreeHelper.GetChild(ItemGrid, 2);
Grid ButtonGrid = (Grid)VisualTreeHelper.GetChild(ItemGridButton, 0);
ContentPresenter CP = (ContentPresenter)VisualTreeHelper.GetChild(ButtonGrid, 1);
ContentPresenter CPchlild = (ContentPresenter)VisualTreeHelper.GetChild(CP, 0);
StackPanel sp = (StackPanel)VisualTreeHelper.GetChild(CPchlild, 0);