最近cs项目中有个看板的功能需求,整个系统是基于DevExpress组件开发的,由于对这个组件的布局不是很熟,也借鉴了网上一些其他人的做法,普遍都是通过GridControl的BandedGridView来实现的,但是网上很多做法都是从设计视图手动创建绑定Brand的,并不是动态生成的,于是我花了半天时间,把这个控件的用法研究了一下,可以通过代码动态创建生成表头,写了个demo,在这和大家分享一下。

GridControl里面默认的控件是GridView,需要手动转换成BrandedGridView,具体如何转换,网上有很多,这里就不详细介绍了。

先看下designer的代码:

namespace WindowsFormsApplication1
{
    partial class Form2
    {
        /// <summary>
        /// Required designer variable.
        /// </summary>
        private System.ComponentModel.IContainer components = null;

        /// <summary>
        /// Clean up any resources being used.
        /// </summary>
        /// <param name="disposing">true if managed resources should be disposed; otherwise, false.</param>
        protected override void Dispose(bool disposing)
        {
            if (disposing && (components != null))
            {
                components.Dispose();
            }
            base.Dispose(disposing);
        }

        #region Windows Form Designer generated code

        /// <summary>
        /// Required method for Designer support - do not modify
        /// the contents of this method with the code editor.
        /// </summary>
        private void InitializeComponent()
        {
            this.panel1 = new System.Windows.Forms.Panel();
            this.button1 = new System.Windows.Forms.Button();
            this.gridControl1 = new DevExpress.XtraGrid.GridControl();
            this.bandedGridView1 = new DevExpress.XtraGrid.Views.BandedGrid.BandedGridView();
            this.panel1.SuspendLayout();
            ((System.ComponentModel.ISupportInitialize)(this.gridControl1)).BeginInit();
            ((System.ComponentModel.ISupportInitialize)(this.bandedGridView1)).BeginInit();
            this.SuspendLayout();
            //
            // panel1
            //
            this.panel1.Controls.Add(this.button1);
            this.panel1.Dock = System.Windows.Forms.DockStyle.Top;
            , );
            this.panel1.Name = "panel1";
            , );
            ;
            //
            // button1
            //
            , );
            this.button1.Name = "button1";
            , );
            ;
            this.button1.Text = "演示";
            this.button1.UseVisualStyleBackColor = true;
            this.button1.Click += new System.EventHandler(this.button1_Click);
            //
            // gridControl1
            //
            this.gridControl1.Dock = System.Windows.Forms.DockStyle.Fill;
            , );
            this.gridControl1.MainView = this.bandedGridView1;
            this.gridControl1.Name = "gridControl1";
            , );
            ;
            this.gridControl1.ViewCollection.AddRange(new DevExpress.XtraGrid.Views.Base.BaseView[] {
            this.bandedGridView1});
            //
            // bandedGridView1
            //
            this.bandedGridView1.GridControl = this.gridControl1;
            this.bandedGridView1.Name = "bandedGridView1";
            this.bandedGridView1.OptionsView.ShowGroupPanel = false;
            this.bandedGridView1.OptionsView.ShowIndicator = false;
            this.bandedGridView1.CustomDrawCell += BandedGridView1_CustomDrawCell;
            //
            // Form2
            //
            this.AutoScaleDimensions = new System.Drawing.SizeF(6F, 12F);
            this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
            , );
            this.Controls.Add(this.gridControl1);
            this.Controls.Add(this.panel1);
            this.Name = "Form2";
            this.Text = "Form2";
            this.panel1.ResumeLayout(false);
            ((System.ComponentModel.ISupportInitialize)(this.gridControl1)).EndInit();
            ((System.ComponentModel.ISupportInitialize)(this.bandedGridView1)).EndInit();
            this.ResumeLayout(false);

        }

        #endregion

        private System.Windows.Forms.Panel panel1;
        private System.Windows.Forms.Button button1;
        private DevExpress.XtraGrid.GridControl gridControl1;
        private DevExpress.XtraGrid.Views.BandedGrid.BandedGridView bandedGridView1;
    }
}

然后是界面的代码:

using System;
using System.Collections.Generic;
using System.Data;
using System.Drawing;
using System.Windows.Forms;
using DevExpress.Utils;
using DevExpress.XtraGrid.Views.BandedGrid;
using DevExpress.XtraGrid.Views.Base;

namespace WindowsFormsApplication1
{

    public partial class Form2 : Form
    {
        public Form2()
        {
            InitializeComponent();
            InitBandGrid();
        }

        private void button1_Click(object sender, EventArgs e)
        {
            gridControl1.DataSource = GetData();
        }

