我在前面随笔《在Winform系统开发中,对表格列表中的内容进行分组展示》,介绍了Winform程序中对表格内容进行了分组的展示,在WPF应用中,同样也可以对表格的内容进行分组展示,不过处理方式和Winform有所差异,本篇随笔同样基于SqlSugar开发框架的基础上,实现在WPF应用中实现DataGrid的分组显示,以及嵌套明细展示效果。

1、回顾Winform的表格分组展示效果

对于常规的二维表格数据,如下所示。

我们根据其中一个字段对表格数据进行分组展示,这样更方便用户对特定数据的归类展示处理。

Winform的界面中,我们基于DevExpress的GridView控件对数据进行分组展示,其中代码如下所示。

//增加汇总字段和显示
var gridView1 = this.winGridViewPager1.gridView1;
if (checkGroup.Checked)
{
this.winGridViewPager1.ShowLineNumber = false;
gridView1.IndicatorWidth = 0;
gridView1.OptionsView.ShowGroupExpandCollapseButtons = true;//显示折叠的分组
gridView1.OptionsView.AllowCellMerge = true; //允许合并字段
gridView1.OptionsView.GroupDrawMode = GroupDrawMode.Standard; gridView1.GroupSummary.Clear();
gridView1.Columns["Category"].GroupIndex = 0;//对类别进行分组展示 var item = new GridGroupSummaryItem();
item.FieldName = "Id";
item.DisplayFormat = " (合计数量 = {0:n})";
item.SummaryType = DevExpress.Data.SummaryItemType.Count;//Sum、Average等
gridView1.GroupSummary.Add(item);
gridView1.ExpandAllGroups();
}
else
{
gridView1.GroupSummary.Clear();
this.winGridViewPager1.ShowLineNumber = true;
gridView1.OptionsView.AllowCellMerge = false;
}

我们可以看到,只需要实现对 GroupSummary的添加处理即可实现汇总效果的展示。

2、在WPF应用中实现DataGrid的分组显示

在WPF应用中,数据的显示通过DataGrid控件进行展示,默认是没有分组效果的,如果需要分组效果,需要定制表格的分组样式才能达到效果。

我们同样基于SqlSugar开发框架的基础上,基于原料表的数据展示,实现在WPF应用中实现DataGrid的分组显示,实现的效果如下所示。

我们这里根据【类别】字段来进行分组统一,其中分组样式在XAML上定义如下所示。

<DataGrid.GroupStyle>
<GroupStyle>
<GroupStyle.ContainerStyle>
<Style TargetType="{x:Type GroupItem}">
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type GroupItem}">
<Expander IsExpanded="True">
<Expander.Header>
<StackPanel Orientation="Horizontal">
<TextBlock FontWeight="Bold" Text="类别:" />
<TextBlock FontWeight="Bold" Text="{Binding Name}" />
<TextBlock Text="{Binding ItemCount, StringFormat=' (合计数量 = {0} )'}" />
</StackPanel>
</Expander.Header>
<ItemsPresenter />
</Expander>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
</GroupStyle.ContainerStyle>
<GroupStyle.HeaderTemplate>
<DataTemplate>
<TextBlock FontWeight="Bold" Text="{Binding Name}" />
</DataTemplate>
</GroupStyle.HeaderTemplate>
</GroupStyle>
</DataGrid.GroupStyle>

如果我们需要控件的虚拟化处理(提高显示性能),那么设置下虚拟化处理属性即可。

<DataGrid
x:Name="grid"
Grid.Row="1"
hc:DataGridAttach.ShowRowNumber="True"
AutoGenerateColumns="False"
HeadersVisibility="All"
IsReadOnly="True"
ItemsSource="{Binding ViewModel.Items}"
MouseDoubleClick="DataGrid_MouseDoubleClick"
RowHeaderWidth="60"
SelectionChanged="DataGrid_SelectionChanged"
SelectionMode="Extended"
VerticalScrollBarVisibility="Auto"
VirtualizingPanel.IsVirtualizing="True"
VirtualizingPanel.IsVirtualizingWhenGrouping="True"

