1
votes

I am currently working on a Plug-In for AutoCAD, scripting language is VB.net.

Basically I have a User Control which holds a TabControl, each TabItem is an object which just holds the TabItem.Header and TabItem.Content definition. The TabItems are generated dynamically through a xml file. As I am using MVVM this is all stored in an ObservableCollection which is bound to the TabControl items.

As I am fighting with MVVM a little bit and I am rather new to WPF I need a little guidance on the following task: Everything is working fine so far but the only problem I have is that I want a little button at the end of the visible TabItems. When I click on it I can switch through all the Tabs, doesn't matter if they are visible or not.

For a better undertstanding, this should be the desired result: Image File

I just want a simple explanation on how to achieve that (all the samples on the net are rather complex to me). I tried it with a ScrollViewer, but the result is bad. Here is the current code:

TabControl Template:

<Style  x:Key="TabControl"
        TargetType="{x:Type TabControl}">

    <Setter Property="Background"
            Value="{StaticResource TabBackground}">
    </Setter>
    <Setter Property="BorderBrush"
            Value="{StaticResource TabItemActiveBorder}">
    </Setter>
    <Setter Property="BorderThickness"
            Value="0,1,1,0">
    </Setter>

    <Setter Property="Template">
        <Setter.Value>
            <ControlTemplate TargetType="{x:Type TabControl}">
                <StackPanel>
                    <ScrollViewer HorizontalScrollBarVisibility="Disabled"
                                  VerticalScrollBarVisibility="Visible">
                        <TabPanel x:Name="HeaderPanel"
                                  Panel.ZIndex="1"
                                  KeyboardNavigation.TabIndex="1"
                                  Grid.Column="0"
                                  Grid.Row="0"
                                  Margin="2,2,2,0"
                                  IsItemsHost="true" />
                    </ScrollViewer>
                    <ContentPresenter x:Name="PART_SelectedContentHost"
                                      SnapsToDevicePixels="{TemplateBinding SnapsToDevicePixels}"
                                      Margin="{TemplateBinding Padding}"
                                      ContentSource="SelectedContent" />
                </StackPanel>
                <!--<Grid>
                    <Grid.RowDefinitions KeyboardNavigation.TabNavigation="Local">
                        <RowDefinition Height="Auto" />
                        <RowDefinition Height="*" />
                    </Grid.RowDefinitions>

                    <ScrollViewer>
                        <TabPanel x:Name="HeaderPanel"
                                  Panel.ZIndex="1"
                                  Margin="0,0,4,-1"
                                  IsItemsHost="True"
                                  KeyboardNavigation.TabIndex="1"
                                  Background="Transparent" />
                    </ScrollViewer>
                </Grid>-->
            </ControlTemplate>
        </Setter.Value>
    </Setter>
</Style>

<Style x:Key="TabItem"
       TargetType="{x:Type TabItem}">
    <Setter Property="Template">
        <Setter.Value>
            <ControlTemplate TargetType="{x:Type TabItem}">
                <Grid>
                    <Border Name="Border"
                            Margin="0,-2,5,0"
                            Padding="0,1,0,1"
                            Height="55"
                            BorderBrush="{StaticResource TabItemActiveBorder}"
                            CornerRadius="0,5,5,0">
                        <ContentPresenter x:Name="ContentSite"
                                          VerticalAlignment="Center"
                                          HorizontalAlignment="Center"
                                          ContentSource="Header"
                                          Margin="2,5,2,5"
                                          RecognizesAccessKey="True" />
                    </Border>
                </Grid>
                <ControlTemplate.Triggers>
                    <Trigger Property="IsSelected"
                             Value="True">
                        <Setter Property="Panel.ZIndex"
                                Value="100" />
                        <Setter TargetName="Border"
                                Property="Margin"
                                Value="-1,-2,1,0" />
                        <Setter Property="TextElement.Foreground"
                                Value="{StaticResource TabItemActiveText}" />
                        <Setter TargetName="Border"
                                Property="Background"
                                Value="{StaticResource TabBackground}" />
                        <Setter TargetName="Border"
                                Property="BorderThickness"
                                Value="0,1,1,1" />
                    </Trigger>
                    <Trigger Property="IsSelected"
                             Value="false">
                        <Setter Property="TextElement.Foreground"
                                Value="{StaticResource TabItemInactiveText}" />
                        <Setter TargetName="Border"
                                Property="Background"
                                Value="{StaticResource TabItemInactiveBackground}" />
                        <Setter TargetName="Border"
                                Property="BorderThickness"
                                Value="0,1,1,1" />
                    </Trigger>
                    <Trigger Property="IsEnabled"
                             Value="False">
                        <Setter TargetName="Border"
                                Property="Background"
                                Value="{StaticResource InActiveControlBackGround}" />
                        <Setter TargetName="Border"
                                Property="BorderBrush"
                                Value="{StaticResource InActiveControlBackGround}" />
                        <Setter Property="Foreground"
                                Value="{StaticResource InActiveControlBackGround}" />
                    </Trigger>
                </ControlTemplate.Triggers>
            </ControlTemplate>
        </Setter.Value>
    </Setter>

    <Setter Property="HeaderTemplate">
        <Setter.Value>
            <DataTemplate>
                <ContentPresenter Content="{TemplateBinding Content}">
                    <ContentPresenter.LayoutTransform>
                        <RotateTransform Angle="270" />
                    </ContentPresenter.LayoutTransform>
                </ContentPresenter>
            </DataTemplate>
        </Setter.Value>
    </Setter>