        List<ColumnHeaderInfo> InitColumnHeader()
        {
            string[] Day = { "星期日", "星期一", "星期二", "星期三", "星期四", "星期五", "星期六" };
            List<ColumnHeaderInfo> list = new List<ColumnHeaderInfo>();
            var date = DateTime.Now.Date;
            ; i < ; i++)
            {
                var colDate = date.AddDays(i);
                ColumnHeaderInfo info = new ColumnHeaderInfo
                {
                    Date = colDate.ToString("yyyy-MM-dd"),
                    WeekDay = Day[Convert.ToInt32(colDate.DayOfWeek.ToString("d"))]
                };
                list.Add(info);
            }
            return list;
        }

        /// <summary>
        /// 根据仓库权限初始化仓库显示列头
        /// </summary>
        private void InitBandGrid()
        {
            var list = InitColumnHeader();
            bandedGridView1.BeginUpdate();
            bandedGridView1.BeginDataUpdate();

            bandedGridView1.BandPanelRowHeight = ;
            bandedGridView1.RowHeight = ;
            bandedGridView1.OptionsView.ShowColumnHeaders = false; //因为有Band列了,所以把ColumnHeader隐藏
            bandedGridView1.OptionsView.AllowCellMerge = true;

            bandedGridView1.Bands.Clear();

            GridBand gbStoreType = new GridBand
            {
                Name = @"StoreType",
                Caption = @" "
            };
            BandedGridColumn col = new BandedGridColumn
            {
                Name = "colStoreType",
                Caption = @" ",
                FieldName = "StoreType",
                Visible = true
            };
            gbStoreType.Columns.Add(col); //把新增的显示字段绑定到gridband上,以供显示数据用
            bandedGridView1.Bands.Add(gbStoreType);

            gbStoreType.View.Columns.Add(col);

            if (list != null)
                foreach (var item in list)
                {
                    GridBand gbDate = new GridBand
                    {
                        Name = @"Date_" + item.Date,
                        Caption = item.Date
                    };
                    GridBand gbWeekDay = gbDate.Children.AddBand(item.WeekDay);

                    GridBand gbCol1 = gbWeekDay.Children.AddBand("预约收货时段");

                    //必须先将其绑定至bandgridview上后才能去添加column,否则无法加载数据
                    var bandName1 = "Date_WeekDay_col1_" + item.Date;
                    var bandFieldName1 = "Date_WeekDay_col1_" + item.Date;
                    BandedGridColumn col1 = new BandedGridColumn
                    {
                        Name = bandName1,
                        Caption = @"预约收货时段",
                        FieldName = bandFieldName1,
                        Visible = true
                    };
                    gbCol1.Columns.Add(col1); //把新增的显示字段绑定到gridband上,以供显示数据用

                    GridBand gbCol2 = gbWeekDay.Children.AddBand("实际预约/最大预约");
                    var bandName2 = "Date_WeekDay_col2_" + item.Date;
                    var bandFieldName2 = "Date_WeekDay_col2_" + item.Date;
                    BandedGridColumn col2 = new BandedGridColumn
                    {
                        Name = bandName2,
                        Caption = @"实际预约/最大预约",
                        FieldName = bandFieldName2,
                        Visible = true
                    };
                    gbCol2.Columns.Add(col2); //把新增的显示字段绑定到gridband上,以供显示数据用

                    bandedGridView1.Bands.Add(gbDate);
                    gbCol1.View.Columns.Add(col1);
                    gbCol2.View.Columns.Add(col2);

                    col1.OptionsColumn.AllowMerge = DefaultBoolean.False;
                    col2.OptionsColumn.AllowMerge = DefaultBoolean.False;

                    gbDate.AppearanceHeader.TextOptions.HAlignment = HorzAlignment.Center; //这是合并表头居中显示
                    gbWeekDay.AppearanceHeader.TextOptions.HAlignment = HorzAlignment.Center; //这是合并表头居中显示
                    gbCol1.AppearanceHeader.TextOptions.HAlignment = HorzAlignment.Center; //这是合并表头居中显示
                    gbCol2.AppearanceHeader.TextOptions.HAlignment = HorzAlignment.Center; //这是合并表头居中显示

                }
            bandedGridView1.EndDataUpdate();
            bandedGridView1.EndUpdate();
        }

