PRISM + Tabs =痛苦

时间:2009-10-23 15:59:38

标签: wpf prism tabcontrol tabitem

我很难尝试使用PRISM 2.0 for WPF的一个非常简单的场景。我希望我的应用程序的主要工作区域是TabControl。每次添加视图时,我都希望它在TabItem上显示为TabControl

听起来很容易吗?

我的区域,位于我的Shell.XAML中,如下所示:

<Controls:TabControl 
    Name="MainRegion" 
    cal:RegionManager.RegionName="{x:Static Infrastructure:RegionNames.TabRegion}"
    ItemContainerStyle="{StaticResource ShellTabItemStyle}" />

样式:ShellTabItemStyle看起来像这样:

<Style x:Key="ShellTabItemStyle" TargetType="{x:Type TabItem}">
    <Setter Property="Header" Value="{Binding Content.DataContext.HeaderInfo, RelativeSource={RelativeSource Self}}" />
</Style>

这应该将Header的{​​{1}}设置为视图的TabItem上的HeaderInfo属性。 (我从this article得到了这个想法)我的观点的DataContext非常简单DataContext,其上有Presenter属性:

HeaderInfo

我的视图是一个简单的WPF用户控件,如下所示:

public string HeaderInfo = "The Header Text";

到目前为止,这么好。如果我将视图添加到该区域,我将获得一个选项卡控件,并获得一个文本设置为“标题文本”的选项卡。我的问题是标签上绝对没有内容出现。我的观点包含一个简单的 <StackPanel> <TextBox Text="Hello World" Name="MyTextBox"></TextBox> <Image Source="..SomeImage.PNG" Name="MyImage"></Image> </StackPanel> 和一个Image,但它们都没有显示在TextBox中。如果我打破Snoop并环顾四周,就看不到图像了。

我在这里缺少什么 - 有更简单的方法吗?

3 个答案:

答案 0 :(得分:3)

我无法得到任何建议的答案。广泛的谷歌搜索也没有帮助。我在周末对这个问题进行了一些思考,我想的更多,我发现这个方法有一点代码味道就越多。你将一个视图注入你的选项卡区域......发生了一些神奇的事情并添加了一个选项卡......你必须添加一些难以理解的动态绑定到存储在某个文件中的某些XAML样式,这可能会也可能不会设置你的标题文本。如果这个中的任何一个元素只是有点不对,那么你就不会得到错误,但它不起作用。

在我看来,除非你对PRISM,模型和XAML有深刻的理解,否则它既脆弱又易于破坏,并且相当容易破解。幸运的是,有一种更好,更简单的方法:

只需创建一个名为 TabRegionView 的视图,其中只包含一个空白的TabControl。您可能希望将其添加到Shell.xaml中。创建名为 InjectTabView 的事件,其具有UserControl类型的Payload,并在 TabRegionView 控件中订阅此事件。当事件在 TabRegionView 中触发时,您手动创建TabItem并将视图添加到TabItem,如下所示:

public void TabAdded(UserControl view)
{
    var item = new TabItem();
    item.Content = view;
    item.IsSelected = true;
    item.Header = "Header Text";
    mainTab.Items.Add(item);
}

如果要将视图显示为新选项卡,则代码如下所示:

    var view = new View(params);
    _eventAggregator.GetEvent<InjectTabViewEvent>()
        .Publish(view);

这将由 TabRegionView 选取,视图将作为新标签添加。您可以轻松地将View包含在包含标题文本,图像和bool的某些类型的线束中,以指示是否应自动选择该选项卡。

恕我直言,这种技术具有双重优势,可让您直接控制正在发生的事情并且更容易理解。

我非常有兴趣从任何PRISM officianados获得对此的意见。

答案 1 :(得分:2)

如果您使用的是RegionManager,则需要激活您的视图。可能有一段代码要将视图添加到区域,您还需要告诉该区域激活它。

public void AddViewToRegion(IRegion region, object view)
{
     region.Add(view);
     region.Activate(view);
}

看起来很傻,但如果你不这样做,你会得到你所看到的行为。我发现这有点令人沮丧,但它很容易修复。如果您至少不激活添加的第一个视图,则添加多个选项卡时,行为甚至更加奇怪。

我的理解是,如果你不这样做,视图永远不会成为可视化树的一部分(这是TabControl在标签没有时停用(从可视树中删除)这一事实的副作用“在前面”。这对某些操作很有用,但是这样的事情会有点不稳定。

答案 2 :(得分:0)

一些随意的想法:

  • 尝试从TabControl中删除样式
  • Snoop工具的帮助下检查可视化树。您应该在TabControl下看到带有视图的UserControl的TabItem。接下来,您可以检查UserControl及其子项(视图的内容)有什么问题。它们可能因某种原因而隐藏起来。
  • 要考虑的其他事情 - RegionAdapter。 RegionAdapters负责调整区域的视图以托管UIControl。