WPF用Style和Template定制DataGrid

#程序员##万众创业##IT教育##.net#

锐英源精品原创,禁止全文或局部转载,禁止任何形式的非法使用,侵权必究。点名“简易百科”和闲暇巴盗用锐英源原创内容。


前几天写DataGrid,想实现DataGrid不同行不同背景色,在codeproject上找到了个好文章翻译给大家,自己也提高下。要点是滚动条也可以定制,这比Winform写代码定制要灵活强大,希望大家能够喜欢。本文核心特点是脚本定制,这和WinForm的代码定制方式不同, 更灵活,同时非法操作也更少,是进步。但关联因素比较多。

提示下:看不懂codeproject,找锐英源。

介绍

在本文中,我们将介绍如何更改数据网格控件的外观。

如何自定义DataGrid的DataGridColumnHeader、DataGridRow、DataGridCell、DatagridRowHeader和ScrollViewer的模板。

在这篇文章中你可以学习,如何使用 DatagridRowHeader 样式扩展多个 RowDetailTemplate,

如何更改 DataGrid 中的 ScrollBar 样式。

背景

DataGrid 是 WPF 中一个强大的控件。它用于在自定义网格中呈现数据集合。


使用代码

DataGridColumnHeader 样式

默认列标题:

自定义列标题:

第 1 步:创建 TargetType=DatagridColumnHeader 的样式

C++

 

第 2 步:创建 TargetType=DatagridColumnHeader 的 ControlTemplate 并在模板中添加。

C++

             

使用 LinearGradientBrush 设置背景颜色来创建边框,以使用指定的偏移量设置线性的多种颜色。

LinearGradientBrush 有 2 个属性

- StartPoint:用于在给定点(X 和 Y)填充颜色。

- EndPoint:渐变颜色将停止填充到给定的端点(X 和 Y)

ContentPresenter 保存 DataGridColumn 的内容(数据/标题文本等)。

第 3 步:为鼠标悬停时更改 DataGridColumn 的 BackgroundColor 目标而添加 VisualState。

C++

              

VisualStateManager 用于在特定状态发生变化时进行动画控制(Normal、MouseOver、Focus 等)

Storyboard 是一个容器时间线,为其子动画提供对象和属性定位信息。简而言之,所有动画都放在情节提要中。

Storyboard 具有 Storyboard.TargetNameStoryboard.TargetProperty附加属性。这些属性用于将指定的动画设置为目标控件的目标属性。

ColorAnimationUsingKeyFrames用于在指定的 Duration 内沿一组 KeyFrame 为 Color 属性的值设置动画。

在上面的代码中,添加了 ColorAnimationUsingKeyFrames 以将数据网格columnHeaderBorder控件的GardientStop[1] 颜色从 #FF7F00 更改 LightYellow。

要了解有关动画和故事板的更多信息,请阅读链接帖子。

当用户将鼠标悬停在数据网格列上时,在 Storyboard 中添加了 ColorAnimation 以更改颜色。

DataGridRow 样式

默认行:

自定义行:



如上图2所示,第一个是默认的DataGrid样式,

第二个是使用行颜色、备用行颜色和鼠标悬停行颜色自定义样式。

第 1 步:创建 TargetType=DataGridRow 的样式

C++

  

在上面的代码中,为 DataGridRow 创建了样式并将行背景属性设置为LightYellow。

步骤 2:为 DataGridRow 创建模板

C++

                                    

在上面的代码中,DataGridRow ControlTemplate 包含 DataGridCellPresenter、DataGridDetailsPresenter 和 DataGridRowHeader。

保持所有这些 Presenter 原样。

我们只需要更改主边框背景颜色,

边框 ( DGR_Border ) 背景颜色设置为 LinerGradientBrush 并结合黄色和弧度。

所以每一行在网格中都用这个背景颜色突出显示。

第 3 步:现在,添加 VisualState 以设置交替行、鼠标悬停行和选定行的 DataGridRow 背景颜色。

要设置交替行颜色,首先我们需要在 DataGrid 中将 AlternationCount 属性值设置为 2。

C++

然后,添加 VisualStates(AlternatingRow、MouseOver 和 Selected Row)

C++

                              

要更改备用行颜色,visualstatemanager 为数据网格行提供 Normal_AlternatingRow 视觉状态。

在上面的代码片段中,添加了三个 VisualState

一个用于 AlternateRow,一个用于 MouseOverRow,一个用于 SelectedRow。

所有都有 ColorAnimation,它会在特定状态更改时更改 DGR_Border控件背景的 GradientStop[0] 和 GradientStop[1] 颜色。

DataGridCell 样式

我创建了这种样式来隐藏默认的数据网格行选择颜色(蓝色)。

因为即使设置 DataGridRow 选择的颜色,它也不会影响 UI,DataGridCell 默认样式会将背景颜色覆盖为其默认颜色。

C++

  

在上面的代码中,我在边框控件中将子控件设置为 ConentPresenter,并将边框控件放置在 ControlTemplate 根目录中。

