TabControl- preventing user from changing the selected tab: MessageBox causing bug


Staff member
I've been pounding away at this issue for a little while, and have only found part of the solution.

I'm trying to set up a TabControl so that I can in some cases prevent the user from changing the currently selected tab. When the user is prevented from changing the currently selected tab, then they are shown a dialog box.

I have already read the following documents:

<li><a href="">WPF - reset ListBox scroll position when ItemsSource changes</a></li>
<li><a href="" rel="nofollow noreferrer"></a></li>
<li><a href="" rel="nofollow noreferrer"></a></li>
<li><a href="" rel="nofollow noreferrer"></a></li>

I have implemented the solution indicated in the 3rd link (though all of the above create the same error seen below). And it works, <strong>but</strong>...

Things mess up thoroughly if the user does the following:

<li>attempts to change the tab when such an action is disallowed. The MessageBox pops up with the error.</li>
<li>the user clicks "OK" and is returned to the original window.</li>
<li>the user tries again to change the tab. <strong>No MessageBox appears.</strong></li>
<li>if the user minimizes the window, and then maximizes it again, then the MessageBox that was supposed to appear earlier appears.</li>
<li>the user clicks "OK" and is returned to the original window... <strong>but the tab has been changed to the one they selected before, even though they should not be able to change tabs</strong>. </li>

This is obviously <strong>not</strong> ideal behavior. <strong>Why isn't the MessageBox appearing the second time, and why is the tab changing when it should be disallowed from doing so?</strong>

If I remove the MessageBox part, it works fine.

Here is the code for the TabControl.SelectionChanged event handler:

bool _isChanging = false;

    private void tabControlForNavigation_SelectionChanged(object sender, SelectionChangedEventArgs e)
        if (!_isChanging &amp;&amp; canChangeTabs.IsChecked.HasValue)
            _isChanging = true;

            bool canLeave = canChangeTabs.IsChecked.Value;  //normally this would be replaced by a check in the ViewModel

            if (!canLeave)
                int prevIndex = tabControlForNavigation.Items.IndexOf(tabControlForNavigation.SelectedContent);
                tabControlForNavigation.SelectedIndex = prevIndex;
                MessageBox.Show("Can't change tabs!"); //if I comment out this line, everything works fine.

            _isChanging = false;

I am using MVVM to implement this. The Window looks like this:

&lt;Window x:Class="TestTabControlSwitching.MainWindow"
        &lt;RowDefinition Height="Auto" /&gt;
        &lt;RowDefinition /&gt;
    &lt;CheckBox x:Name="canChangeTabs"
              Content="Can Change Tabs"
              IsChecked="True" /&gt;
    &lt;TabControl x:Name="tabControlForNavigation"
                ItemsSource="{Binding Collection}"
                SelectedItem="{Binding SelectedItem}"
                &lt;ContentPresenter Content="{Binding Path=Name}" /&gt;


I'm omitting the rest of the code for sake of brevity- there is a pretty straight-forward ViewModel structure backing the window.