< DrawingBrush | パンチングメタル >

August 20, 2008

ListView のカラムヘッダの幅を固定する

WPF の ListView では、カラムヘッダの幅を変更を不可にする手段が用意されていないようです。(Windows 標準の ListView にもなかった気もしますが・・・)

GridViewColumn の HeaderContainerStyle プロパティで、GridViewColumnHeader のスタイルを指定することができるので、Expression Blend で展開した GridViewColumnHeader の VisualTree をいじくることに。

結局、幅変更用の Thumb を無効にすることで目的を達成することができました。

<Window
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    x:Class="ListViewColumnTest.Window2"
    Title="Window2">
    <Window.Resources>
        
        <!-- ブラシリソース -->
        <SolidColorBrush x:Key="GridViewColumnHeaderBackground" Color="#FFECE9D8"/>
        <LinearGradientBrush x:Key="GridViewColumnHeaderHighlightBackground" EndPoint="0,1" StartPoint="0,0">
            <GradientStop Color="#FFECE9D8" Offset="0"/>
            <GradientStop Color="#FFCBC7B8" Offset="1"/>
        </LinearGradientBrush>
        <SolidColorBrush x:Key="GridViewColumnHeaderDarkBackground" Color="#FFCBC7B8"/>
        <SolidColorBrush x:Key="GridViewColumnHeaderGripperBackground" Color="#FFC7C5B2"/>
        
        <!-- カラムヘッダサイズ変更用の Thumb -->
        <Style x:Key="GridViewColumnHeaderGripper" TargetType="{x:Type Thumb}">
            <Setter Property="Canvas.Right" Value="-9"/>
            <Setter Property="Width" Value="18"/>
            <Setter Property="Height" Value="{Binding Path=ActualHeight, RelativeSource={RelativeSource TemplatedParent}}"/>
            <Setter Property="Padding" Value="0,3,0,4"/>
            <Setter Property="Background" Value="{StaticResource GridViewColumnHeaderGripperBackground}"/>
            <Setter Property="Template">
                <Setter.Value>
                    <ControlTemplate TargetType="{x:Type Thumb}">
                        <Border Background="Transparent" Padding="{TemplateBinding Padding}">
                            <DockPanel HorizontalAlignment="Center">
                                <Rectangle Fill="{TemplateBinding Background}" Width="1"/>
                                <Rectangle Fill="White" Width="1"/>
                            </DockPanel>
                        </Border>
                    </ControlTemplate>
                </Setter.Value>
            </Setter>
        </Style>
        
        <!-- ブラシリソース -->
        <SolidColorBrush x:Key="TabItemHotBorderBrush" Color="#FFE68B2C"/>
        <SolidColorBrush x:Key="TabItemHotBorderBackround" Color="#FFFFC73C"/>
        <SolidColorBrush x:Key="GridViewColumnHeaderHoverBackground" Color="#FFFAF8F3"/>
        <SolidColorBrush x:Key="GridViewColumnHeaderPressBorder" Color="#FFA5A597"/>
        <SolidColorBrush x:Key="GridViewColumnHeaderPressBackground" Color="#FFDEDFD8"/>
        
        <!-- カラムヘッダのテンプレート -->
        <Style x:Key="FixedGridViewColumnHeaderStyle" TargetType="{x:Type GridViewColumnHeader}">
            <Setter Property="HorizontalContentAlignment" Value="Center"/>
            <Setter Property="VerticalContentAlignment" Value="Center"/>
            <Setter Property="Background" Value="{StaticResource GridViewColumnHeaderBackground}"/>
            <Setter Property="BorderThickness" Value="1"/>
            <Setter Property="Padding" Value="2,0,2,0"/>
            <Setter Property="Foreground" Value="{DynamicResource {x:Static SystemColors.ControlTextBrushKey}}"/>
            <Setter Property="Template">
                <Setter.Value>
                    <ControlTemplate TargetType="{x:Type GridViewColumnHeader}">
                        <Grid SnapsToDevicePixels="true" Background="{TemplateBinding Background}">
                            <Border x:Name="HighlightBorder" VerticalAlignment="Bottom" Height="3" Background="{StaticResource GridViewColumnHeaderHighlightBackground}" BorderBrush="{StaticResource GridViewColumnHeaderDarkBackground}" BorderThickness="0,0,0,1"/>
                            <Border Margin="1,0,1,0" BorderBrush="{TemplateBinding BorderBrush}" BorderThickness="{TemplateBinding BorderThickness}" Padding="{TemplateBinding Padding}">
                                <ContentPresenter SnapsToDevicePixels="{TemplateBinding SnapsToDevicePixels}" HorizontalAlignment="{TemplateBinding HorizontalContentAlignment}" Margin="0,0,0,1" x:Name="HeaderContent" VerticalAlignment="{TemplateBinding VerticalContentAlignment}" RecognizesAccessKey="True"/>
                            </Border>
                            <Canvas>
                                <!-- カラムヘッダ幅変更用の Thumb の IsEnabled を False に -->
                                <Thumb x:Name="PART_HeaderGripper" Style="{StaticResource GridViewColumnHeaderGripper}" IsEnabled="False"/>
                            </Canvas>
                            <Border x:Name="HeaderPressBorder" BorderThickness="1"/>
                        </Grid>
                        <ControlTemplate.Triggers>
                            <Trigger Property="IsMouseOver" Value="true">
                                <Setter Property="BorderBrush" TargetName="HighlightBorder" Value="{StaticResource TabItemHotBorderBrush}"/>
                                <Setter Property="Background" TargetName="HighlightBorder" Value="{StaticResource TabItemHotBorderBackround}"/>
                                <Setter Property="CornerRadius" TargetName="HighlightBorder" Value="0,0,3,3"/>
                                <Setter Property="BorderThickness" TargetName="HighlightBorder" Value="1,0,1,1"/>
                                <Setter Property="Background" TargetName="PART_HeaderGripper" Value="Transparent"/>
                                <Setter Property="Background" Value="{StaticResource GridViewColumnHeaderHoverBackground}"/>
                            </Trigger>
                            <Trigger Property="IsPressed" Value="true">
                                <Setter Property="Visibility" TargetName="HighlightBorder" Value="Hidden"/>
                                <Setter Property="Visibility" TargetName="PART_HeaderGripper" Value="Hidden"/>
                                <Setter Property="BorderBrush" TargetName="HeaderPressBorder" Value="{StaticResource GridViewColumnHeaderPressBorder}"/>
                                <Setter Property="Margin" TargetName="HeaderPressBorder" Value="1,0,0,0"/>
                                <Setter Property="Margin" TargetName="HeaderContent" Value="1,1,0,0"/>
                                <Setter Property="Background" Value="{StaticResource GridViewColumnHeaderPressBackground}"/>
                                <Setter Property="BorderBrush" Value="{StaticResource GridViewColumnHeaderPressBackground}"/>
                            </Trigger>
                            <Trigger Property="Height" Value="Auto">
                                <Setter Property="MinHeight" Value="20"/>
                            </Trigger>
                            <Trigger Property="IsEnabled" Value="false">
                                <Setter Property="Foreground" Value="{DynamicResource {x:Static SystemColors.GrayTextBrushKey}}"/>
                            </Trigger>
                        </ControlTemplate.Triggers>
                    </ControlTemplate>
                </Setter.Value>
            </Setter>
            <Style.Triggers>
                <Trigger Property="Role" Value="Floating">
                    <Setter Property="Opacity" Value="0.7"/>
                    <Setter Property="Template">
                        <Setter.Value>
                            <ControlTemplate TargetType="{x:Type GridViewColumnHeader}">
                                <Canvas x:Name="PART_FloatingHeaderCanvas"/>
                            </ControlTemplate>
                        </Setter.Value>
                    </Setter>
                </Trigger>
                <Trigger Property="Role" Value="Padding">
                    <Setter Property="Template">
                        <Setter.Value>
                            <ControlTemplate TargetType="{x:Type GridViewColumnHeader}">
                                <Grid SnapsToDevicePixels="true" Background="{TemplateBinding Background}">
                                    <Border VerticalAlignment="Bottom" Height="3" Background="{StaticResource GridViewColumnHeaderHighlightBackground}" BorderBrush="{StaticResource GridViewColumnHeaderDarkBackground}" BorderThickness="0,0,0,1"/>
                                    <Border Margin="1,0,1,0" BorderBrush="{TemplateBinding BorderBrush}" BorderThickness="{TemplateBinding BorderThickness}" Padding="{TemplateBinding Padding}"/>
                                </Grid>
                                <ControlTemplate.Triggers>
                                    <Trigger Property="Height" Value="Auto">
                                        <Setter Property="MinHeight" Value="20"/>
                                    </Trigger>
                                </ControlTemplate.Triggers>
                            </ControlTemplate>
                        </Setter.Value>
                    </Setter>
                </Trigger>
            </Style.Triggers>
        </Style>
        
        <!-- データソース -->
        <XmlDataProvider x:Key="MyDataSource" Source="http://frog.raindrop.jp/index.xml" XPath="/rss/channel">
            <XmlDataProvider.XmlNamespaceManager>
                <XmlNamespaceMappingCollection>
                    <XmlNamespaceMapping Prefix="dc" Uri="http://purl.org/dc/elements/1.1/"/>
                    <XmlNamespaceMapping Prefix="sy" Uri="http://purl.org/rss/1.0/modules/syndication/"/>
                    <XmlNamespaceMapping Prefix="admin" Uri="http://webns.net/mvcb/"/>
                    <XmlNamespaceMapping Prefix="rdf" Uri="http://www.w3.org/1999/02/22-rdf-syntax-ns#"/>
                </XmlNamespaceMappingCollection>
            </XmlDataProvider.XmlNamespaceManager>
        </XmlDataProvider>
        
    </Window.Resources>

    <Grid x:Name="LayoutRoot">
        <ListView ItemsSource="{Binding Source={StaticResource MyDataSource}, XPath=item}">
            <ListView.View>
                <GridView>
                    <GridViewColumn Header="タイトル" Width="300" DisplayMemberBinding="{Binding XPath=title}" HeaderContainerStyle="{DynamicResource FixedGridViewColumnHeaderStyle}"/>
                    <GridViewColumn Header="カテゴリ" Width="250" DisplayMemberBinding="{Binding XPath=dc:subject}" HeaderContainerStyle="{DynamicResource FixedGridViewColumnHeaderStyle}"/>
                    <GridViewColumn Header="更新日時" DisplayMemberBinding="{Binding XPath=dc:date}"/>
                </GridView>
            </ListView.View>
        </ListView>
    </Grid>
</Window>

トラックバック

このエントリーにトラックバック:
http://frog.raindrop.jp/cgi-bin/mt/mt-tb.cgi/2157

コメント

コメントする

※ コメントスパム対策のため、コメント本文はおはよう、こんにちわ、こんばんわのいずれかより始めるようにしてください。

name:
email:

※ 必要ですが、表示しません。

url:
情報を保存する ?