- Purpose: we want to be able to intervent before leaving a TabItem and for example to cancel before the new TabItem has been selected, if necessary.
- Problem: the wpf TabControl doesn't know SelectionChanging respectively PreviewSelectionChanged event (by the way Teleriks RadTabControl knows it).
- Prerequisites: wpf and catel framework.
- Solution:
ShellView.xaml
<catel:datawindow ...loaded="DataWindow_Loaded">
...
<tabcontrol x:name="TabCtrlMain" issynchronizedwithcurrentitem="True">
<tabitem regions:regionmanager.regionname="{x: Static utils:RegionNames.MainContentRegion}">
<tabitem regions:regionmanager.regionname="{x: Static utils:RegionNames.AuswertungRegion}">
ShellView.xaml.cs
#region Properties
...
///
/// We want the ViewModel know the TabItems collection of the TabControl so it can observe the navigation between the
/// TabItems in a manner where it is e.g. possible to prevent the navigation if a ViewModel is dirty.
///
///
/// credits:
/// http://joshsmithonwpf.wordpress.com/2009/09/04/how-to-prevent-a-tabitem-from-being-selected/
/// http://marlongrech.wordpress.com/2008/11/22/icollectionview-explained/
///
[ViewToViewModel]
public ICollectionView TabItemsCollection
{
get { return ( ICollectionView)GetValue(TabItemsCollectionProperty); }
set { SetValue(TabItemsCollectionProperty, value); }
}
// Using a DependencyProperty as the backing store for TabItemsCollection. This enables animation, styling, binding, etc...
public static readonly DependencyProperty TabItemsCollectionProperty =
DependencyProperty.Register("TabItemsCollection" , typeof (ICollectionView ), typeof(ShellView ), new UIPropertyMetadata (null ));
#endregion
#region Methods
...
///
/// This method is called after the ViewModel is initialized. So we can initialize here the TabItemsCollection,
/// since we are not able to populate it when registering.
///
///
///
private void DataWindow_Loaded( object sender, RoutedEventArgs e)
{
if (TabItemsCollection == null)
TabItemsCollection = CollectionViewSource.GetDefaultView(TabCtrlMain.Items);
}
#endregion
ShellViewViewModel.cs
#region Constructor
public ShellViewModel()
{
...
TabItemsCollection.CurrentChanging += OnTabItemsCollectionCurrentChanging;
...
}
#endregion
#region Properties
...
///
/// Gets or sets the TabItemsCollection property value which is populated from View.
///
public ICollectionView TabItemsCollection { get ; set ; }
#endregion
#region Methods
...
///
/// Observe the navigation between the TabItems, save BEFORE leaving the current TabItem.
/// For this to run the TabControl within the View needs to set IsSynchronizedWithCurrentItem="True".
///
///
///
private void OnTabItemsCollectionCurrentChanging(object sender, CurrentChangingEventArgs e)
{
var collection = sender as ItemCollection;
if (collection != null)
{
var itemCollection = collection;
var currentTabItem = (TabItem)itemCollection.CurrentItem;
...
}
}
...
///
/// Unsubscribe.
///
protected override void Close()
{
TabItemsCollection.CurrentChanging -= OnTabItemsCollectionCurrentChanging;
}