我将边框控件背景和边框笔刷设置为透明, 因此隐藏了 DatGridCell 背景。

现在,选定的行样式将从 DataGridRow Selected VisualSate 应用。

DataGrid 行详细信息模板


第 1 步:为 RowDetails 创建 DataTemplate

C++

          

在上面的代码中,两个边框控件放置在网格内。

在 First Border Backgroud 中使用 LinearGradientBrush 设置,数据绑定以在 RowDetails 面板中显示。

在 Second Birder 中,背景设置为 RadialGradientBrush,以在细节面板顶部放置一个光环,如上图所示( RowDetail 面板中的温度描述文本周围的颜色)。

下图将描述 RadialGradient 的工作原理(填充颜色)。

第 2 步:为 Show/Hide RowDetail 面板创建 ToggleButton 样式。

C++

< Style TargetType= " ToggleButton" 

使用路径创建了两个形状,一个用于折叠行详细信息面板,一个用于展开行详细信息面板。



Path 用于创建三角形、六边形、椭圆等形状或图形对象,Path 继承自 Shape 类。

您还可以使用路径绘制图片。您可以使用 Fill 属性用颜色填充形状。




第 3 步:为选中/未选中状态的更改路径添加 VisualState。

C++

      CollapsedVisible      

ObjectAnimationUsingKeyFrames动画允许您为动画关键帧使用对象而不是原始值

ObjectAnimationUsingKeyFrames 动画中唯一允许的 DiscreteObjectkeyframes 关键帧。

在上面的代码中,Expand/Collapsed Path 的 Visiblity 使用在
Checked VisualState之上的 ObjectAnimationUsingKeyFrames 进行了更改。

在 ToggleButton 扩展路径的选中状态下,使用 ColorAnimationUsingKeyFrames 更改了颜色。

SplineColorKeyFrame用于使用样条插值将前一个关键帧的颜色值设置为它自己的值。它在由 KeySpline 属性确定的值之间创建变量转换。

第 4 步:在 DataGrid 中设置 RowDetailTemplate,在 RowHeaderTemplate 中添加 ToggleButton。

C++

       

我已将 RowDetailTemplate 设置为StaticResource,因为 DataTemplate 是在同一页面中创建的。如果 DataTemplate 或 Style 放置在 ResourceDictionary 中,那么您必须使用DynamicResource设置 Style 。

要在每行表头添加ToggleButton,需要设置RowHeaderTemplate,如上源码所示,ToggleButton控件设置在DataGrid RowHeaderTemplate的DataTemplate中。

它将在每个行标题上显示三角形图像(使用路径创建),例如:

现在,我们需要在单击 Triangle 时展开 RowDetail,或者我们可以说选中 TogggleButton

第 5 步:处理 ToggleButton 单击事件以展开/折叠 RowDetail

首先,您必须在 DataGrid 样式中设置一个属性,以更改所选 DataGridRow 上的 RowDetail Visibility

C++

< Style TargetType= “ {x:Type DataGrid}” >        < Setter Property= “ RowDetailsVisibilityMode” Value= “ VisibleWhenSelected” / >  

当特殊的DataRow选择上时,会设置RowDetailVisibilityMode到Visible。


C++

private void ToggleButton_Click(object sender, RoutedEventArgs e){DependencyObject obj = (DependencyObject)e.OriginalSource;while (!(obj is DataGridRow) && obj != null) obj = VisualTreeHelper.GetParent(obj);if (obj is DataGridRow){if ((obj as DataGridRow).DetailsVisibility == Visibility.Visible){(obj as DataGridRow).IsSelected = false;}else{(obj as DataGridRow).IsSelected = true;}}} 

在 ToggleButton 单击事件中,首先使用VisualTreeHelper.GerParent方法找到所选切换按钮的当前数据网格行。

VisualTreeHelper 用于执行涉及可视树中节点的任务。

GetParent 方法将返回一个表示可视对象父级的DependencyObject值。

现在,根据 ToggleButton 选中状态和 DataGridRow.DetailsVisibility设置 DataGridRow IsSelected属性。

第 6 步:添加事件处理程序 - RowDetailsVisibilityChanged 以管理 ToggleButton 选中状态


C++

     

- 在 .CS 文件中创建方法,该方法将从父 DependencyObject 中按名称查找 FrameworkElement。

C++

public static FrameworkElement GetTemplateChildByName(DependencyObject parent, string name){int childnum = VisualTreeHelper.GetChildrenCount(parent);for (int i = 0; i < childnum; i++){var child = VisualTreeHelper.GetChild(parent, i);if (child is FrameworkElement && ((FrameworkElement)child).Name == name){return child as FrameworkElement;}else{var s = GetTemplateChildByName(child, name);if (s != null)return s;}}return null;}      

上述方法将遍历 Parent DependencyObject 中所有可用的子控件,并按其名称返回子控件。此方法是递归方法,它将调用方法本身,直到找到子控件或直到最后一个子元素,无论是第一个。

如果未找到子元素,它将迭代到最后一个子元素并返回值。

