在我的应用程序中,我有一个带有自定义DataTemplate的ListBox。 XAML如下:
<ListBox Name="lstTasks">
<ListBox.ItemTemplate>
<DataTemplate>
<StackPanel Orientation="Horizontal" VerticalAlignment="Top">
<CheckBox Name="chkIsChecked" VerticalAlignment="Top" IsChecked="{Binding Path=IsChecked, Mode=TwoWay}"/>
<RichTextBox Name="rtbTask" HorizontalAlignment="Left" Height="50" VerticalAlignment="Top" Width="450"
BorderBrush="{DynamicResource {x:Static SystemColors.ActiveCaptionTextBrushKey}}" Margin="0,0,0,10"/>
</StackPanel>
</DataTemplate>
</ListBox.ItemTemplate>
</ListBox>
我使用一个名为CheckBoxItem的自定义类作为我的ListBoxItems。如果我想将一个项目添加到ListBox,我将使用以下代码作为示例:
lstTasks.Items.Add(new CheckBoxItem("", false));
如果我想从ListBox中检索此项目,请使用以下代码:
CheckBoxItem CheckBoxItem = (CheckBoxItem)lstTasks.Items[0];
我对数据绑定没有任何问题;它工作正常。我的问题是检索DataTemplate中的一个子节点。在应用程序中,用户可以在每个CheckBoxItem中编辑RichTextBox的内容。我希望能够将RichTextBox的内容保存到外部文件。我已经创建了获取RTF文本并将其存储在String中的方法,但我似乎无法访问任何给定CheckBoxItem的RichTextBox。
我已经在网上搜索了很长时间但似乎找不到任何有用的东西。使用VisualTree不起作用,因为CheckBoxItems不是DependencyObjects,不能将它们转换为它们。因此,我非常感到困惑,非常感谢对此问题的任何见解。
我的一个想法是跟踪某种集合中的所有RichTextBox。我处理他们的Loaded事件然后将它们添加到那里的集合中,但我真的不想这样做,因为它似乎是不必要的内存使用。
提前感谢您的帮助!
答案 0 :(得分:2)
没有简单的方法。但是知道你之前已经遇到了VisualTree
之前的事情,也许你已经看到了以下示例中的大部分代码。您可能错过的第一行是向您展示如何从ListBoxItem
获取CheckBoxItem
。手头有ListBoxItem
表示您有DependencyObject
开始使用VisualTree
内容技术查找RichTextBox
:
var myListBoxItem = (lstTasks.ItemContainerGenerator.ContainerFromItem(lstTasks.Items[0]));
// Getting the ContentPresenter of myListBoxItem
ContentPresenter myContentPresenter = FindVisualChild<ContentPresenter>(myListBoxItem);
// Finding richtextbox from the DataTemplate that is set on that ContentPresenter
DataTemplate myDataTemplate = myContentPresenter.ContentTemplate;
RichTextBox myTextBlock = (RichTextBox)myDataTemplate.FindName("rtbTask", myContentPresenter);
FindVisualChild
的实施private childItem FindVisualChild<childItem>(DependencyObject obj) where childItem : DependencyObject
{
for (int i = 0; i < VisualTreeHelper.GetChildrenCount(obj); i++)
{
DependencyObject child = VisualTreeHelper.GetChild(obj, i);
if (child != null && child is childItem)
return (childItem)child;
else
{
childItem childOfChild = FindVisualChild<childItem>(child);
if (childOfChild != null)
return childOfChild;
}
}
return null;
}
:
{{1}}