JVimes JVimes - 1 month ago 19
C# Question

WPF TabControl header spacing, keyboard focus rectangle doesn't line up

I'm setting ControlTemplates to space out TabItems, but the keyboard focus rectangle doesn't align anymore:

enter image description here

Anyone know an easy way to fix this?

Here's the simplified sample code:

<TabControl x:Name="tabControl">
<TabControl.Resources>
<ControlTemplate x:Key="tabItemTemplate"
TargetType="{x:Type TabItem}">
<Grid x:Name="templateRoot" Margin="0,0,40,0">
<Border BorderBrush="LightGray"
BorderThickness="1"/>
<ContentPresenter ContentSource="Header"
Margin="10,5"/>
</Grid>
</ControlTemplate>
</TabControl.Resources>
<TabItem Header="TabItem" Template="{StaticResource tabItemTemplate}"/>
<TabItem Header="TabItem" Template="{StaticResource tabItemTemplate}"/>
<TabItem Header="TabItem" Template="{StaticResource tabItemTemplate}"/>
</TabControl>

Answer

Easiest way I found is to customize the FocusVisualStyle and give it a margin similar to what was used to space out the tabs.

Example:

<TabControl x:Name="tabControl">
    <TabControl.Resources>
        <Style x:Key="tabItemStyle" TargetType="TabItem">
            <Setter Property="FocusVisualStyle">
                <Setter.Value>
                    <Style>
                        <Setter Property="Control.Template">
                            <Setter.Value>
                                <ControlTemplate>
                                    <Rectangle Margin="2,2,42,2" SnapsToDevicePixels="True"
                                            Stroke="{DynamicResource {x:Static SystemColors.ControlTextBrushKey}}"
                                            StrokeDashArray="1 2" StrokeThickness="1" />
                                </ControlTemplate>
                            </Setter.Value>
                        </Setter>
                    </Style>
                </Setter.Value>
            </Setter>
            <Setter Property="Template">
                <Setter.Value>
                    <ControlTemplate TargetType="{x:Type TabItem}">
                        <Grid x:Name="templateRoot" Margin="0,0,40,0">
                            <Border BorderBrush="LightGray" BorderThickness="1" />
                            <ContentPresenter Margin="10,5" ContentSource="Header" />
                        </Grid>
                    </ControlTemplate>
                </Setter.Value>
            </Setter>
        </Style>
    </TabControl.Resources>
    <TabItem Header="TabItem" Style="{StaticResource tabItemStyle}" />
    <TabItem Header="TabItem" Style="{StaticResource tabItemStyle}" />
    <TabItem Header="TabItem" Style="{StaticResource tabItemStyle}" />
</TabControl>

enter image description here

That custom FocusVisualStyle is a modified version of the default (I adjusted the margin), which I extracted from a dummy TabItem via the Properties Window:

enter image description here