如何在整个 DataGrid 列周围添加边框 header?
How to add a border around the entire DataGrid column header?
我对 DataGrid
进行了很多自定义,但令人惊讶的是我无法在不破坏的情况下围绕整个 header 区域添加边框。
这就是我想要完成的事情:
下面的控件负责显示header区域:DataGridColumnHeadersPresenter
.
我在它周围添加了一个边框,正如您从上面的屏幕截图中看到的那样,它确实有效,但只有当 网格为空时问题才会出现!(这意味着还需要删除空行,这可以通过设置 CanUserAddRows="False"
).
来完成
到目前为止,这是我的风格:
<Border BorderBrush="Red" BorderThickness="1" Grid.Column="1">
<DataGridColumnHeadersPresenter x:Name="PART_ColumnHeadersPresenter" Margin="0,0,0,5"
Visibility="{Binding HeadersVisibility, ConverterParameter={x:Static DataGridHeadersVisibility.Column}, Converter={x:Static DataGrid.HeadersVisibilityConverter}, RelativeSource={RelativeSource AncestorType={x:Type DataGrid}}}">
</DataGridColumnHeadersPresenter>
</Border>
我所做的只是用边框将其包裹起来,但现在当我应用过滤以使网格为空时,header 消失在右侧并且应用程序变慢到爬行。
示范:
如果我删除边框,一切都会按预期进行。看起来 DataGrid 需要一个非常具体的树结构,否则它就会爆炸。
我尝试更改 DataGridColumnHeadersPresenter
的模板,但也需要一个非常具体的结构,如下所示:
<DataGridColumnHeadersPresenter.Template>
<ControlTemplate TargetType="{x:Type DataGridColumnHeadersPresenter}">
<Grid>
<DataGridColumnHeader x:Name="PART_FillerColumnHeader"
IsHitTestVisible="False" />
<ItemsPresenter />
</Grid>
</ControlTemplate>
</DataGridColumnHeadersPresenter.Template>
如果我给DataGridColumnHeader
一个BorderBrush
和BorderThickness
,它看起来不对,如果我在任何地方添加自己的边框控制,同样的问题会出现。
DataGridColumnHeadersPresenter
实际上有BorderBrush
和BorderThickness
属性,但它们根本没有作用。
我发现的一个解决方法是将 Grid.Column
设置为 0
,这样它就可以代替行 header 的列 header,然后只需设置 HeadersVisibility="Column"
在 DataGrid
上,所以它看起来没有损坏,问题就消失了。不幸的是,我需要 header 行,所以这是一个不可接受的解决方案。
DataGrid 的默认样式可以在 here 中找到,或者只是 right-click 它在 Visual Studio 中,然后转到编辑模板,然后编辑副本,这就是我所做的。
一定有一种简单的方法可以做到这一点,我现在可能还没有看到...
好的,所以在@jsanalytics 指出存在 DataGridHeaderBorder
之后,我才回来解决这个问题,并且通过更深入地分析默认树结构,通过一些反复试验,我设法得到工作完成。
虽然我不想要 DataGridHeaderBorder
,它是 Windows 主题的一部分,但用常规边框代替了它。
我的实现:
<DataGridColumnHeadersPresenter Grid.Column="1" x:Name="PART_ColumnHeadersPresenter"
Visibility="{Binding HeadersVisibility, ConverterParameter={x:Static DataGridHeadersVisibility.Column}, Converter={x:Static DataGrid.HeadersVisibilityConverter}, RelativeSource={RelativeSource AncestorType={x:Type DataGrid}}}">
<DataGridColumnHeadersPresenter.Template>
<ControlTemplate TargetType="{x:Type DataGridColumnHeadersPresenter}">
<Grid HorizontalAlignment="Left">
<ItemsPresenter />
<DataGridColumnHeader x:Name="PART_FillerColumnHeader" IsHitTestVisible="False">
<DataGridColumnHeader.Template>
<ControlTemplate TargetType="{x:Type DataGridColumnHeader}">
<Grid>
<Border BorderThickness="2" BorderBrush="Red">
<ContentPresenter RecognizesAccessKey="True"
SnapsToDevicePixels="True" />
</Border>
<!--Uncomment if you need these resizing grippers-->
<!--<Thumb x:Name="PART_LeftHeaderGripper" HorizontalAlignment="Left" />
<Thumb x:Name="PART_RightHeaderGripper" HorizontalAlignment="Right" />-->
</Grid>
</ControlTemplate>
</DataGridColumnHeader.Template>
</DataGridColumnHeader>
</Grid>
</ControlTemplate>
</DataGridColumnHeadersPresenter.Template>
</DataGridColumnHeadersPresenter>
您可能需要根据自己的需要对其进行调整,但这满足了我们的要求:-)
我对 DataGrid
进行了很多自定义,但令人惊讶的是我无法在不破坏的情况下围绕整个 header 区域添加边框。
这就是我想要完成的事情:
下面的控件负责显示header区域:DataGridColumnHeadersPresenter
.
我在它周围添加了一个边框,正如您从上面的屏幕截图中看到的那样,它确实有效,但只有当 网格为空时问题才会出现!(这意味着还需要删除空行,这可以通过设置 CanUserAddRows="False"
).
到目前为止,这是我的风格:
<Border BorderBrush="Red" BorderThickness="1" Grid.Column="1">
<DataGridColumnHeadersPresenter x:Name="PART_ColumnHeadersPresenter" Margin="0,0,0,5"
Visibility="{Binding HeadersVisibility, ConverterParameter={x:Static DataGridHeadersVisibility.Column}, Converter={x:Static DataGrid.HeadersVisibilityConverter}, RelativeSource={RelativeSource AncestorType={x:Type DataGrid}}}">
</DataGridColumnHeadersPresenter>
</Border>
我所做的只是用边框将其包裹起来,但现在当我应用过滤以使网格为空时,header 消失在右侧并且应用程序变慢到爬行。
示范:
如果我删除边框,一切都会按预期进行。看起来 DataGrid 需要一个非常具体的树结构,否则它就会爆炸。
我尝试更改 DataGridColumnHeadersPresenter
的模板,但也需要一个非常具体的结构,如下所示:
<DataGridColumnHeadersPresenter.Template>
<ControlTemplate TargetType="{x:Type DataGridColumnHeadersPresenter}">
<Grid>
<DataGridColumnHeader x:Name="PART_FillerColumnHeader"
IsHitTestVisible="False" />
<ItemsPresenter />
</Grid>
</ControlTemplate>
</DataGridColumnHeadersPresenter.Template>
如果我给DataGridColumnHeader
一个BorderBrush
和BorderThickness
,它看起来不对,如果我在任何地方添加自己的边框控制,同样的问题会出现。
DataGridColumnHeadersPresenter
实际上有BorderBrush
和BorderThickness
属性,但它们根本没有作用。
我发现的一个解决方法是将 Grid.Column
设置为 0
,这样它就可以代替行 header 的列 header,然后只需设置 HeadersVisibility="Column"
在 DataGrid
上,所以它看起来没有损坏,问题就消失了。不幸的是,我需要 header 行,所以这是一个不可接受的解决方案。
DataGrid 的默认样式可以在 here 中找到,或者只是 right-click 它在 Visual Studio 中,然后转到编辑模板,然后编辑副本,这就是我所做的。
一定有一种简单的方法可以做到这一点,我现在可能还没有看到...
好的,所以在@jsanalytics 指出存在 DataGridHeaderBorder
之后,我才回来解决这个问题,并且通过更深入地分析默认树结构,通过一些反复试验,我设法得到工作完成。
虽然我不想要 DataGridHeaderBorder
,它是 Windows 主题的一部分,但用常规边框代替了它。
我的实现:
<DataGridColumnHeadersPresenter Grid.Column="1" x:Name="PART_ColumnHeadersPresenter"
Visibility="{Binding HeadersVisibility, ConverterParameter={x:Static DataGridHeadersVisibility.Column}, Converter={x:Static DataGrid.HeadersVisibilityConverter}, RelativeSource={RelativeSource AncestorType={x:Type DataGrid}}}">
<DataGridColumnHeadersPresenter.Template>
<ControlTemplate TargetType="{x:Type DataGridColumnHeadersPresenter}">
<Grid HorizontalAlignment="Left">
<ItemsPresenter />
<DataGridColumnHeader x:Name="PART_FillerColumnHeader" IsHitTestVisible="False">
<DataGridColumnHeader.Template>
<ControlTemplate TargetType="{x:Type DataGridColumnHeader}">
<Grid>
<Border BorderThickness="2" BorderBrush="Red">
<ContentPresenter RecognizesAccessKey="True"
SnapsToDevicePixels="True" />
</Border>
<!--Uncomment if you need these resizing grippers-->
<!--<Thumb x:Name="PART_LeftHeaderGripper" HorizontalAlignment="Left" />
<Thumb x:Name="PART_RightHeaderGripper" HorizontalAlignment="Right" />-->
</Grid>
</ControlTemplate>
</DataGridColumnHeader.Template>
</DataGridColumnHeader>
</Grid>
</ControlTemplate>
</DataGridColumnHeadersPresenter.Template>
</DataGridColumnHeadersPresenter>
您可能需要根据自己的需要对其进行调整,但这满足了我们的要求:-)