以编程方式在 WPF 中添加 views/controls
Programmatically adding views/controls in WPF
从数据库加载数据后(假设我们加载了课程),我想在列表中显示它们。我读过您可以使用 UserControl
动态添加内容,但这些示例专门用于动态更改内容,而不是显示结果列表。
我想要的是创建一个 XAML 模板并为每个列表项实例化一次,然后将其添加到列表中(换句话说,将其添加到一个 StackedPanel
)。我怎样才能做到这一点?另外,我应该使用 Page
还是 UserControl
?
这正是 ListBox
和 ItemsControl
控件创建的内容。 ListBox是ItemsControl的增强版,所以我只说后者,基本的。
ItemsControl
包含名为 ItemsSource
的依赖项 属性。在那里传递一个集合,ItemsControl 将生成一个 "panel",其中包含从该来源获取的 "views" 个项目。
默认情况下,ItemsControl 使用 StackPanel 作为面板,但如果需要,您可以通过 ItemPanel
属性.
进行更改
默认情况下,ItemsControl 使用默认的 WPF 模板匹配来为每个项目生成和呈现视图。但是,您可以专门使用 ItemTemplate
属性 来设置 DataTemplate
来指示视图的外观。
示例:
<!-- simple vertical/StackPanel list -->
<ItemsControl ItemsSource="{Binding MyItems}">
<ItemsControl.ItemTemplate>
<!-- the template of a single Item -->
<!-- note that I'm setting it here explicitely -->
<!-- but the ItemTemplate prop could have been bound, resourcized, etc -->
<DataTemplate>
<Border BorderThickness="1">
<!-- reads a ShoeSize from the items from MyItems -->
<TextBlock Text="{Binding ShoeSize}" />
</Border>
</DataTemplate>
</ItemsControl.ItemTemplate>
</ItemsControl>
<!-- simple horizontal/StackPanel list -->
<ItemsControl ItemsSource="{Binding MyItems}">
<ItemsControl.ItemsPanel>
<ItemsPanelTemplate>
<StackPanel Orientation="Horizontal" />
</ItemsPanelTemplate>
</ItemsControl.ItemsPanel>
<ItemsControl.ItemTemplate>
<DataTemplate>
<Border BorderThickness="1">
<TextBlock Text="{Binding ShoeSize}" />
</Border>
</DataTemplate>
</ItemsControl.ItemTemplate>
</ItemsControl>
<!-- you can use any panel and any itemtemplate -->
<ItemsControl ItemsSource="{Binding MyXYPoints}">
<ItemsControl.ItemsPanel>
<ItemsPanelTemplate>
<!-- any Panel is OK! even plain canvas -->
<Canvas />
</ItemsPanelTemplate>
</ItemsControl.ItemsPanel>
<ItemsControl.ItemTemplate>
<DataTemplate>
<!-- just remember that in canvas there's no autolayout -->
<!-- so you need to set the coords on each item! -->
<Ellipse Width="2" Height="2"
Canvas.Left="{Binding PositionX}"
Canvas.Top="{Binding PositionY}" />
</DataTemplate>
</ItemsControl.ItemTemplate>
</ItemsControl>
ListBox
本质上是相同的控件,但为您提供了一些 'default' 好东西,例如在项目太多时滚动(使用虚拟化)的能力,select项,等等。您可以从 ItemsControl 获得这些功能,但您需要自己实现或至少配置它们。 ListBox 只是已经完成了。但绝对 "heavier" 比 ItemsControl,所以选择最合适的。
总之.. 我写了那篇文章只是因为我今天心情不好。但是您确实需要阅读更多有关 ItemsControl 和 Bindings 的内容。在 WPF 中,您几乎从不将东西放在 UI "manually from code" 上。实际上我不应该写那么多,因为专家们已经涵盖了所有这些。请阅读 this excellent series of articles by Dr.Wpf。尤其是 "I" 一章,因为它与您所问的内容完全相关,但我真的建议您全部阅读。它们有些详细,对某些读者来说有点过分,但它们可以让您了解手头有哪些很棒的工具,这是您急需的概述。
从数据库加载数据后(假设我们加载了课程),我想在列表中显示它们。我读过您可以使用 UserControl
动态添加内容,但这些示例专门用于动态更改内容,而不是显示结果列表。
我想要的是创建一个 XAML 模板并为每个列表项实例化一次,然后将其添加到列表中(换句话说,将其添加到一个 StackedPanel
)。我怎样才能做到这一点?另外,我应该使用 Page
还是 UserControl
?
这正是 ListBox
和 ItemsControl
控件创建的内容。 ListBox是ItemsControl的增强版,所以我只说后者,基本的。
ItemsControl
包含名为 ItemsSource
的依赖项 属性。在那里传递一个集合,ItemsControl 将生成一个 "panel",其中包含从该来源获取的 "views" 个项目。
默认情况下,ItemsControl 使用 StackPanel 作为面板,但如果需要,您可以通过 ItemPanel
属性.
默认情况下,ItemsControl 使用默认的 WPF 模板匹配来为每个项目生成和呈现视图。但是,您可以专门使用 ItemTemplate
属性 来设置 DataTemplate
来指示视图的外观。
示例:
<!-- simple vertical/StackPanel list -->
<ItemsControl ItemsSource="{Binding MyItems}">
<ItemsControl.ItemTemplate>
<!-- the template of a single Item -->
<!-- note that I'm setting it here explicitely -->
<!-- but the ItemTemplate prop could have been bound, resourcized, etc -->
<DataTemplate>
<Border BorderThickness="1">
<!-- reads a ShoeSize from the items from MyItems -->
<TextBlock Text="{Binding ShoeSize}" />
</Border>
</DataTemplate>
</ItemsControl.ItemTemplate>
</ItemsControl>
<!-- simple horizontal/StackPanel list -->
<ItemsControl ItemsSource="{Binding MyItems}">
<ItemsControl.ItemsPanel>
<ItemsPanelTemplate>
<StackPanel Orientation="Horizontal" />
</ItemsPanelTemplate>
</ItemsControl.ItemsPanel>
<ItemsControl.ItemTemplate>
<DataTemplate>
<Border BorderThickness="1">
<TextBlock Text="{Binding ShoeSize}" />
</Border>
</DataTemplate>
</ItemsControl.ItemTemplate>
</ItemsControl>
<!-- you can use any panel and any itemtemplate -->
<ItemsControl ItemsSource="{Binding MyXYPoints}">
<ItemsControl.ItemsPanel>
<ItemsPanelTemplate>
<!-- any Panel is OK! even plain canvas -->
<Canvas />
</ItemsPanelTemplate>
</ItemsControl.ItemsPanel>
<ItemsControl.ItemTemplate>
<DataTemplate>
<!-- just remember that in canvas there's no autolayout -->
<!-- so you need to set the coords on each item! -->
<Ellipse Width="2" Height="2"
Canvas.Left="{Binding PositionX}"
Canvas.Top="{Binding PositionY}" />
</DataTemplate>
</ItemsControl.ItemTemplate>
</ItemsControl>
ListBox
本质上是相同的控件,但为您提供了一些 'default' 好东西,例如在项目太多时滚动(使用虚拟化)的能力,select项,等等。您可以从 ItemsControl 获得这些功能,但您需要自己实现或至少配置它们。 ListBox 只是已经完成了。但绝对 "heavier" 比 ItemsControl,所以选择最合适的。
总之.. 我写了那篇文章只是因为我今天心情不好。但是您确实需要阅读更多有关 ItemsControl 和 Bindings 的内容。在 WPF 中,您几乎从不将东西放在 UI "manually from code" 上。实际上我不应该写那么多,因为专家们已经涵盖了所有这些。请阅读 this excellent series of articles by Dr.Wpf。尤其是 "I" 一章,因为它与您所问的内容完全相关,但我真的建议您全部阅读。它们有些详细,对某些读者来说有点过分,但它们可以让您了解手头有哪些很棒的工具,这是您急需的概述。