在WPF中的页面之间切换

时间:2014-07-24 11:49:06

标签: c# wpf blend

我想制作一个类似于任何网站中使用的布局 - 标题,侧边栏和页脚保持不变,但中心部分。我有多个页面/窗口在wpf混合C#应用程序中显示,它们完全不同。例如,stackoverflow具有主页的布局和每个问题的另一个布局。这是另一个例子:

first  page second page

我必须在之前的项目中执行此操作并使用单个网格布局,然后,对于每个页面,我必须隐藏()所有这些并显示每个项目位于顶部 -

诀窍是什么?如何在wpf应用程序中执行相同的操作?在一个典型的C#应用​​程序中,我每次都必须打开一个子窗口,但这些日子看起来很难看。

提前谢谢!

3 个答案:

答案 0 :(得分:6)

如果您要在WPF中使用Page,那么您需要阅读MSDN上的Navigation Overview页面。简而言之,您可以使用NavigationService Class在WPF应用程序中的Page之间导航。要从后面的代码更改页面,您可以执行以下操作:

NextPage page = new NextPage();
NavigationService.Navigate(page);

要让用户更改Page,您可以使用<{1}}中的Hyperlink Class

Page

要设置所需的页面,您必须将<Hyperlink NavigateUri="pack://application:,,,/AppName;component/Pages/NextPage.xaml"> Navigate to Next Page </Hyperlink> 加载到Frame,然后可以在Page中随意布局:

MainWindow.xaml

答案 1 :(得分:4)

听起来你需要一个自定义的usercontrol和一些数据绑定。

您可以将XAML中的DataTemplates声明为模型类型为key的资源,以便WPF自动选择正确的DataTemplate:

  • 有一个主ViewModel,它公开了一个ImageSourceViewModel属性。该属性将根据需要返回CameraSourceViewModel或FileSourceViewModel。

  • 在您的页面中,DataContext将是主ViewModel,您将拥有如下XAML:

然后,

<Page x:Class="Page1"
  xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
  xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
  xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" 
  xmlns:d="http://schemas.microsoft.com/expression/blend/2008" 
  xmlns:my="clr-namespace:WpfApplication1"
  mc:Ignorable="d" 
  d:DesignHeight="300" d:DesignWidth="300"
  Title="Page1">
<Page.Resources>
    <DataTemplate DataType="{x:Type my:CameraSourceViewModel}">
        <my:CameraSourceView/>
    </DataTemplate>
    <DataTemplate DataType="{x:Type my:FileSourceViewModel}">
        <my:FileSourceView/>
    </DataTemplate>
</Page.Resources>
<Grid>
    <ContentControl Content="{Binding ImageSourceViewModel}"/>
</Grid>

我应该指出,此示例使用MVVM模式允许viewmodel层决定中间的内容。希望这很清楚,如果没有,请给我一个喊叫,我会尝试扩展它!

答案 2 :(得分:1)

假设我有主视图模型,我在其中创建了一个CurrentPage属性,告诉您要显示哪个页面。

/// <summary>
/// Returns the page ViewModel that the user is currently viewing.
/// </summary>
public ViewModelBase CurrentPage
{
    get { return _currentPage; }
    private set
    {
        if (value != _currentPage)
        {
            if (_currentPage != null)
                _currentPage.IsCurrentPage = false;

            _currentPage = value;

            if (_currentPage != null)
                _currentPage.IsCurrentPage = true;
            RaisePropertyChanged(() => CurrentPage);
        }
    }
}

在您的xaml中,您可以在某种控制下绑定您的页面。让我们说我在Border元素中做这件事。

<!-- CURRENT PAGE AREA -->
<Border Background="White" Grid.Column="1" Grid.Row="0">
    <HeaderedContentControl Content="{Binding Path=CurrentPage}" 
        Header="{Binding Path=CurrentPage.DisplayName}" />
</Border>

您可以在资源中为视图模型定义视图,如下所示:
(部分完成XAML)

<UserControl x:Class="BAT.View.BATWizardView"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" 
        xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
        xmlns:view="clr-namespace:BAT.View"
        xmlns:viewmodel="clr-namespace:BAT.ViewModel"
        mc:Ignorable="d" 
        d:DesignHeight="350" d:DesignWidth="600">

   <UserControl.Resources>
      <!-- These four templates map a ViewModel to a View. -->
      <DataTemplate DataType="{x:Type viewmodel:MyComparisonViewModel1}">
          <view:MyView1 />
      </DataTemplate>

      <DataTemplate DataType="{x:Type viewmodel:MyComparisonViewModel2}">
          <view:MyView2 />
      </DataTemplate>

   </UserControl.Resources>
   <Grid>
      <Border Background="White" Grid.Column="1" Grid.Row="0">
         <HeaderedContentControl Content="{Binding Path=CurrentPage}" 
                      Header="{Binding Path=CurrentPage.DisplayName}" />
      </Border>
   </Grid>
</UserControl>

看看是否有帮助。