Search code examples
c#uwppivotitem

UWP Pivot control clears its content when I navigate to a other page and goes back


I have a UWP page with a pivot control. I am using MVVM pattern where the ItemsSource property of the pivot is bound to an observable collection of my viewmodels. I am using the ItemTemplateSelector of the pivot to select the appropriate DataTemplate for each view model based on the Pivot SelectedItem which in turn is bound to the selected view model.

Here the is XAML that I am using:

<Pivot  Grid.Column="1" Grid.Row="1" Grid.RowSpan="2" Margin="10" 
IsHeaderItemsCarouselEnabled="False" 
ItemsSource ="{x:Bind MainPageViewModel.EditViewModels}"  
SelectedItem="{x:Bind MainPageViewModel.SelectedEntityViewModel,Mode=TwoWay}"
ItemTemplateSelector="{StaticResource DetailViewTemplateSelector}"  >
<Pivot.HeaderTemplate>
    <DataTemplate x:DataType="viewModel:DetailViewModelBase">
        <StackPanel Orientation="Horizontal">
            <TextBlock Text="{Binding TabHeader,Mode=OneWay}" FontSize="12" 
               VerticalAlignment="Center"/>
       </StackPanel >
    </DataTemplate>
</Pivot.HeaderTemplate>
</Pivot>

Within the same page, I have a navigation view where the navigationItem click event creates a new view model based on the selected item and adds it to the observable collection MainPageViewModel.EditViewModels and set the SelectedViewModel to the newly created one.

The application works fine as expected working arround implicit DataTemplate that is in WPF and missing in UWP. The only problem I am having is that when I navigate from the page that contains the Pivot controls and comes back, then all the Pivot Items are cleared and not showed.

I have set in the page constructor this.NavigationCacheMode = Windows.UI.Xaml.Navigation.NavigationCacheMode.Required and did not override the NavigateTo method.

If I set my usercontrols within the Pivot Items directly without using DataTemplate selector then the Pivot items are maintained when I come back to the page. The pivot items are cleared only when I use the ItemTemplateSelector.

Any help will be greatly appreciated. I spent more than four days on it without being able to figure out the problem.

Thanks in advance


Solution

  • I took a look at your sample and noticed your MainCrudPage_Loaded method is always creating a new instance of TabelaWindow_ViewModel and assigning it to your MainPageViewModel property and DataContext:

    private async void MainCrudPage_Loaded(object sender, RoutedEventArgs e)
    {
        MainPageViewModel = new TabelaWindow_ViewModel();// Sinergia.UWP.BootStrap.AppContainer.Container.Resolve<Sinergia.UWP.ViewModels.Window.TabelaWindow_ViewModel>();
        //await MainPageViewModel.LoadAsync();
        DataContext = MainPageViewModel;
        //naviView.DataContext = MainPageViewModel.NavigationVM;
        this.Bindings.Update();
    }
    

    As the Loaded event is always called, regardless of whether the Page is cached, you are effectively overwriting the cached data View Model data when you navigate back. As the page cache reuses the existing instance of MainPage, the MainPageViewModel and DataContext are already populated when you return to the page (you can check this by putting a breakpoint at the beginning of the MainCrudPage_Loaded method.

    If you update your sample to the following, you will see what I mean:

    private async void MainCrudPage_Loaded(object sender, RoutedEventArgs e)
    {
        if (null == DataContext)
        {
            MainPageViewModel = new TabelaWindow_ViewModel();// Sinergia.UWP.BootStrap.AppContainer.Container.Resolve<Sinergia.UWP.ViewModels.Window.TabelaWindow_ViewModel>();
            //await MainPageViewModel.LoadAsync();
            DataContext = MainPageViewModel;
        }
        //naviView.DataContext = MainPageViewModel.NavigationVM;
        this.Bindings.Update();
    }
    

    I hope that helps.