C#开发学习笔记:向Dev控件库中的GridControl添加自定义复选框

本文介绍如何在Dev控件库的GridControl中添加并配置复选框列,包括通过代码实现多选及自定义复选框列的过程,并提供解决复选框状态异常问题的方法。

<span style="font-family: Arial, Helvetica, sans-serif; background-color: rgb(255, 255, 255);">Dev控件库自带的有复选框列,默认是不显示状态,如果需要则设置相关的两个属性:</span><pre name="code" class="csharp"><span>	</span>//设置grid显示选择列
        gridview.OptionsSelection.MultiSelect = true;
        gridview.OptionsSelection.MultiSelectMode = GridMultiSelectMode.CheckBoxRowSelect;

 

向Dev控件库中的GridControl添加自定义复选框

1.用代码添加:

 //设置grid数据行可以多选
        gridview.OptionsSelection.MultiSelect = true;//设置数据行可以多行选择
        gridview.OptionsSelection.MultiSelectMode = GridMultiSelectMode.RowSelect;//设置选中一整行
        DevExpress.XtraGrid.Columns.GridColumn col = new DevExpress.XtraGrid.Columns.GridColumn();
        col.FieldName = "Selection";
        col.Caption = "选择";
        col.VisibleIndex = 0;//设置列显示顺序,0表示显示为第一列
        col.SortMode = DevExpress.XtraGrid.ColumnSortMode.Value;
        col.DisplayFormat.FormatType = DevExpress.Utils.FormatType.Numeric;
        col.ColumnEdit = new RepositoryItemCheckEdit() //绑定该列为复选框列(checkedit控件)
        {
              NullStyle=DevExpress.XtraEditors.Controls.StyleIndeterminate.Unchecked,//设置未选中时,复选框的样子
              ValueChecked ="True",//设置选中时的value值
              ValueUnchecked = "False"//设置未选中时value的值
        };
        col.UnboundType = DevExpress.Data.UnboundColumnType.Boolean;//设置数据绑定的类型为boolean类型
        col.AppearanceCell.TextOptions.HAlignment = DevExpress.Utils.HorzAlignment.Near;                
        gridview.Appearance.HeaderPanel.TextOptions.HAlignment = DevExpress.Utils.HorzAlignment.Center;//设置列标题居中
        gridview.Columns.Add(col);
        col.AbsoluteIndex = 0;//由于数据源有隐藏列(会导致列重新排序),所以需要设置该属性为0(将添加的设置为第一列)
	DataTable dt = new DataTable();
        foreach (DevExpress.XtraGrid.Columns.GridColumn item in gridview.Columns)
        {
            if (item.Caption == "选择")
            {
                 dt.Columns.Add(item.FieldName);
                 break;
            }
        }
<span style="white-space:pre">	</span>//将dt与数据源合并(相当于将复选框列填加到数据源)
        ds.Tables[0].Merge(dt);
        gridcontrol.DataSource = ds.Tables[0];

在添加列时,遇见了选中复选框后,鼠标焦点移到其他cell时,复选框状态又还原为未选中状态(一开始未绑定数据源),查找资料之后添加了绑定复选框列;到数据源的代码,测试时问题依然存在,后来发现原因为在绑定列为复选框时,没有绑定ValueChecked 和ValueUnchecked的值 (这两个值我绑定的为String类型,用Run Designer添加列自动为Boolean类型,不知道是否为版本原因(我使用的是15.2.10,其他人使用的是低版本),其他人不修改这两个属性的值类型为String也不会出现上述问题,而我的却会出现)

2,直接使用Grid的Run Designer添加

可以参考http://blog.youkuaiyun.com/jiankunking/article/details/17992063

3.当cell的值改变时设置复选框为选中状态

   <span style="white-space:pre">	</span>private void gridView1_CellValueChanging(object sender, DevExpress.XtraGrid.Views.Base.CellValueChangedEventArgs e)
        {           
            gridView1.SetRowCellValue(e.RowHandle,gridView1.Columns.ColumnByFieldName("Selection"), "True");
        }

