【发布时间】:2015-03-18 21:10:55
【问题描述】:
我在 MVVM 项目中有一个现有的 ViewModel 和 View。实际上,此视图以特定样式的方式呈现项目集合。我将把这个现有的 ViewModel 称为“CollectionPresenter”。
到目前为止,这在 XAML 中已呈现如下:
<Grid>
<ns:CollectionPresenter />
</Grid>
现在,我希望在选项卡视图中理想地提供这些“CollectionPresenter”视图模型的动态集合。
我的方法是定义这些“CollectionPresenters”的可观察集合,首先在构建父视图模型时创建它们。上面的 XAML 然后更改为如下所示:
<TabControl ItemsSource="{TemplateBinding CollectionPresenters}">
<TabControl.ItemTemplate>
<DataTemplate>
<TextBlock Text="{Binding CollectionPresenterTitle}">
</DataTemplate>
<TabControl.ItemTemplate>
<TabControl.ContentTemplate>
... this is where things get confusing
</TabControl.ContentTemplate>
<TabControl>
您可以在上面看到我的问题是 ContentTemplate。
当我加载它时,我得到一个选项卡控件,它的选项卡数量与我可观察的“CollectionPresenter”对象集合一样多。
但是,选项卡控件的内容始终为空。
这种方法正确吗?还有更好的方法吗?
编辑:添加一些额外的东西以使其更清晰
我尝试了以下方法,但它不起作用。带有选项卡控件的 XAML(绑定到“事物”工作正常):
<TabControl ItemsSource="{TemplateBinding Things}">
<TabControl.ItemTemplate>
<DataTemplate DataType="{x:Type viewModels:Thing}">
<TextBlock Text="{Binding ThingName}" Width="200" Background="Blue" Foreground="White"/>
</DataTemplate>
</TabControl.ItemTemplate>
<TabControl.ContentTemplate>
<DataTemplate DataType="{x:Type viewModels:Thing}">
<TextBlock Text="{Binding ThingName}" Width="500" Height="500" Background="Blue" Foreground="White"/>
</DataTemplate>
</TabControl.ContentTemplate>
</TabControl>
“事物”可观察集合的定义(位于带有选项卡控件的 XAML 的模板化父对象 (ParentObject) 内):
public static readonly DependencyProperty ThingsProperty =
DependencyProperty.Register("Things", typeof(ObservableCollection<Thing>), typeof(ParentObject), new PropertyMetadata(null));
public ObservableCollection<Thing> Things
{
get { return (ObservableCollection<Thing>)GetValue(ThingsProperty); }
set { SetValue(ThingsProperty, value); }
}
“事物”视图模型的精简版:
public class Thing : ViewModelBase
{
public Thing()
{
}
public void Initialise(ObservableCollection<Thing> things, string thingName)
{
Things = things;
ThingName = thingName;
}
public static readonly DependencyProperty ThingNameProperty =
DependencyProperty.Register("ThingName", typeof(string), typeof(Thing), new PropertyMetadata(null));
public string ThingName
{
get { return (string)GetValue(ThingNameProperty); }
set { SetValue(ThingNameProperty, value); }
}
}
【问题讨论】:
-
你可能想看看我对WPF MVVM navigate views问题的回答。
-
感谢@Sheridan,但没有帮助。我遇到的问题是 TabItem 的 ItemsSource 包含一组视图模型 - 但是当我定义 TabControl.ItemTemplate 并使用 {Binding ....} 引用视图模型的属性时它不起作用 - 并且视觉树不显示视图模型...它仅显示选项卡项,在 ItemTemplate 中具有可视项,但没有引用 ItemsSource 集合中的实际项...
-
您的方法有缺陷,这就是为什么我为您提供了如何正确操作的链接。使用您的方法,您必须一次加载所有视图模型,这是对 RAM 的巨大且不必要的浪费。
-
视图模型需要预先加载,因为选项卡纯粹是为了让屏幕上应该的内容同时分布在 2-5 个选项卡上(因为在单个选项卡上没有物理空间)。基本上我们不希望动态加载视图模型,我们希望它们都被预加载 - 但只是在屏幕上通过选项卡访问。
-
链接的答案也向您展示了您的问题的解决方案......我将添加一个答案。