Freigeben über


Anleitung: Finden von DataTemplate-Generated-Elementen

In diesem Beispiel wird gezeigt, wie man Elemente findet, die von einem DataTemplateerzeugt werden.

Beispiel

In diesem Beispiel gibt es eine ListBox, die an bestimmte XML-Daten gebunden ist.

<ListBox Name="myListBox" ItemTemplate="{StaticResource myDataTemplate}"
         IsSynchronizedWithCurrentItem="True">
  <ListBox.ItemsSource>
    <Binding Source="{StaticResource InventoryData}" XPath="Books/Book"/>
  </ListBox.ItemsSource>
</ListBox>

Die ListBox verwendet die folgenden DataTemplate:

<DataTemplate x:Key="myDataTemplate">
  <TextBlock Name="textBlock" FontSize="14" Foreground="Blue">
    <TextBlock.Text>
      <Binding XPath="Title"/>
    </TextBlock.Text>
  </TextBlock>
</DataTemplate>

Wenn Sie das vom DataTemplate eines bestimmten ListBoxItemgenerierte TextBlock-Element abrufen möchten, benötigen Sie die ListBoxItem, suchen die ContentPresenter innerhalb dieses ListBoxItemund rufen dann FindName für das DataTemplate auf, das auf diesem ContentPresenterfestgelegt ist. Das folgende Beispiel zeigt, wie Sie diese Schritte ausführen. Zu Demonstrationszwecken erstellt dieses Beispiel ein Meldungsfeld, in dem der Textinhalt des DataTemplate-generierten Textblocks angezeigt wird.

// Getting the currently selected ListBoxItem
// Note that the ListBox must have
// IsSynchronizedWithCurrentItem set to True for this to work
ListBoxItem myListBoxItem =
    (ListBoxItem)(myListBox.ItemContainerGenerator.ContainerFromItem(myListBox.Items.CurrentItem));

// Getting the ContentPresenter of myListBoxItem
ContentPresenter myContentPresenter = FindVisualChild<ContentPresenter>(myListBoxItem);

// Finding textBlock from the DataTemplate that is set on that ContentPresenter
DataTemplate myDataTemplate = myContentPresenter.ContentTemplate;
TextBlock myTextBlock = (TextBlock)myDataTemplate.FindName("textBlock", myContentPresenter);

// Do something to the DataTemplate-generated TextBlock
MessageBox.Show("The text of the TextBlock of the selected list item: "
    + myTextBlock.Text);
' Getting the currently selected ListBoxItem
' Note that the ListBox must have
' IsSynchronizedWithCurrentItem set to True for this to work
Dim myListBoxItem As ListBoxItem = CType(myListBox.ItemContainerGenerator.ContainerFromItem(myListBox.Items.CurrentItem), ListBoxItem)

' Getting the ContentPresenter of myListBoxItem
Dim myContentPresenter As ContentPresenter = FindVisualChild(Of ContentPresenter)(myListBoxItem)

' Finding textBlock from the DataTemplate that is set on that ContentPresenter
Dim myDataTemplate As DataTemplate = myContentPresenter.ContentTemplate
Dim myTextBlock As TextBlock = CType(myDataTemplate.FindName("textBlock", myContentPresenter), TextBlock)

' Do something to the DataTemplate-generated TextBlock
MessageBox.Show("The text of the TextBlock of the selected list item: " & myTextBlock.Text)

Es folgt die Implementierung von FindVisualChild, die Methoden von VisualTreeHelper verwendet:

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;
}
Private Function FindVisualChild(Of childItem As DependencyObject)(ByVal obj As DependencyObject) As childItem
    For i As Integer = 0 To VisualTreeHelper.GetChildrenCount(obj) - 1
        Dim child As DependencyObject = VisualTreeHelper.GetChild(obj, i)
        If child IsNot Nothing AndAlso TypeOf child Is childItem Then
            Return CType(child, childItem)
        Else
            Dim childOfChild As childItem = FindVisualChild(Of childItem)(child)
            If childOfChild IsNot Nothing Then
                Return childOfChild
            End If
        End If
    Next i
    Return Nothing
End Function

Siehe auch