4.获取Grid中新增的选中的数据

        DataTable dt = new DataTable();
        DataTable result_dt = new DataTable();
        try
        {               
             int[] RowHandle = gridview.GetSelectedRows();
             dt=gridview.GetFocusedDataRow().Table;
             result_dt.Merge(gridview.GetFocusedDataRow().Table);
             result_dt.Clear();
             //将新增的数据行添加到dt数据表
             for (int i = 0; i < RowHandle.Count(); i++)
             {
                if (gridview.GetDataRow(RowHandle[i]) != null)
                     dt.Rows.Add(gridview.GetDataRow(RowHandle[i]));
             }
             //将选中的数据过滤出来(通过添加的选择列过滤)
             foreach (DataRow dr in dt.Rows)
             {
                 if(dr["Selection"]=="True")
                      result_dt.ImportRow(dr);
             }                
         }
一开始使用的获取数据行的代码是DataRow dr = gridview.GetFocusedDataRow();这样确实可以获取到数据行(只针对一行数据而言,如果是新增多行数据,则使用上面的方法),但是在使用dt.ImportRow(dr)时发现dr并没有添加到表中,原因是dr的 RowStateDeleted,Deleted 该状态表示该行不属于任何表,或则已经从表中分离出去了,不再属于任何表的 DataRow 对象。(相当于自由人),不能使用ImprotRow方法,所以使用dt.Rows.Add()方法