        private void BandedGridView1_CustomDrawCell(object sender,
            RowCellCustomDrawEventArgs e)
        {
            var currentView = sender as BandedGridView;
            if (currentView == null) return;

            var row = currentView.GetDataRow(e.RowHandle);
            if (row["RedColumnIndex"] != DBNull.Value && !string.IsNullOrWhiteSpace(e.CellValue.ToString()))
            {
                string[] args = row["RedColumnIndex"].ToString()
                    .Split(new[] {','}, StringSplitOptions.RemoveEmptyEntries);
                foreach (var arg in args)
                {
                    if (e.Column.VisibleIndex == int.Parse(arg))
                    {
                        e.Appearance.BackColor = Color.Red;
                    }
                }
            }
            if (row["GreenColumnIndex"] != DBNull.Value && !string.IsNullOrWhiteSpace(e.CellValue.ToString()))
            {
                string[] args = row["GreenColumnIndex"].ToString()
                    .Split(new[] { ',' }, StringSplitOptions.RemoveEmptyEntries);
                foreach (var arg in args)
                {
                    if (e.Column.VisibleIndex == int.Parse(arg))
                    {
                        e.Appearance.BackColor = Color.Green;
                    }
                }
            }
        }

        DataTable GetData()
        {
            var list = InitColumnHeader();
            DataTable dt = new DataTable();
            dt.Columns.Add("StoreType");
            foreach (var item in list)
            {
                dt.Columns.Add("Date_WeekDay_col1_" + item.Date);
                dt.Columns.Add("Date_WeekDay_col2_" + item.Date);
            }
            dt.Columns.Add("RedColumnIndex");
            dt.Columns.Add("GreenColumnIndex");
            dt.Rows.Add("常温","8:00-9:00", "1000/800", "8:00-9:00", "1000/800", "8:00-9:00", "1000/800", "8:00-9:00",
                "1000/800", "8:00-9:00", "1000/800", "8:00-9:00", "1000/800", "8:00-9:00", "1000/800","2,4,6,8,10,12,14","");
            dt.Rows.Add("常温","8:00-9:00", "1000/800", "8:00-9:00", "1000/800", "8:00-9:00", "1000/800", "8:00-9:00",
                "1000/800", "8:00-9:00", "1000/800", "8:00-9:00", "1000/800", "8:00-9:00", "1000/800", "", "6,8,10,12,14");
            dt.Rows.Add("常温","8:00-9:00", "1000/800", "8:00-9:00", "1000/800", "8:00-9:00", "1000/800", "8:00-9:00",
                "1000/800", "8:00-9:00", "1000/800", "8:00-9:00", "1000/800", "8:00-9:00", "1000/800", "10,12,14","");
            dt.Rows.Add("冷冻", "8:00-9:00", "1000/800", "8:00-9:00", "1000/800", "8:00-9:00", "1000/800", "8:00-9:00",
               "1000/800", "8:00-9:00", "1000/800", "8:00-9:00", "1000/800", "8:00-9:00", "1000/800","","");
            dt.Rows.Add("冷冻", "8:00-9:00", "1000/800", "8:00-9:00", "1000/800", "8:00-9:00", "1000/800", "8:00-9:00",
                "1000/800", "8:00-9:00", "1000/800", "8:00-9:00", "1000/800", "8:00-9:00", "1000/800","","");
            dt.Rows.Add("冷冻", "8:00-9:00", "1000/800", "8:00-9:00", "1000/800", "8:00-9:00", "1000/800", "8:00-9:00",
                "1000/800", "8:00-9:00", "1000/800", "8:00-9:00", "1000/800", "8:00-9:00", "1000/800","","");
            return dt;
        }

        public class ColumnHeaderInfo
        {
            public string Date { get; set; }
            public string WeekDay { get; set; }
        }
    }
}

运行后的效果:

说明:

  • Demo数据仅为了展示,所以我在窗体代码里面写死了,绑定的动态数据源最好是DataTable类型,因为列名也是动态创建生成的,可扩展性比较强
  • 为了美观,设置了BrandedGridView的行高属性:BandPanelRowHeight表头高度,RowHeight每行数据单元格的行高
  • 需求中有预警设置指定单元格背景色的功能,以前用普通的DataGridView的时候,有CellFormating事件,处理比较方便,GridView控件里面有个类似的事件,叫CustomDrawCell,具体实现可参考以上代码

到此为止,基本上就实现了如何用代码动态创建生成复合表头的功能,希望可以对大家有所帮助,谢谢

