ItemsControl + NavigationRequest

Mar 25, 2013 at 5:04 PM
Hi List
my MainRegion looks like this:
<TabControl VerticalContentAlignment="Stretch" HorizontalContentAlignment="Stretch" Foreground="#FF546780"
                        ItemContainerStyle="{DynamicResource TabHeaderStyle}"
                        prism:RegionManager.RegionName="{x:Static infra:RegionNames.MainRegion}">

                <TabControl.Background>
Now i'm adding a UserControl with a ListView to select Items by using RequestNavigate.
For each Selected Item there is another UserControl added to display-edit with RequestNavigate as well.
When selecting another Module from my Menu, only the 'Display-Edit' UC's are removed, the first UC, the ListView is untouched. Neither the OnNavigated....... nor the IsNavigationTarget methods are called.
If the ListView is the only Control in MainRegion all works as expected (TabItem is removed).
Did i have to add the 'Display-Edit' UC's by Region.Add(view) or is there any better idea.

Thanks
Peter

Any idea's.
Developer
Mar 25, 2013 at 9:34 PM
Hi Peter,

It would be helpful if you could provide us with more information or a couple code snippets about how you are adding and removing the views from the TabControl region, so that we could have a better understanding of your scenario and help you further in this.

Regards,

Damian Cherubini
http://blogs.southworks.net/dcherubini
Mar 25, 2013 at 9:57 PM
Hi,
there is nothing Special.
Just as in the doc's
In the ListView, started by Requestnavigate, i start an regionManager.RequestNavigate ("MyeditView,.........) from a Command.
In MyEditView i check with IsNavigationTarget if i have to create a new View or use the one already started.
So all my Views are created with RequestNavigate.
This is why i'm thinking that all the views should be removed when a RequestNavigate to some other bunch of views are called.

If you need more code, i will send them when i'm back in Office.
Peter
Mar 26, 2013 at 8:24 AM
Hi and good morning,
here we are:

Command-Execute Method to start the ListView:
private void RunList()
     {
        var region = this.regionManager.Regions[RegionNames.MainRegion];
        var uri = new Uri(WellKnownNames.EmpListView,UriKind.Relative);
        region.RequestNavigate(uri,base.NavigationCallback);
     }
Command inside listeView to run EditView:
private void DoSelectedEmployeeCommand()
    {
        UriQuery query = new UriQuery();
        query.Add(WellKnownNames.EmpRegionContext, SelectedEmployee.Id.ToString());
        regionManager.RequestNavigate(RegionNames.MainRegion,
                                      new Uri(WellKnownNames.EmpEditView + query.ToString(), UriKind.Relative));


    }
Methodes in EditView :

public override void OnNavigatedTo(Microsoft.Practices.Prism.Regions.NavigationContext navigationContext)
    {       
        if (Employee == null) {
            var empId = navigationContext.Parameters[WellKnownNames.EmpRegionContext];
            Employee = employeeService.Get(Guid.Parse(empId));
            VmTitle = Employee.Lastname;
        }
    }


    public override void OnNavigatedFrom(Microsoft.Practices.Prism.Regions.NavigationContext navigationContext)
    {
        if (navigationContext.Uri.ToString() != WellKnownNames.EmpEditView) {
            myKeepAlive = false;
        }else {
            myKeepAlive = true;
        }
    }

    public override bool IsNavigationTarget(Microsoft.Practices.Prism.Regions.NavigationContext navigationContext)
    {
        var empId = navigationContext.Parameters[WellKnownNames.EmpRegionContext];

        if (!String.IsNullOrWhiteSpace(empId) && Employee != null && Employee.Id.ToString() == empId)
                  return true;    
         return false;
    }

    private bool myKeepAlive;

    public override bool KeepAlive {
// get { return true; }
        get { return myKeepAlive; }
    }
Hope this was helpfull

Peter
Developer
Mar 27, 2013 at 9:50 PM
Hi Peter,

After checking your code I believe the "problem" you are experiencing is related to when you are setting the keepAlive attribute of the views. Basically, the OnNavigatedFrom method is only executed in the view that is being "navigated from" or in other words, in the currently active view before the NavigationRequest. For example, if you have the following views in the TabControl and you navigate to an OtherView:
  • ListView
  • EditView(1)
  • EditView(2) <-- Selected view
The OnNavigatedFrom will only be executed in the EditView(2), so only its keepAlive attribute will be changed to false while the others will keep being true. This is why only the visible view is being removed. Therefore, it doesn't seem that this approach will be effective to achieve the functionality you are looking for.

If you wish to "clear" the region when you inject a view from a different module, a possible approach could be to keep track of what module is being used and before navigating to a view from another module, remove all the views in the region. There are several approaches you can follow to do this. For example, you could use the EventAggregator and subscribe all the views (i.e. ListView, EditView, etc) to a certain event, so that in their corresponding handlers, they change the keepAlive attribute to false. Hence, before navigating to the other view, you can publish this event to set all the KeepAlive properties off all the views to false so that they are removed as expected.

I hope this helps,

Damian Cherubini
http://blogs.southworks.net/dcherubini
Apr 2, 2013 at 6:48 AM
Hi Damian,
i will follow your approach
Thanks
Peter