2009-01-07 27 views
18

所以我建立,将有大量的Windows应用程序,都具有相同的基本布局:如何在WPF中创建模板窗口?

  1. 一个主窗口
  2. 在右上角
  3. 标题块
  4. A A标志状态显示器底部
  5. 窗口特定控件的区域。

目前我必须在每个窗口重新创建这个结构。理想情况下,我希望将此布局编码到一个位置,也许放到一个自定义Window子类中以便于使用。有没有人有任何线索如何开始,或有类似问题的以往经验?

回答

31

您可以创建一个新的ControlTemplate,以一个窗口为目标来完成此操作,如下所示。

<ControlTemplate x:Key="WindowControlTemplate1" TargetType="{x:Type Window}"> 
    <Border 
     Background="{TemplateBinding Background}" 
     BorderBrush="{TemplateBinding BorderBrush}" 
     BorderThickness="{TemplateBinding BorderThickness}" 
     > 
     <Grid> 
      <Grid.RowDefinitions> 
       <RowDefinition Height="Auto"/> 
       <RowDefinition Height="0.93*"/> 
       <RowDefinition Height="Auto"/> 
      </Grid.RowDefinitions> 

      <Grid.ColumnDefinitions> 
       <ColumnDefinition Width="0.21*"/> 
       <ColumnDefinition Width="0.79*"/> 
      </Grid.ColumnDefinitions> 

      <ContentPresenter 
       Grid.ColumnSpan="2" 
       Grid.Row="1" 
       Content="{TemplateBinding Content}" 
       ContentTemplate="{TemplateBinding ContentTemplate}" 
       /> 
      <ResizeGrip 
       HorizontalAlignment="Right" 
       x:Name="WindowResizeGrip" 
       VerticalAlignment="Bottom" 
       IsTabStop="False" 
       Visibility="Collapsed" 
       Grid.Column="1" 
       Grid.Row="2" 
       /> 
      <TextBlock Text="My Logo" /> 
      <TextBlock Grid.Column="1" Text="My Title"/> 
      <StatusBar Height="20" Grid.ColumnSpan="2" Grid.Row="2"/> 
     </Grid> 
    </Border> 

    <ControlTemplate.Triggers> 
     <MultiTrigger> 
      <MultiTrigger.Conditions> 
       <Condition Property="ResizeMode" Value="CanResizeWithGrip"/> 
       <Condition Property="WindowState" Value="Normal"/> 
      </MultiTrigger.Conditions> 
      <Setter Property="Visibility" TargetName="WindowResizeGrip" Value="Visible"/> 
     </MultiTrigger> 
    </ControlTemplate.Triggers> 
</ControlTemplate> 
-3

为什么你使用“大量的窗户?”为什么不只是一个带有选项卡控件的单个窗口?或者带有用户控件的单个窗口?

无论如何,要回答您的问题,usercontrols是您希望获得您所描述的功能的一种方法。

创建一个新的Window类,并让它具有“Childrens”属性,该属性允许将某个对象嵌入到希望“窗口特定控件”去向的停靠面板中。

在启动新窗口时,实例化窗口类型和具有特定控件的用户控件,将用户控件添加到窗口的Children属性中,然后显示该窗口。你甚至可以绑定事件处理程序,DataContexts和目前还没有的。

+1

为什么这么多downvotes?对我来说这似乎是一个有效的问题,也许不是理想的答案,但对于正确的情况绝对值得考虑。 – MikeKulls 2014-09-02 07:25:26

+0

因为虽然它提出了一个解决方案,但它并没有真正回答这个问题。另外,它是解决方案的高度强力方法。在所有的实际中,我都将它描述为一种通过WPF解决它的WINFORMS方法(选定的答案是)。 – 2014-09-02 13:18:52

+0

也许你对“带有选项卡控制的单个窗口”位过于关注?在正确的情况下,具有可互换用户控件的单一窗口是完美有效的解决方案。这是避免代码重复的唯一解决方案,如果您有超过1个窗口,那么无论多小,都需要在每个窗口中复制某种类型的代码。如果需要更改,那么该代码需要在多个位置进行更改。这两种方式都不是什么问题,但它确实值得考虑。 – MikeKulls 2014-09-17 03:26:36

6

如果你足够勇敢采取一个大的架构转变,你可以考虑来自&模式CompositeWPF(以前代号为Prism)在微软的实践家伙。

您感兴趣的是能够在shell(即窗口)中定义“区域”,然后使用视图来填充区域。它使用Model-View-Presenter模式允许从模型中独立开发“视图”,因为随着时间的推移shell可以很容易地重新定位,因为shell只定义区域并且不直接耦合到其中。原则上,这有助于将壳与视图和视图相互分离,并使单元测试更容易......等等等等等等。

虽然您的情况是CompositeWPF旨在解决的应用程序类型之一,但这是一个巨大的跳跃,并且会让您放慢脚步。

作为CompositeWPF的一部分,您将需要采用各种可能会混淆新手的模式,例如, UnityContainer,控制反转,MVP(或模型/视图/视图模型)和依赖注入。

我记得当我第一次开始使用示例应用程序时感到困惑,因为它不是很明显,甚至一些观点甚至被创建!统一容器将实例化对象并神奇地调用参数化的构造函数。

CompositeWPF是一个优雅的解决方案,但不是一个简单或直接的问题。在我最后的项目中使用了CompositeWPF后,我打算再次将它用于下一个合适的应用程序。

2

最简单的方法是为窗口特定控件创建WPF“页面”,并在主窗口中放置一个“框架”。你甚至可以用这种方式创建一个很好的导航。