基于DevExpress的BandedGridView动态生成多行(复合)表头的更多相关文章

  1. 编辑表格输入内容、根据input输入框输入数字动态生成表格行数、编辑表格内容提交传给后台数据处理

    编辑表格输入内容.根据input输入框输入数字动态生成表格行数.编辑表格内容提交传给后台数据处理 记录自己学习做的东西,写的小demo,希望对大家也有帮助! 代码如下: <!DOCTYPE ht ...

  2. Java获取后台数据,动态生成多行多列复选框

    本例目标: 获取后台数据集合,将集合的某个字段,比如:姓名,以复选框形式显示在HTML页面 应用场景: 获取数据库的人员姓名,将其显示在页面,供多项选择 效果如下: 一.后台 查询数据库,返回List ...

  3. winform中动态生成多行label,同时添加滚动条

    设计思路大概是这样的,Form内添加一个groupBox,groupBox内添加一个panel,panel的属性AutoScroll=true,在panel内动态添加label. 原始From如下: ...

  4. 分享我基于NPOI+ExcelReport实现的导入与导出EXCEL类库:ExcelUtility (续3篇-导出时动态生成多Sheet EXCEL)

    ExcelUtility 类库经过我(梦在旅途)近期不断的优化与新增功能,现已基本趋向稳定,功能上也基本可以满足绝大部份的EXCEL导出需求,该类库已在我们公司大型ERP系统全面使用,效果不错,今天应 ...

  5. 基于webpack的前端工程化开发解决方案探索(一):动态生成HTML(转)

    1.什么是工程化开发 软件工程的工程化开发概念由来已久,但对于前端开发来说,我们没有像VS或者eclipse这样量身打造的IDE,因为在大多数人眼中,前端代码无需编译,因此只要一个浏览器来运行调试就行 ...

  6. 论一种基于JS技术的WEB前端动态生成框图的方法

    前言 HTML是一种标记语言,由HTML的标签元素和文本编写的文档可被浏览器描述为一幅网页.通常情况下网页的实现是由HTML.CSS和Javascript三者结合完成的,HTML负责网页的结构,CSS ...

  7. DevExpress 中根据数据库字典动态生成卡式菜单 z

    第三方的Devexpress套件因为要使用权限机制控制不同用户进入系统显示菜单所以要配合字典数据动态生成.在WEB中这种问题灰常的轻松在winform里就稍微有点不同为了用DEV实现卡式菜单有组的概念 ...

  8. MSChart使用之动态生成多个多行ChartArea

    前台代码: <asp:Chart ID=" > <Titles> <asp:Title Name="Title1" runat=" ...

  9. Java利用poi生成word(包含插入图片,动态表格,行合并)

    转(小改): Java利用poi生成word(包含插入图片,动态表格,行合并) 2018年12月20日 09:06:51 wjw_11093010 阅读数:70 Java利用poi生成word(包含插 ...

随机推荐

  1. 微信小程序左滑删除功能

    效果图如下: wxml代码: <view class="container"> <view class="touch-item {{item.isTou ...

  2. 伤不起的微信小程序

    前段时间不是很忙,刚好公司需要开发一个微信小程序,于是我就入坑了(此坑还是有点深滴,请备好干粮). 我是一名iOS开发工程师,个人觉得入门开发小程序的话,需要基本的web前端知识,比如说:代码的书写格 ...

  3. 使用chart和echarts制作图表

      前  言 chart.js是一个简单.面向对象.为设计者和开发者准备的图表绘制工具库.它可以帮你用不同的方式让你的数据变得可视化.每种类型的图表都有动画效果,并且看上去非常棒,即便是在retina ...

  4. HDU 4135 Co-prime(容斥+数论)

    Co-prime Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)Total Su ...

  5. 计蒜之道 初赛第一场B 阿里天池的新任务(简单)

    阿里“天池”竞赛平台近日推出了一个新的挑战任务:对于给定的一串 DNA 碱基序列 tt,判断它在另一个根据规则生成的 DNA 碱基序列 ss 中出现了多少次. 首先,定义一个序列 ww: \displ ...

  6. javascript中自定义事件

    自定义事件:用户可以指定事件类型,这个类型实际上就是一个字符串,然后为这个类型的事件指定事件处理函数,可以注册多个事件处理函数(用数组管理),调用时,从多个事件处理函数中找到再调用. function ...

  7. Servlet的理解

    一.什么是Servlet? Servlet是用Java编写的web组件,实际上可以简单的理解为是用来处理请求的,为什么这么说,看了它的生命周期就知道了. 二.常见的Servlet容器 4容器顾名思义是 ...

  8. 发放福利:原价135元/年的阿里云CDN流量包(500GB)免费送

    不少朋友看过本站推荐的两篇文章:1. <阿里云全民云计算活动:云服务器ECS二折起>2. <阿里云双11优惠活动-爆款云服务器> 大部分人都说不错,很快下单购买了服务器,后续使 ...

  9. 《项目架构那点儿事》——快速构建Junit用例

    [前 言]按照惯例,在实际项目中我往往会对自己编写的程序进行测试,当测试通过后才能将其用于实战中,当然,编写单元测试是不可避免的,可以直接清晰的检验出 我们程序的可靠性.可只执行性,从中发现问题从而得 ...

  10. NodeJS 常用模块积累

    cluster&forever cluster & forever 虽然 nodejs 原生已经提供了 cluster 模块,大部分情况下可以满足我们的基本需求,但这两个模块 clus ...