>

表格的字段,如没有特殊处理,我们用常用的定义效果即可,如下所示。

<DataGrid.Columns>
<DataGridTextColumn
Width="SizeToCells"
MinWidth="100"
Binding="{Binding Id}"
Header="ID编号" />
<DataGridTextColumn
Width="SizeToCells"
MinWidth="100"
Binding="{Binding Category}"
Header="类别" />
<DataGridTextColumn
Width="SizeToCells"
MinWidth="100"
Binding="{Binding Code}"
Header="原料编码" />
..............
</DataGrid.Columns>

对于分组的效果处理,我们后台的C#代码也需要进行一定的适应处理,如下所示。

我们采用MVVM的模式处理查询操作,获得数据并转换为CollectionView后,设置分组信息即可,如下代码所示。

/// <summary>
/// 查询处理
/// </summary>
[RelayCommand]
private async Task Search()
{
//查询获得视图模型的数据
await this.ViewModel.SearchCommand.ExecuteAsync(null); //把数据集合转换为CollectionView,并设置其GroupDescriptions
var viewSource = CollectionViewSource.GetDefaultView(this.ViewModel.Items);
if (this.ViewModel.IsUseGroup)
{
viewSource.GroupDescriptions.Clear();
viewSource.GroupDescriptions.Add(new PropertyGroupDescription("Category"));
}
this.grid.ItemsSource = viewSource;
}

这样就是写了数据的显示和分组处理了。

上面的SearchCommand就是视图模型基类函数的查询获得数据的处理方式。

    /// <summary>
/// 触发查询处理命令
/// </summary>
/// <returns></returns>
[RelayCommand]
public virtual async Task Search()
{
//切换第一页
this.PagerInfo.CurrentPageIndex = 1;
//查询更新
await GetData();
}

GetData也是视图模型基类函数的通用处理方式,通过分页和条件信息,获得对应的数据记录。

    /// <summary>
/// 根据分页和查询条件查询,请求数据
/// </summary>
/// <returns></returns>
public virtual async Task GetData()
{
//转换下分页信息
ConvertPagingInfo();
var result = await service.GetListAsync(this.PageDto);
if (result != null)
{
this.Items = result.Items?.ToList();
this.PagerInfo.RecordCount = result.TotalCount;
}
}

3、在WPF应用中实现嵌套明细展示效果

我们这里继续介绍另外一个DataGrid的效果,通过明细展示的方式显示其中一条记录相关联的表格信息,有时候也可以看成是主从关联信息。

单我们单击其中一条记录的时候,展示嵌套表格,展示详细的明细信息,如下效果所示。

这个效果主要是通过定义DataGrid.RowDetailsTemplate进行明细内容的处理的。例如我们定义明细的模板如下所示,其实也就是显示另外一个表格信息。

<DataGrid.RowDetailsTemplate>
<DataTemplate>
<DataGrid
MaxHeight="500"
hc:DataGridAttach.ShowRowNumber="True"
AlternatingRowBackground="LightBlue"
AutoGenerateColumns="False"
HeadersVisibility="Column"
IsReadOnly="True"
RowHeaderWidth="60"
ScrollViewer.VerticalScrollBarVisibility="Auto"
SelectionUnit="FullRow">
<DataGrid.Columns>
<DataGridTextColumn
MinWidth="120"
Binding="{Binding Name}"
Header="显示名称" />
<DataGridTemplateColumn Width="80" Header="图标">
<DataGridTemplateColumn.CellTemplate>
<DataTemplate>
<ui:SymbolIcon
Width="32"
FontSize="32"
Symbol="{Binding Icon}" />
</DataTemplate>
</DataGridTemplateColumn.CellTemplate>
</DataGridTemplateColumn>
<DataGridTextColumn
Width="80"
Binding="{Binding Seq}"
Header="排序" />
<DataGridTextColumn
Width="100"
Binding="{Binding FunctionId}"
Header="功能ID" />
</DataGrid.Columns> </DataGrid>
</DataTemplate>
</DataGrid.RowDetailsTemplate>