VisualTreeHelper.GetChild 方法将在 Visual Tree 中找到第一个孩子。

- 创建 DataGrid RowDetailsVisibilityChanged 事件处理程序

C++

private void dataGrid1_RowDetailsVisibilityChanged(object sender,DataGridRowDetailsEventArgs e){DataGridRow row = e.Row as DataGridRow;FrameworkElement tb = GetTemplateChildByName(row, "RowHeaderToggleButton");if (tb != null){if (row.DetailsVisibility == System.Windows.Visibility.Visible){(tb as ToggleButton).IsChecked = true;}else{(tb as ToggleButton).IsChecked = false;}} }        

上述方法将从 Selected DataGridRow 模板中找到 ToggleButton。

如果找到了 ToggleButton,且DataGridRow DetailsVisibility=Visible则将其IsChecked属性设置为true

否则将IsChecked 属性设置为false。

基于行详细信息可见性更改,此方法用于更改 Expand/Collapsed Path(Shape)

DataGrid 滚动条样式



第 1 步:创建重复按钮样式

C++

      

更改重复按钮模板以删除默认样式。

在 ControlTemplate 中添加了边框控件并将背景设置为透明。现在将ContentPresenter 放在 Border 内,

ContentPresenter 用于显示 ContentControl 的内容。

当您要自定义控件模板时,请不要忘记将 ContentPresenter 放在 Template 中,否则您的数据将不会显示。

第 2 步:创建所需的画笔和颜色资源

C++

#AE2F33#800000#AAC64D45#AA0000#FF666666#77C64D45#99C64D45         

WPF 提供以下不同类型的画笔:

- SolidColorBrush:将用纯色绘制区域。

-LinearGradientBrush:将绘制具有线性渐变的区域。

- RadialGradientBrush:将绘制具有径向渐变的区域。焦点定义渐变的起点,圆定义渐变的终点。

- ImageBrush:将用图像绘制区域。

- DrawingBrush:使用 System.Windows.Media.Drawing 绘制区域,其中可以包括形状、文本、视频、图像或其他绘图。

画笔用于用图形/颜色填充/绘制对象/FrameworkElements。

我为滚动条的默认、悬停和按下状态创建了画笔。

第 3 步:创建 ScrollBar Thumb 样式

C++

 

创建的 TargetType=Thumb 样式,通过将 Style 设置为 StaticResource/DynamiceResource,它将在滚动条中应用 Thumb 样式。

在 ControlTemplate 中添加了 Rectangle 控件并将 Fill 属性设置为 {TemplateBinding Background} ,此 TemplateBinding 将从控件背景绑定颜色,因此它将 Rectangle 填充颜色设置为 BackgroundBrush ( )

第 4 步:创建 ScrollBar 样式

C++

 

在 ScollBar ControlTemplate 中,添加了两个重复按钮(一个用于顶部,一个用于底部)和 Thumb。

对于 Top RepeatButton,您必须将 Command 设置为 ScrollBar.LineUpCommand 并设置之前在 ResourceDictionary 中创建的 Style={DynamicResource ScrollButtons}。

使用路径为顶部按钮创建形状并放置在重复按钮中。

同样,对于底部重复按钮,您必须将 Command 设置为 ScrollBar.LineDownCommand 设置与顶部按钮相同的样式。

创建 Track 并将 Thumb 添加到Track.Thumb。将以前创建的 Thumb 样式设置为 Track.Thumb。

Track 表示一个控制基元,用于处理 System.Windows.Controls.Primitives 的定位和大小。用于设置 Primitives.Track.Value 的拇指控件

第 5 步:为 RepeatButton 和 Thumb 添加触发器以更改 MouseOver 上的颜色并更改 Pressed 属性。

C++

   > 

在上面的示例中,我为 RepeatButton 创建了 MouseOver 触发器来更改 Fill 属性。

为 Thumb 2 创建触发器,一个用于 MouseOver,一个用于 Dragging 以更改 Thumb Background 属性。

您也可以在其他属性上创建触发器(例如:按下、启用等)

第 6 步:最后,在 DataGrid Tempalate 中设置 ScrollBar 样式。

C++

                                                                                

在 DataGrid ControlTemplate 的 ScrollViewer 中添加了两个 ScrollBar。

一种用于垂直滚动,一种用于水平滚动。将 Style 设置为 {DynamicResource MyScrollBar} ,就像之前创建的滚动条样式一样。

在这篇文章中,我尝试包含完全自定义 DataGrid 样式的所有要点,以更改控件的外观和外观。

兴趣点

在开发过程中,请记住如何在需要时显示多个 RowDetails 面板和显示/隐藏 RowDetail 面板。

为此,我有 Crated ToggleButton 并添加到 DataGrid 的 RowHeaderTemplate 中,单击 ToggleButton 显示 RowDetails 并再次单击隐藏详细信息面板。

我也在这篇文章中实现了与显示/隐藏行详细信息面板相关的更改。这是 DataGrid 中的新事物。

发表评论
留言与评论(共有 0 条评论) “”
   
验证码:

相关文章

推荐文章