嗨,我在itemscontrol的datatemplate中只有一个文本框。当我将itemcontrols绑定到一个可观察的集合时,我得到两个文本框。但是我需要根据每个文本框做一些操作,我想用一些id分别找到每个文本框。
任何人都可以帮助如何在WPF中的itemscontrol中找到控件。
答案 0 :(得分:67)
使用ItemContainerGenerator,您可以获取项目的生成容器,并向下遍历可视树以查找TextBox。在ItemsControl的情况下,它将是ContentPresenter,但ListBox将返回ListBoxItem,ListView将返回ListViewItem等。
ContentPresenter cp = itemsControl.ItemContainerGenerator.ContainerFromItem(item) as ContentPresenter;
TextBox tb = FindVisualChild<TextBox>(cp);
if (tb != null)
{
// do something with tb
}
public static T FindVisualChild<T>(DependencyObject depObj) where T : DependencyObject
{
if (depObj != null)
{
for (int i = 0; i < VisualTreeHelper.GetChildrenCount(depObj); i++)
{
DependencyObject child = VisualTreeHelper.GetChild(depObj, i);
if (child != null && child is T)
{
return (T)child;
}
T childItem = FindVisualChild<T>(child);
if (childItem != null) return childItem;
}
}
return null;
}
如果您想使用
,也可以按索引获取容器itemsControl.ItemContainerGenerator.ContainerFromIndex(0);
答案 1 :(得分:5)
谢谢布莱斯,我试图勾选向上箭头,但它说我的评价太低了!遗憾!
我修改了代码以返回给定类型的所有子项的列表,因为它是我需要的,并且认为其他人可能会发现它有用。
再次感谢布莱斯,真的很有帮助 - 对评价事感到抱歉!
public static List<T> FindVisualChildren<T>(DependencyObject depObj) where T : DependencyObject
{
List<T> list = new List<T>();
if (depObj != null)
{
for (int i = 0; i < VisualTreeHelper.GetChildrenCount(depObj); i++)
{
DependencyObject child = VisualTreeHelper.GetChild(depObj, i);
if (child != null && child is T)
{
list.Add((T)child);
}
List<T> childItems = FindVisualChildren<T>(child);
if (childItems != null && childItems.Count() > 0)
{
foreach (var item in childItems)
{
list.Add(item);
}
}
}
}
return list;
}
答案 2 :(得分:2)
您可能想尝试使用VisualTreeHelper。 ItemsControl本身的属性只允许您获取绑定的数据,而不是用于可视化数据的模板实例,而VisualTreeHelper允许您在WPF渲染时浏览可视树。
如果您遍历父ItemControl的可视子项(递归),您在查看屏幕上看到的文本框时应该没有任何困难。
答案 3 :(得分:1)
另一个例子:
private void DataGridBank_KeyUp(object sender, System.Windows.Input.KeyEventArgs e)
{
try
{
switch (e.Key)
{
case Key.Down:
if ((DataGridBank.SelectedIndex + 1) <= DataGridBank.Items.Count)
{
DataGridBank.SelectedIndex = DataGridBank.SelectedIndex + 1;
FocusCell();
}
break;
case Key.Up:
if ((DataGridBank.SelectedIndex - 1) >= 0)
{
DataGridBank.SelectedIndex = DataGridBank.SelectedIndex - 1;
FocusCell();
}
break;
case Key.Enter:
case Key.Tab:
FocusCell();
break;
}
}
catch (Exception ex)
{
}
}
private void DataGridBank_Loaded(object sender, RoutedEventArgs e)
{
try
{
if (DataGridBank.Items.Count > 0)
{
DataGridBank.SelectedIndex = 0;
FocusCell();
}
}catch(Exception ex)
{
}
}
private void FocusCell()
{
var selectedRow = (DataGridRow)DataGridBank.ItemContainerGenerator.ContainerFromItem(DataGridBank.SelectedItem);
var textImport = FindVisualChild<TextBox>(selectedRow);
textImport.Focus();
textImport.SelectAll();
}
public static T FindVisualChild<T>(DependencyObject depObj) where T : DependencyObject
{
if (depObj != null)
{
for (int i = 0; i < VisualTreeHelper.GetChildrenCount(depObj); i++)
{
DependencyObject child = VisualTreeHelper.GetChild(depObj, i);
if (child != null && child is T)
{
return (T)child;
}
T childItem = FindVisualChild<T>(child);
if (childItem != null) return childItem;
}
}
return null;
}
答案 4 :(得分:0)
如果您有包含数据模板的数据网格和模板列, 您可以使用以下代码示例
<DataGridTemplateColumn x:Name="photoPathColumn" Header="{x:Static resx:FrmResource.Photo}">
<DataGridTemplateColumn.CellEditingTemplate x:Uid="keyelm">
<DataTemplate x:Name="dodo">
<StackPanel Orientation="Horizontal" Height="Auto">
<TextBlock x:Name="photo" x:Uid="imageFile" Text="{Binding Path=PhotoPath}" />
<Button x:Name="Browse" Content="..." Click="Browse_Click" />
</StackPanel>
</DataTemplate>
</DataGridTemplateColumn.CellEditingTemplate>
photoPathColumn.CellEditingTemplate.FindName("photo",photoPathColumn.GetCellContent(CustomersDataGrid.CurrentItem))