WPF:如何将通用数据绑定到 TreeView?
WPF: how to bind generic data to a TreeView?
我有一个 TreeView,我想给它绑定一些数据;我想为每种类型的数据显示不同的 TreeViewItem 布局并查看 this example 我想出了如何去做。
到目前为止我有以下 类:
public class Category
{
public string Name { get; set; }
public List<Product> Products { get; set; }
}
public class Product
{
public string Name { get; set; }
}
现在我需要使用这样的包装器来处理数据:
public class DataWrapper<T> where T : class
{
public T Data { get; set; }
}
而且我想将如下创建的列表设置为 TreeView 的 ItemSource:
IList<DataWrapper<Category>> list = new List<DataWrapper<Category>>();
Category c = new Category() { Name = "C1", Products = new List<Product>() { new Product() { Name = "P1" }, new Product() { Name = "P2" } } };
list.Add(new DataWrapper<Category>() { Data = c });
c = new Category() { Name = "C2", Products = new List<Product>() { new Product() { Name = "P3" }, new Product() { Name = "P4" } } };
list.Add(new DataWrapper<Category>() { Data = c });
c = new Category() { Name = "C3", Products = new List<Product>() { new Product() { Name = "P5" }, new Product() { Name = "P6" } } };
list.Add(new DataWrapper<Category>() { Data = c });
所以我所做的是将 DataContext 设置为 treeView:
myTreeView.DataContext =list;
这是 xaml:
<TreeView x:Name="myTreeView">
<TreeView.Resources>
<HierarchicalDataTemplate DataType="{x:Type src:Category}" ItemsSource="{Binding Path=Data}">
<StackPanel>
<TextBlock Text="Category:" />
<TextBlock Text="{Binding Path=Name}" />
</StackPanel>
</HierarchicalDataTemplate>
<HierarchicalDataTemplate DataType="{x:Type src:Product}">
<StackPanel>
<TextBlock Text="Product:" />
<TextBlock Text="{Binding Path=Name}" />
</StackPanel>
</HierarchicalDataTemplate>
</TreeView.Resources>
</TreeView>
但它当然不起作用:)
谁能向我解释如何正确绑定此类对象列表?
谢谢
它不起作用的原因是您将 ItemsSource
绑定到类型为 List<DataWrapper<Category>>
的 DataContext
上名为 Data
的 属性并且没有这个 属性.
我不太确定您需要包装纸做什么。最简单的方法是摆脱包装器,使列表成为项目类型 Category
的列表,并将此列表用作 ItemsSource
:
IList<Category> list = new List<Category>();
Category c = new Category() { Name = "C1", Products = new List<Product>() { new Product() { Name = "P1" }, new Product() { Name = "P2" } } };
list.Add(c);
...
// Set this list as ItemsSource
myTreeView.ItemsSource=list;
这样就可以正确应用数据模板的类型绑定。
或者,如果您需要包装器,只需将包装器设为非通用即可:
public class CategoryWrapper
{
public Category Data { get; set; }
}
并修改分类模板:
<HierarchicalDataTemplate DataType="{x:Type src:CategoryWrapper}" ItemsSource="{Binding Path=Data.Products}">
<StackPanel>
<TextBlock Text="Category:" />
<TextBlock Text="{Binding Path=Data.Name}" />
</StackPanel>
</HierarchicalDataTemplate>
使它成为非通用的原因是,将通用类型指定为模板的 DataType
并不容易:
<!-- Doesn't work! -->
DataType="{x:Type src:DataWrapper<Category>}"
希望对您有所帮助!如果此解决方案对您的情况不起作用,请告诉我,我会再次查看...
我有一个 TreeView,我想给它绑定一些数据;我想为每种类型的数据显示不同的 TreeViewItem 布局并查看 this example 我想出了如何去做。
到目前为止我有以下 类:
public class Category
{
public string Name { get; set; }
public List<Product> Products { get; set; }
}
public class Product
{
public string Name { get; set; }
}
现在我需要使用这样的包装器来处理数据:
public class DataWrapper<T> where T : class
{
public T Data { get; set; }
}
而且我想将如下创建的列表设置为 TreeView 的 ItemSource:
IList<DataWrapper<Category>> list = new List<DataWrapper<Category>>();
Category c = new Category() { Name = "C1", Products = new List<Product>() { new Product() { Name = "P1" }, new Product() { Name = "P2" } } };
list.Add(new DataWrapper<Category>() { Data = c });
c = new Category() { Name = "C2", Products = new List<Product>() { new Product() { Name = "P3" }, new Product() { Name = "P4" } } };
list.Add(new DataWrapper<Category>() { Data = c });
c = new Category() { Name = "C3", Products = new List<Product>() { new Product() { Name = "P5" }, new Product() { Name = "P6" } } };
list.Add(new DataWrapper<Category>() { Data = c });
所以我所做的是将 DataContext 设置为 treeView:
myTreeView.DataContext =list;
这是 xaml:
<TreeView x:Name="myTreeView">
<TreeView.Resources>
<HierarchicalDataTemplate DataType="{x:Type src:Category}" ItemsSource="{Binding Path=Data}">
<StackPanel>
<TextBlock Text="Category:" />
<TextBlock Text="{Binding Path=Name}" />
</StackPanel>
</HierarchicalDataTemplate>
<HierarchicalDataTemplate DataType="{x:Type src:Product}">
<StackPanel>
<TextBlock Text="Product:" />
<TextBlock Text="{Binding Path=Name}" />
</StackPanel>
</HierarchicalDataTemplate>
</TreeView.Resources>
</TreeView>
但它当然不起作用:) 谁能向我解释如何正确绑定此类对象列表?
谢谢
它不起作用的原因是您将 ItemsSource
绑定到类型为 List<DataWrapper<Category>>
的 DataContext
上名为 Data
的 属性并且没有这个 属性.
我不太确定您需要包装纸做什么。最简单的方法是摆脱包装器,使列表成为项目类型 Category
的列表,并将此列表用作 ItemsSource
:
IList<Category> list = new List<Category>();
Category c = new Category() { Name = "C1", Products = new List<Product>() { new Product() { Name = "P1" }, new Product() { Name = "P2" } } };
list.Add(c);
...
// Set this list as ItemsSource
myTreeView.ItemsSource=list;
这样就可以正确应用数据模板的类型绑定。
或者,如果您需要包装器,只需将包装器设为非通用即可:
public class CategoryWrapper
{
public Category Data { get; set; }
}
并修改分类模板:
<HierarchicalDataTemplate DataType="{x:Type src:CategoryWrapper}" ItemsSource="{Binding Path=Data.Products}">
<StackPanel>
<TextBlock Text="Category:" />
<TextBlock Text="{Binding Path=Data.Name}" />
</StackPanel>
</HierarchicalDataTemplate>
使它成为非通用的原因是,将通用类型指定为模板的 DataType
并不容易:
<!-- Doesn't work! -->
DataType="{x:Type src:DataWrapper<Category>}"
希望对您有所帮助!如果此解决方案对您的情况不起作用,请告诉我,我会再次查看...