I've made an example to illustrate the "right WPF way" to go about this scenario. Again, it might not match the code you already have, but it should give you some ideas on how to adapt your code. First, the code-behind:
public partial class TabItemBinding : Window
{
public ObservableCollection<TextItem> Items { get; set; }
public TabItemBinding()
{
Items = new ObservableCollection<TextItem>();
Items.Add(new TextItem() { Header = "1", Content = new TextBox() { Text = "First item" } });
Items.Add(new TextItem() { Header = "2", Content = new TextBox() { Text = "Second item" } });
Items.Add(new TextItem() { Header = "3", Content = new TextBox() { Text = "Third item" } });
InitializeComponent();
}
}
public class TextItem
{
public string Header { get; set; }
public FrameworkElement Content { get; set; }
}
Nothing crazy here, I'm just creating a model class and setting up a collection of that class. The real goodness happens in the XAML:
<Window x:Class="TestWpfApplication.TabItemBinding"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="TabItemBinding" Height="300" Width="300"
DataContext="{Binding RelativeSource={RelativeSource Self}}">
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
<RowDefinition Height="*"/>
</Grid.RowDefinitions>
<ToolBar Grid.Row="0">
<Button Command="Undo">Undo</Button>
</ToolBar>
<TabControl Grid.Row="1" ItemsSource="{Binding Items}">
<TabControl.ItemContainerStyle>
<Style TargetType="TabItem">
<Setter Property="Header" Value="{Binding Header}"/>
<Setter Property="Content" Value="{Binding Content}"/>
</Style>
</TabControl.ItemContainerStyle>
</TabControl>
</Grid>
I hook up the Button
to ApplicationCommands.Undo
, which will automatically take care of the undo for us as long as we have an active editing TextBox
. The TabControl
itself is bound to the collection we made in the code-behind, which will provide a header and some text to edit. And any edits we make will be undo-able. The result:
By the way, it's important to note that the undo command will automatically disable itself if there is not an active editing context. So if there are no tab pages, it will be disabled without any extra code on our part.