Xaml的结构如下所示。

另外,我们在视图模型中除了定义一级的数据记录外,还定义一个嵌套记录集合对象,如下所示。

        /// <summary>
/// 编辑的数据列表
/// </summary>
[ObservableProperty]
private ObservableCollection<MenuInfo>? menuItems; /// <summary>
/// 指定父级的子级数据列表
/// </summary>
[ObservableProperty]
private ObservableCollection<MenuInfo>? detailItems;

这样我们在行选择变化的时候,重新获得明细的记录,然后绑定显示事件即可,如下代码所示。

   /// <summary>
/// 记录行变化的时候,触发明细记录的获取处理
/// </summary>
private async void DataGrid_SelectionChanged(object sender, SelectionChangedEventArgs e)
{
var datagrid = sender as DataGrid;
if (datagrid != null)
{
var item = datagrid!.SelectedItem as MenuInfo;
if (item != null)
{
await ViewModel.GetDetailList(item.Id);
}
}
}

而在页面初始化的时候,我们可以构造一个事件,用来绑定明细记录的绑定显示处理。

    //明细记录可见性变化的时候,触发数据的绑定处理事件
this.grid.RowDetailsVisibilityChanged += (s, e) =>
{
var datagrid = s as DataGrid;
if (datagrid != null)
{
var DetailsDataGrid = e.DetailsElement as DataGrid;
if(DetailsDataGrid != null)
{
DetailsDataGrid.ItemsSource = viewModel.DetailItems;
}
}
};

这样就可以正常的显示嵌套明细的记录了。

在WPF应用中实现DataGrid的分组显示,以及嵌套明细展示效果的更多相关文章

  1. jquery easyui window中的datagrid,只能显示一次问题

    最近项目中用到easyui 的动态创建window ,window中嵌入了datagruid.第一次打开是能显示数据,但再次打开时确没显示: 注:url已成功返回了数据. 多次查阅easyui帮助文档 ...

  2. Android中的dp,px以及wrap_content的实际展示效果

    因为一个效果中的图片设置了wrap_content的属性,但在720dp跟540dp上面显示不一致使老大非常恼火.跟他讲也讲不明白.于是乎让我们彼此测试来探个究竟.首先测试的是个图片: 它的物理像素是 ...

  3. WPF 中获取DataGrid 模板列中控件的对像

    WPF 中获取DataGrid 模板列中控件的对像 #region 当前选定行的TextBox获得焦点 /// <summary> /// 当前选定行的TextBox获得焦点 /// &l ...

  4. wpf中的datagrid绑定操作按钮是否显示或者隐藏

    如图,需要在wpf中的datagrid的操作那列有个确认按钮,然后在某些条件下确认按钮可见,某些情况下不可见的,放在mvc里直接在cshtml页面中if..else就行了. 但是在wpf里不行..网上 ...

  5. wpf中为DataGrid添加checkbox支持多选全选

    项目中用到DataGrid, 需要在第一列添加checkbox, 可以多选.全选. 其中涉及的概念DataTemplate, DataGridCellStyle, DataGridCellContro ...

  6. C#开发微信门户及应用(10)--在管理系统中同步微信用户分组信息

    在前面几篇文章中,逐步从原有微信的API封装的基础上过渡到微信应用平台管理系统里面,逐步介绍管理系统中的微信数据的界面设计,以及相关的处理操作过程的逻辑和代码,希望从更高一个层次,向大家介绍微信的应用 ...

  7. wpf CollectionViewSource与ListBox的折叠、分组显示,及输入关键字 Filter的筛选

    在wpf中虽然ObservableCollection<T>作为ListBox的Itemsource,很好,很强大!但是CollectionViewSource与ListBox才是天作之合 ...

  8. WPF 实现主从的datagrid以及操作rowdetailtemplate 的方法

    原文:WPF 实现主从的datagrid以及操作rowdetailtemplate 的方法 WPF 实现主从的datagrid以及操作rowdetailtemplate 的方法        最近在做 ...

  9. Hadoop学习笔记—11.MapReduce中的排序和分组

    一.写在之前的 1.1 回顾Map阶段四大步骤 首先,我们回顾一下在MapReduce中,排序和分组在哪里被执行: 从上图中可以清楚地看出,在Step1.4也就是第四步中,需要对不同分区中的数据进行排 ...

  10. 在WPF程序中使用摄像头兼谈如何使用AForge.NET控件(转)

    前言: AForge.NET 是用C#写的一个关于计算机视觉和人工智能领域的框架,它包括图像处理.神经网络.遗传算法和机器学习等.在C#程序中使用摄像头,我习惯性使用AForge.NET提供的类库.本 ...

