如何在数据模板中获取文本

本文关键字:获取 取文本 数据 | 更新日期: 2023-09-27 18:37:21

我使用了下面的代码

    <DataTemplate x:Key="myTemplate">
        <TextBlock Text="Hi"></TextBlock>
    </DataTemplate>

在这种情况下,我可以使用以下代码获取文本块文本

DataTemplate myTemplate = this.Resources["myTemplate"] as DataTemplate;
  TextBlock rootElement = myTemplate.LoadContent() as TextBlock;
  //I can get the text "rootElement.text "

但是当我使用绑定意味着我无法获取文本时

<DataTemplate x:Key="myTemplate">
    <TextBlock Text="{Binding EmployeeName}"></TextBlock>
</DataTemplate>

如何在数据模板中获取文本

为了访问在DataTemplate中定义的元素,我们首先需要掌握一个ContentPresenter。我们可以从应用了DataTemplate的项目中获取ContentPresenter。然后,我们可以从ContentPresenter访问DataTemplate,然后使用 FindName 方法访问其元素。下面是 MSDN 上"如何:查找数据模板生成的元素"页中的一个示例,您应阅读该示例以了解完整详细信息:

// 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);

DataTemplates就像蓝图,描述了特定数据应该如何在屏幕上显示。数据模板只是资源。它们可以由多个元素共享。DataTemplate不是从FrameworkElement派生出来的,所以它们不能自己有DataContext/Databinding。将DataTemplate应用于某个元素时,会隐式为其提供适当的数据上下文。

所以,我想,除非你将模板应用于某些东西,否则你将无法获得有界数据。

使用DataBinding时,您可以获得文本,甚至更容易。您唯一应该记住的是模板DataContext。如果您在ListBox中使用模板 - 那么上下文将特别Item即:

public class Employee : INotifyPropertyChanged
{
    public string EmployeeName 
    {
       get 
       {
          return this.employeeName;
       }
       set 
       {
          this.employeeName = value;
          this.OnPropertyChanged("EmployeeName");
       }
    }
    ...
}

ViewModel

public class EmployeeViewModel : INotifyPropertyChanged
{
    public List<Employee> Employees
    {
       get
       {
           return this.employees;
       }
       set
       {
          this.employees = value;
          this.OnPropertyChanged("Employees");
       }
    }
    ...    
}

xaml

<ListBox ItemsSource={Binding Employees}>
 <ListBox.ItemTemplate>
   <DataTemplate x:Key="myTemplate">
    <TextBlock Text="{Binding EmployeeName}"></TextBlock>
   </DataTemplate>
 </ListBox.ItemTemplate>
</ListBox>

有了这样的结构,你将拥有

ListBox    | Value source
Employee0  | (Employees[0].EmployeeName)
Employee1  | (Employees[1].EmployeeName)
...        | ...
EmployeeN  | (Employees[n].EmployeeName)