Dynamically displaying Items using FlipView and DataTemplateSelector in WinRT
我正在使用 Flipview 和 DataTemplateSelector 来确定在运行时应用哪个 DataTemplate 来显示我的控件中的项目。
我有两个 DataTemplate,一个是静态的,第二个可以被数量不定的项目使用。
目前
我的第一个视图显示:
-“这是一个测试 – 内容”
Followed by 18 other views 看起来像这样:
-“http://www.google.com/0”
-“http://www.google.com/1”
-“http://www.google.com/ 2”
– 依此类推,直到 17
我想要
项目”http://www.google.com/”被分组为 3 on a view。
例如第二个视图会显示:
- “http://www.google.com/ 0, http://www.google.com/ 1, http://www.google.com/ 2”
第三个视图会显示:
- “http://www.google.com/ 3, http://www.google.com/ 4, http://www.google.com/ 5”
等等..
下面是我的代码:
FlipViewDemo.xaml
1
2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 |
<Page.Resources>
<DataTemplate x:Key=“FirstDataTemplate”> <Grid> <TextBlock Text=“{Binding Content}” Margin=“10,0,18,18”></TextBlock> </Grid> </DataTemplate> <DataTemplate x:Key=“SecondDataTemplate”> <TextBox Text=“{Binding Url}”></TextBox> </DataTemplate> <local:MyDataTemplateSelector x:Key=“MyDataTemplateSelector” FirstTextTemplate=“{StaticResource FirstDataTemplate}” SecondTextTemplate=“{StaticResource SecondDataTemplate}”> </local:MyDataTemplateSelector> </Page.Resources> <Grid Background=“{ThemeResource ApplicationPageBackgroundThemeBrush}”> <FlipView x:Name=“itemGridView” ItemTemplateSelector=“{StaticResource MyDataTemplateSelector}” Margin=“265,220,284,162”> </FlipView> </Grid> |
FlipViewDemo.xaml.cs
1
2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 |
public sealed partial class FlipViewDemo : Page
{ public FlipViewDemo() { this.InitializeComponent(); var items = new List<BaseClass>(); items.Add(new FirstItem for (int i = 0; i < 18; i++) public class FirstItem : BaseClass public class SecondItem : BaseClass public class MyDataTemplateSelector : DataTemplateSelector protected override DataTemplate SelectTemplateCore(object item, return base.SelectTemplateCore(item, container); |
我想也许这可以通过组和列表视图来实现。但我不确定如何做到这一点。
这可能是一个愚蠢的问题,但使用谷歌,我找不到答案。英语也不是我的母语;请原谅打字错误。
我认为实现您正在寻找的方法是以更好地代表您想要显示的内容的方式公开数据。然后,您可以使用嵌套控件来显示它。我只是把它放在一起(使用我自己的测试数据)。这可能不是您想要的,但它应该可以帮助您解决问题。
视图模型
在这里,我创建了一个辅助方法来构建包含子集合的集合,每个子集合都有 3 个项目。
1
2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 |
class FlipViewDemo
{ private List<object> mData; public IEnumerable<object> Data public FlipViewDemo() private void AddData(object data) class TemplateSelector : DataTemplateSelector public override DataTemplate SelectTemplate(object item, DependencyObject container) |
Xaml
这里我使用 ItemsControl 来垂直堆叠数据中的项目。每个项目要么是三个对象的列表,要么是一个对象。我对三个对象的列表中的每一个都使用 FlipView,对单个对象使用简单的 ContentPresenter。
1
2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 |
<Page.Resources>
<DataTemplate x:Key=“ListTemplate”> <FlipView ItemsSource=“{Binding}”> <FlipView.ItemTemplate> <DataTemplate> <ContentPresenter Margin=“0 0 10 0” Content=“{Binding}” /> </DataTemplate> </FlipView.ItemTemplate> </FlipView> </DataTemplate> <DataTemplate x:Key=“ObjectTemplate”> <ContentPresenter Margin=“0 0 10 0” Content=“{Binding}” /> </DataTemplate> <local:TemplateSelector x:Key=“TemplateSelector” ListTemplate=“{StaticResource ListTemplate}” ObjectTemplate=“{StaticResource ObjectTemplate}” /> </Page.Resources> <ItemsControl |
注意:您通常不需要模板选择器来处理这样的事情,但是由于您需要在 List<T> 和 Object 之间进行选择,因此我不知道仅使用 < Xaml 中的 x5> 属性,因为 List<T> 是泛型类型。 (我尝试了 {x:Type collections:List`1} 并没有用。)
- 嗨,泽维尔,非常感谢。我试图在模拟器中运行它,但没有得到任何东西,只是黑屏。这对你有用吗?
- 它确实对我有用,但我的设置与您的原始设置略有不同。我让 FlipViewDemo 成为一个单独的类,并将其设置为视图上的数据上下文,而不是将代码放在代码隐藏中。此外,我将它作为常规的 Windows WPF 应用程序而不是 WinRT 运行(因为我没有为此设置)。我只打算将代码作为参考,而不是直接运行示例。我主要想强调解决您的具体问题的领域。
您需要在视图模型中对项目进行分组,并将 ItemsSource 数据绑定到组。在 Flipview 的项目模板中,您可以按组显示项目。
1
2 3 4 5 |
public class PageGroup : PageBase {
public ObservableColection<BaseClass> Items { get; set; } } public ObservableCollection<PageBase> Pages { get; set; } |
1
2 3 4 5 6 7 8 |
<FlipView ItemsSource=“{Binding Pages}”>
<FlipView.ItemTemplate> <DataTemplate DataType=“local:PageGroup”> <ItemsControl ItemsSource=“{Binding Items}” ItemTemplateSelector=“{StaticResource MyDataTemplateSelector}” /> </DataTemplate> </FlipView.ItemTemplate> </FlipView> |
为了以不同于其他页面的方式显示第一页:
1
2 3 4 5 |
public class FirstPage : PageBase {
public string Title { get; } } Pages.Insert(0, new FirstPage()); |
并且您需要在 FlipView 中使用另一个 datatemplaeselector 或隐式数据模板来区分 FirstPage 和 PageGroup
1
2 |
<FlipView ItemsSource=“{Binding Pages}”
ItemTemplateSelector=“{StaticResource PageTemplateSelector}” /> |
您无需担心根据类类型选择合适的模板,您只需在DataTemplate本身中定义类即可。
1
2 3 |
<DataTemplate TargetType=“{x:Type myNamespace:FirstItem}”>
… </DataTemplate> |
您需要通过在页面顶部添加命名空间来指定类的位置:
1
|
xmlns:myNamespace=“clr-namespace:MyApp.MyNamespace”
|
- 嗨迈克,谢谢你的回答。我不明白这如何帮助我在每个视图中显示 3 个项目而不是 1 个
- 我相信他只是说您可以删除模板选择器并更新数据模板本身以在其上定义 TargetType 。这将简化您现有的代码,但它不能回答您的实际问题。
来源:https://www.codenong.com/30397863/