<think>我们使用DevExpressGridControl控件,并给其添加复选框列。 步骤: 1. 确保已经引用了DevExpress的相关库。 2. 在GridControl中创建GridView,并添加一个GridColumn,设置其ColumnEdit为CheckEdit(复选框编辑器)。 3. 绑定数据源,并处理复选框的状态变化(如果需要)。 以下是一个完整的示例: </think># 在C#中为DevExpress GridControl添加复选框列 在C#中为DevExpressGridControl控件添加复选框列非常简单且功能强大。以下我将详细介绍两种主要方法:使用`RepositoryItemCheckEdit`创建复选框列和使用`UnboundColumn`创建未绑定复选框列。 ## 方法1:使用RepositoryItemCheckEdit添加复选框列 ```csharp using DevExpress.XtraGrid; using DevExpress.XtraGrid.Views.Grid; using DevExpress.XtraEditors.Repository; using DevExpress.XtraEditors.Controls; using System.Data; using System.Windows.Forms; public partial class Form1 : Form { public Form1() { InitializeComponent(); // 1. 创建并配置GridControl GridControl gridControl = new GridControl(); gridControl.Dock = DockStyle.Fill; this.Controls.Add(gridControl); GridView gridView = new GridView(gridControl); gridControl.MainView = gridView; // 2. 创建数据源 DataTable table = new DataTable(); table.Columns.Add("ID", typeof(int)); table.Columns.Add("ProductName", typeof(string)); table.Columns.Add("Price", typeof(decimal)); table.Columns.Add("Selected", typeof(bool)); // 布尔类型列将自动显示为复选框 // 添加示例数据 table.Rows.Add(1, "Laptop", 1200.00, false); table.Rows.Add(2, "Smartphone", 800.00, true); table.Rows.Add(3, "Tablet", 500.00, false); gridControl.DataSource = table; // 3. 为"Selected"列添加复选框编辑器 RepositoryItemCheckEdit checkEdit = new RepositoryItemCheckEdit(); checkEdit.ValueChecked = true; // 复选框选中时对应的值 checkEdit.ValueUnchecked = false; // 复选框选中时对应的值 checkEdit.ValueGrayed = null; // 复选框不确定状态时对应的值 // 添加复选框样式 checkEdit.Appearance.TextOptions.HAlignment = DevExpress.Utils.HorzAlignment.Center; // 4. 将复选框编辑器应用到列 gridView.Columns["Selected"].ColumnEdit = checkEdit; gridView.Columns["Selected"].Caption = "选择"; gridView.Columns["Selected"].OptionsColumn.AllowEdit = true; gridView.Columns["Selected"].OptionsColumn.FixedWidth = true; gridView.Columns["Selected"].Width = 60; // 5. 添加复选框状态更改事件处理 gridView.CellValueChanged += (s, e) => { if (e.Column.FieldName == "Selected") { bool isChecked = (bool)gridView.GetRowCellValue(e.RowHandle, "Selected"); string productName = gridView.GetRowCellValue(e.RowHandle, "ProductName").ToString(); MessageBox.Show($"{productName} {(isChecked ? "已选中" : "已取消选择")}"); } }; // 6. 添加全选/取消全选按钮 SimpleButton selectAllButton = new SimpleButton(); selectAllButton.Text = "全选"; selectAllButton.Dock = DockStyle.Top; selectAllButton.Click += (s, e) => SetAllCheckboxes(gridView, true); this.Controls.Add(selectAllButton); SimpleButton deselectAllButton = new SimpleButton(); deselectAllButton.Text = "取消全选"; deselectAllButton.Dock = DockStyle.Top; deselectAllButton.Click += (s, e) => SetAllCheckboxes(gridView, false); this.Controls.Add(deselectAllButton); } // 设置所有复选框状态的辅助方法 private void SetAllCheckboxes(GridView view, bool state) { view.BeginUpdate(); try { for (int i = 0; i < view.DataRowCount; i++) { view.SetRowCellValue(i, "Selected", state); } } finally { view.EndUpdate(); } } } ``` ### 代码详解 1. **网格控件初始化** - 创建`GridControl`并设置其停靠方式 - 关联`GridView`作为主视图 2. **数据源准备** - 创建`DataTable`作为数据源 - 添加包含布尔类型的列(`Selected`),这是显示复选框的关键 - 填充示例数据 3. **复选框编辑器配置** - 创建`RepositoryItemCheckEdit`对象 - 设置复选框三种状态对应的值:选中(true)、未选中(false)、不确定(null) - 自定义复选框外观样式 4. **列配置** - 将复选框编辑器应用到"Selected"列 - 设置列的标题、宽度和编辑属性 5. **事件处理** - 处理`CellValueChanged`事件响应复选框状态变化 - 获取当前行数据并显示提示消息 6. **批量操作** - 添加全选/取消全选按钮 - 实现`SetAllCheckboxes`方法批量更新复选框状态 ## 方法2:使用UnboundColumn添加未绑定复选框列 ```csharp public void AddUnboundCheckboxColumn() { // 获取GridView GridView view = gridControl1.MainView as GridView; // 添加未绑定列 GridColumn checkColumn = view.Columns.AddVisible("Selection", "选择"); checkColumn.UnboundType = DevExpress.Data.UnboundColumnType.Boolean; checkColumn.Visible = true; checkColumn.OptionsColumn.AllowEdit = true; // 创建并应用复选框编辑器 RepositoryItemCheckEdit checkEdit = new RepositoryItemCheckEdit(); view.Columns["Selection"].ColumnEdit = checkEdit; // 处理自定义数据 view.CustomUnboundColumnData += (s, e) => { if (e.Column.FieldName == "Selection") { // 根据行号设置初始值 if (e.IsGetData) { e.Value = (e.ListSourceRowIndex % 2 == 0); // 偶数行默认选中 } else if (e.IsSetData) { // 保存更改后的值(如果需要) // 实际应用中可能保存到数据源或集合中 } } }; // 添加复选框列状态更改事件 view.CellValueChanged += (s, e) => { if (e.Column.FieldName == "Selection") { bool isChecked = (bool)e.Value; int rowHandle = e.RowHandle; string id = view.GetRowCellValue(rowHandle, "ID").ToString(); // 在实际应用中处理选择变更逻辑 Console.WriteLine($"行 {rowHandle} (ID:{id}) 选择状态变更为: {isChecked}"); } }; } ``` ### 代码详解 1. **添加未绑定列** - 使用`AddVisible`方法创建新列 - 设置`UnboundType`为`Boolean`表示布尔类型 - 启用列编辑功能 2. **自定义数据提供** - 处理`CustomUnboundColumnData`事件 - 在`IsGetData`分支中提供初始值(这里根据行号设置) - 在`IsSetData`分支中响应值变更(实际应用中可保存变更) 3. **事件处理** - 处理`CellValueChanged`事件响应复选框变化 - 获取相关行数据并执行业务逻辑 ## 复选框列高级功能 ### 三态复选框实现 ```csharp RepositoryItemCheckEdit triStateCheckEdit = new RepositoryItemCheckEdit(); triStateCheckEdit.AllowGrayed = true; // 启用三态功能 triStateCheckEdit.ValueChecked = true; triStateCheckEdit.ValueUnchecked = false; triStateCheckEdit.ValueGrayed = null; // 不确定状态 // 添加三态复选框事件 triStateCheckEdit.EditValueChanged += (s, e) => { CheckEdit edit = s as CheckEdit; if (edit.CheckState == CheckState.Indeterminate) { MessageBox.Show("不确定状态选择"); } }; ``` ### 自定义复选框外观 ```csharp RepositoryItemCheckEdit styledCheck = new RepositoryItemCheckEdit(); styledCheck.Appearance.Font = new Font("Tahoma", 10); styledCheck.Appearance.ForeColor = Color.Blue; styledCheck.Appearance.Options.UseFont = true; styledCheck.Appearance.Options.UseForeColor = true; // 自定义复选框大小和位置 styledCheck.VerticalAlignment = VerticalAlignment.Center; styledCheck.HorizontalAlignment = HorizontalAlignment.Center; ``` ### 复选框列过滤 ```csharp // 启用筛选功能 gridView1.OptionsView.ShowAutoFilterRow = true; // 为复选框添加筛选控件 RepositoryItemCheckEdit filterCheckEdit = new RepositoryItemCheckEdit(); gridView1.Columns["Selected"].FilterInfo = new ColumnFilterInfo("Selected = true"); // 默认筛选选中项 ``` ## 完整示例:带复选框列的GridControl实现 ```csharp using DevExpress.XtraGrid; using DevExpress.XtraGrid.Views.Grid; using DevExpress.XtraEditors.Repository; using System.Data; using System.Drawing; using System.Windows.Forms; public class CheckboxGridForm : Form { private GridControl gridControl; private GridView gridView; public CheckboxGridForm() { InitializeComponent(); // 创建GridControl gridControl = new GridControl(); gridControl.Dock = DockStyle.Fill; this.Controls.Add(gridControl); // 创建GridView gridView = new GridView(gridControl); gridControl.MainView = gridView; // 准备数据 LoadData(); // 添加复选框列 AddCheckboxColumn(); // 添加操作按钮 CreateActionButtons(); } private void LoadData() { DataTable dt = new DataTable(); dt.Columns.Add("ID", typeof(int)); dt.Columns.Add("Product", typeof(string)); dt.Columns.Add("Category", typeof(string)); dt.Columns.Add("Price", typeof(decimal)); // 添加示例数据 dt.Rows.Add(1, "Laptop", "Electronics", 1200.00m); dt.Rows.Add(2, "Smartphone", "Electronics", 800.00m); dt.Rows.Add(3, "Coffee Maker", "Kitchen", 150.00m); dt.Rows.Add(4, "Blender", "Kitchen", 80.00m); dt.Rows.Add(5, "Desk Chair", "Furniture", 200.00m); gridControl.DataSource = dt; } private void AddCheckboxColumn() { // 创建复选框列 GridColumn checkColumn = new GridColumn(); checkColumn.FieldName = "Selected"; checkColumn.Caption = "选择"; checkColumn.Visible = true; checkColumn.UnboundType = DevExpress.Data.UnboundColumnType.Boolean; // 创建并配置复选框编辑器 RepositoryItemCheckEdit checkEdit = new RepositoryItemCheckEdit(); checkEdit.ValueChecked = true; checkEdit.ValueUnchecked = false; checkEdit.AllowGrayed = false; // 设置列编辑器 checkColumn.ColumnEdit = checkEdit; gridView.Columns.Add(checkColumn); // 自定义列外观 checkColumn.AppearanceCell.TextOptions.HAlignment = DevExpress.Utils.HorzAlignment.Center; checkColumn.Width = 60; checkColumn.OptionsColumn.AllowEdit = true; checkColumn.OptionsColumn.AllowFocus = true; // 处理复选框变化事件 gridView.CellValueChanging += (s, e) => { if (e.Column.FieldName == "Selected") { bool newValue = (bool)e.Value; int id = (int)gridView.GetRowCellValue(e.RowHandle, "ID"); string product = gridView.GetRowCellValue(e.RowHandle, "Product").ToString(); // 在实际应用中处理选择变更 StatusLabel.Text = $"{product} {(newValue ? "已选中" : "已取消")}"; } }; // 初始设置所有行未选中 for (int i = 0; i < gridView.RowCount; i++) { gridView.SetRowCellValue(i, checkColumn, false); } } private void CreateActionButtons() { FlowLayoutPanel panel = new FlowLayoutPanel(); panel.Dock = DockStyle.Bottom; panel.Height = 40; panel.FlowDirection = FlowDirection.LeftToRight; // 全选按钮 Button selectAllButton = new Button(); selectAllButton.Text = "全选"; selectAllButton.Click += (s, e) => SetAllCheckboxes(true); panel.Controls.Add(selectAllButton); // 取消全选按钮 Button deselectAllButton = new Button(); deselectAllButton.Text = "取消全选"; deselectAllButton.Click += (s, e) => SetAllCheckboxes(false); panel.Controls.Add(deselectAllButton); // 获取选中项按钮 Button getSelectedButton = new Button(); getSelectedButton.Text = "获取选中项"; getSelectedButton.Click += (s, e) => GetSelectedItems(); panel.Controls.Add(getSelectedButton); // 状态标签 StatusLabel = new Label(); StatusLabel.Dock = DockStyle.Bottom; StatusLabel.Height = 20; StatusLabel.Text = "就绪"; this.Controls.Add(panel); this.Controls.Add(StatusLabel); } private void SetAllCheckboxes(bool state) { gridView.BeginUpdate(); try { for (int i = 0; i < gridView.DataRowCount; i++) { gridView.SetRowCellValue(i, "Selected", state); } } finally { gridView.EndUpdate(); } StatusLabel.Text = $"已{(state ? "全选" : "取消全选")}所有项"; } private void GetSelectedItems() { StringBuilder sb = new StringBuilder("选中:\n"); for (int i = 0; i < gridView.DataRowCount; i++) { bool isSelected = (bool)gridView.GetRowCellValue(i, "Selected"); if (isSelected) { string product = gridView.GetRowCellValue(i, "Product").ToString(); decimal price = (decimal)gridView.GetRowCellValue(i, "Price"); sb.AppendLine($"{product} - {price:C}"); } } MessageBox.Show(sb.ToString(), "选中项信息"); } private Label StatusLabel; } ``` ## 注意事项 1. **数据绑定** - 使用绑定数据源时,确保数据源中有布尔类型字段 - 使用未绑定列时,需要处理`CustomUnboundColumnData`事件 2. **性能优化** - 批量更新时使用`BeginUpdate`/`EndUpdate` - 避免在循环中频繁刷新UI 3. **事件处理** - `CellValueChanging`:值即将改变时触发 - `CellValueChanged`:值已改变后触发 - `EditValueChanged`:编辑器值改变时触发 4. **样式定制** - 使用`Appearance`属性定制复选框外观 - 通过`RepositoryItemCheckEdit`自定义编辑器行为 5. **复选框状态** - 默认双态:选中(true)/未选中(false) - 三态:增加不确定状态(null)
评论 1
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值