</Style>

mainWindow XAML excerpt:

<Grid Background="{StaticResource TabBackground}">
    <Grid Margin="0,96,0,0">
        <TabControl ItemContainerStyle="{StaticResource TabItem}"
                    TabStripPlacement="Right"
                    ItemsSource="{Binding loadedPalettes}"
                    Style="{StaticResource TabControl}">
            <TabControl.ItemTemplate>
                <DataTemplate>
                    <TextBlock Text="{Binding Header}">
                        <TextBlock.LayoutTransform>
                            <RotateTransform Angle="270" />
                        </TextBlock.LayoutTransform>
                    </TextBlock>
                </DataTemplate>
            </TabControl.ItemTemplate>
            <TabControl.ContentTemplate>
                <DataTemplate>
                    <UserControls:tabDataGrid />
                </DataTemplate>
            </TabControl.ContentTemplate>
        </TabControl>
    </Grid>

TabItem Class:

Private Property _Header As String
Public Property Header As String
    Get
        Return _Header
    End Get
    Set(value As String)
        _Header = value
    End Set
End Property

Private Property _Content As String
Public Property Content As String
    Get
        Return _Content
    End Get
    Set(value As String)
        _Content = value
    End Set
End Property

Thanks in advance!

1

1 Answers

1
votes

I solved the problem by myself. Here is the working piece of template code:

<Style  x:Key="TabControl"
        TargetType="{x:Type TabControl}">

    <Setter Property="Background"
            Value="{StaticResource TabBackground}">
    </Setter>
    <Setter Property="BorderBrush"
            Value="{StaticResource TabItemActiveBorder}">
    </Setter>
    <Setter Property="BorderThickness"
            Value="0,1,1,0">
    </Setter>

    <Setter Property="Template">
        <Setter.Value>
            <ControlTemplate TargetType="{x:Type TabControl}">
                <Grid>
                    <Grid.RowDefinitions>
                        <RowDefinition Height="*" />
                    </Grid.RowDefinitions>
                    <Grid.ColumnDefinitions>
                        <ColumnDefinition Width="*" />
                        <ColumnDefinition Width="Auto" />
                    </Grid.ColumnDefinitions>

                    <ScrollViewer HorizontalScrollBarVisibility="Hidden"
                                  VerticalScrollBarVisibility="Hidden"
                                  Grid.Column="1"
                                  Grid.Row="0">

                        <TabPanel x:Name="HeaderPanel"
                                  Panel.ZIndex="1"
                                  Margin="0,2,2,2"
                                  IsItemsHost="True"
                                  Background="Transparent" />
                    </ScrollViewer>

                    <ContentPresenter x:Name="PART_SelectedContentHost"
                                      SnapsToDevicePixels="{TemplateBinding SnapsToDevicePixels}"
                                      Margin="{TemplateBinding Padding}"
                                      ContentSource="SelectedContent" />
                </Grid>
            </ControlTemplate>
        </Setter.Value>
    </Setter>
</Style>