随机推荐

  1. 鸿蒙轻内核M核源码分析:数据结构之任务排序链表

    摘要:鸿蒙轻内核的任务排序链表,用于任务延迟到期/超时唤醒等业务场景,是一个非常重要.非常基础的数据结构. 本文会继续给读者介绍鸿蒙轻内核源码中重要的数据结构:任务排序链表TaskSortLinkAt ...

  2. openGauss内核:简单查询的执行

    摘要:本文主要分析简单查询语句在业务处理线程Postgres上的执行流程,并介绍如何利用gdb梳理代码逻辑. 本文分享自华为云社区<openGauss内核分析(二):简单查询的执行>,作者 ...

  3. “数”驰天下,华为云DRS 高效支撑T3出行平稳迁移

    摘要:华为云DRS成功助力T3出行在规定时间内完成数十TB级全量数据的迁移. 数字化潮流浩浩汤汤,企业上云如火如荼,网约车行业也借助这一股东风展现出了蓬勃的生命力,因为它的高效便捷,吸引了越来越多的都 ...

  4. 开心档之C++ 数据封装

    C++ 数据封装 所有的 C++ 程序都有以下两个基本要素: **程序语句(代码):**这是程序中执行动作的部分,它们被称为函数. **程序数据:**数据是程序的信息,会受到程序函数的影响. 封装是面 ...

  5. 打通数据治理全链路,火山引擎DataLeap数据治理平台公有云版本正式发布

    更多技术交流.求职机会,欢迎关注字节跳动数据平台微信公众号,回复[1]进入官方交流群   近日,火山引擎DataLeap正式对外发布数据治理平台公有云版.DataLeap是火山引擎大数据研发治理套件, ...

  6. 火山引擎数智平台ByteHouse入围稀土掘金《Top10 年度创新产品》

    更多技术交流.求职机会,欢迎关注字节跳动数据平台微信公众号,回复[1]进入官方交流群 近日,国内开发者技术社区稀土掘金发布「2022 稀土掘金引力榜」,旨在盘点 2022 年在数字化转型领域内最具影响 ...

  7. SQL Server 事务执行、回滚

    MySQL 事务回滚.在执行删除.更新等操作时,防止误操作 生产环境更新数据时必用 begin tran --开启事务 begin--先在事务中 执行 UPDATE Sys_User SET Name ...

  8. Pytest.mark.parametrize()基本用法

    Pytest.mark.parametrize()基本用法 @pytest.mark.parametrize()基本用法 数据驱动:就是把我们测试用例的数据放到excel,yaml,csv,mysql ...

  9. Go--变量的声明

    Go语言是静态类型语言,因此变量(variable)是有明确类型的,编译器也会检查变量类型的正确性. 变量是一段或多段用来存储数据的内存,在go中,变量一旦被定义,一定要使用,不然会报错 内建变量类型 ...

  10. #2612:Find a way(BFS搜索+多终点)

    第一次解决双向BFS问题,拆分两个出发点分BFS搜索 #include<cstdio> #include<cstring> #include<queue> usin ...