到官网得到消息自13.2版本后的Dev Grid中均内置了CheckBox列多选功能。在寻找答案的过程的成果进行记录。
一、13.2版本以后用法
- 启用多选列
对Gird中的View进行以下属性设置:
gridView1.OptionsSelection.MultiSelect = true; gridView1.OptionsSelection.MultiSelectMode = GridMultiSelectMode.CheckBoxRowSelect;
- 清除当前选择
在选中列时后,可配置在选中列以外的地方点击时候会清除当前的选择。14以后才有此功能
gridView1.OptionsSelection.ResetSelectionClickOutsideCheckboxSelector = true; - 获取选中的行
二、早起版本实现
相关链接:http://www.devexpress.com/Support/Center/Example/Details/E1271
- GridCheckMarksSelection类
1 public class GridCheckMarksSelection { 2 protected GridView _view; 3 protected ArrayList selection; 4 GridColumn column; 5 RepositoryItemCheckEdit edit; 6 const int CheckboxIndent = 4; 7 8 public GridCheckMarksSelection() { 9 selection = new ArrayList(); 10 } 11 12 public GridCheckMarksSelection(GridView view) : this() { 13 View = view; 14 } 15 public GridView View { 16 get { return _view; } 17 set { 18 if (_view != value) { 19 Detach(); 20 Attach(value); 21 } 22 } 23 } 24 public GridColumn CheckMarkColumn { get { return column; } } 25 26 public int SelectedCount { get { return selection.Count; } } 27 public object GetSelectedRow(int index) { 28 return selection[index]; 29 } 30 public int GetSelectedIndex(object row) { 31 return selection.IndexOf(row); 32 } 33 public void ClearSelection() { 34 selection.Clear(); 35 Invalidate(); 36 } 37 public void SelectAll() { 38 selection.Clear(); 39 // fast (won't work if the grid is filtered) 40 //if(_view.DataSource is ICollection) 41 // selection.AddRange(((ICollection)_view.DataSource)); 42 //else 43 // slow: 44 for (int i = 0; i < _view.DataRowCount; i++) 45 selection.Add(_view.GetRow(i)); 46 Invalidate(); 47 } 48 public void SelectGroup(int rowHandle, bool select) { 49 if (IsGroupRowSelected(rowHandle) && select) return; 50 for (int i = 0; i < _view.GetChildRowCount(rowHandle); i++) { 51 int childRowHandle = _view.GetChildRowHandle(rowHandle, i); 52 if (_view.IsGroupRow(childRowHandle)) 53 SelectGroup(childRowHandle, select); 54 else 55 SelectRow(childRowHandle, select, false); 56 } 57 Invalidate(); 58 } 59 public void SelectRow(int rowHandle, bool select) { 60 SelectRow(rowHandle, select, true); 61 } 62 public void InvertRowSelection(int rowHandle) { 63 if (View.IsDataRow(rowHandle)) { 64 SelectRow(rowHandle, !IsRowSelected(rowHandle)); 65 } 66 if (View.IsGroupRow(rowHandle)) { 67 SelectGroup(rowHandle, !IsGroupRowSelected(rowHandle)); 68 } 69 } 70 public bool IsGroupRowSelected(int rowHandle) { 71 for (int i = 0; i < _view.GetChildRowCount(rowHandle); i++) { 72 int row = _view.GetChildRowHandle(rowHandle, i); 73 if (_view.IsGroupRow(row)) { 74 if (!IsGroupRowSelected(row)) return false; 75 } else 76 if (!IsRowSelected(row)) return false; 77 } 78 return true; 79 } 80 public bool IsRowSelected(int rowHandle) { 81 if (_view.IsGroupRow(rowHandle)) 82 return IsGroupRowSelected(rowHandle); 83 84 object row = _view.GetRow(rowHandle); 85 return GetSelectedIndex(row) != -1; 86 } 87 88 protected virtual void Attach(GridView view) { 89 if (view == null) return; 90 selection.Clear(); 91 this._view = view; 92 view.BeginUpdate(); 93 try { 94 edit = view.GridControl.RepositoryItems.Add("CheckEdit") as RepositoryItemCheckEdit; 95 96 column = view.Columns.Add(); 97 column.OptionsColumn.AllowSort = DevExpress.Utils.DefaultBoolean.False; 98 column.Visible = true; 99 column.VisibleIndex = 0; 100 column.FieldName = "CheckMarkSelection"; 101 column.Caption = "Mark"; 102 column.OptionsColumn.ShowCaption = false; 103 column.OptionsColumn.AllowEdit = false; 104 column.OptionsColumn.AllowSize = false; 105 column.UnboundType = DevExpress.Data.UnboundColumnType.Boolean; 106 column.Width = GetCheckBoxWidth(); 107 column.ColumnEdit = edit; 108 109 view.Click += new EventHandler(View_Click); 110 view.CustomDrawColumnHeader += new ColumnHeaderCustomDrawEventHandler(View_CustomDrawColumnHeader); 111 view.CustomDrawGroupRow += new RowObjectCustomDrawEventHandler(View_CustomDrawGroupRow); 112 view.CustomUnboundColumnData += new CustomColumnDataEventHandler(view_CustomUnboundColumnData); 113 view.KeyDown += new KeyEventHandler(view_KeyDown); 114 view.RowStyle += new RowStyleEventHandler(view_RowStyle); 115 } finally { 116 view.EndUpdate(); 117 } 118 } 119 protected virtual void Detach() { 120 if (_view == null) return; 121 if (column != null) 122 column.Dispose(); 123 if (edit != null) { 124 _view.GridControl.RepositoryItems.Remove(edit); 125 edit.Dispose(); 126 } 127 128 _view.Click -= new EventHandler(View_Click); 129 _view.CustomDrawColumnHeader -= new ColumnHeaderCustomDrawEventHandler(View_CustomDrawColumnHeader); 130 _view.CustomDrawGroupRow -= new RowObjectCustomDrawEventHandler(View_CustomDrawGroupRow); 131 _view.CustomUnboundColumnData -= new CustomColumnDataEventHandler(view_CustomUnboundColumnData); 132 _view.KeyDown -= new KeyEventHandler(view_KeyDown); 133 _view.RowStyle -= new RowStyleEventHandler(view_RowStyle); 134 135 _view = null; 136 } 137 protected int GetCheckBoxWidth() { 138 DevExpress.XtraEditors.ViewInfo.CheckEditViewInfo info = edit.CreateViewInfo() as DevExpress.XtraEditors.ViewInfo.CheckEditViewInfo; 139 int width = 0; 140 GraphicsInfo.Default.AddGraphics(null); 141 try { 142 width = info.CalcBestFit(GraphicsInfo.Default.Graphics).Width; 143 } finally { 144 GraphicsInfo.Default.ReleaseGraphics(); 145 } 146 return width + CheckboxIndent * 2; 147 } 148 protected void DrawCheckBox(Graphics g, Rectangle r, bool Checked) { 149 DevExpress.XtraEditors.ViewInfo.CheckEditViewInfo info; 150 DevExpress.XtraEditors.Drawing.CheckEditPainter painter; 151 DevExpress.XtraEditors.Drawing.ControlGraphicsInfoArgs args; 152 info = edit.CreateViewInfo() as DevExpress.XtraEditors.ViewInfo.CheckEditViewInfo; 153 painter = edit.CreatePainter() as DevExpress.XtraEditors.Drawing.CheckEditPainter; 154 info.EditValue = Checked; 155 info.Bounds = r; 156 info.CalcViewInfo(g); 157 args = new DevExpress.XtraEditors.Drawing.ControlGraphicsInfoArgs(info, new DevExpress.Utils.Drawing.GraphicsCache(g), r); 158 painter.Draw(args); 159 args.Cache.Dispose(); 160 } 161 void Invalidate() { 162 _view.CloseEditor(); 163 _view.BeginUpdate(); 164 _view.EndUpdate(); 165 } 166 void SelectRow(int rowHandle, bool select, bool invalidate) { 167 if (IsRowSelected(rowHandle) == select) return; 168 object row = _view.GetRow(rowHandle); 169 if (select) 170 selection.Add(row); 171 else 172 selection.Remove(row); 173 if (invalidate) { 174 Invalidate(); 175 } 176 } 177 void view_CustomUnboundColumnData(object sender, CustomColumnDataEventArgs e) { 178 if (e.Column == CheckMarkColumn) { 179 if (e.IsGetData) 180 e.Value = IsRowSelected(View.GetRowHandle(e.ListSourceRowIndex)); 181 else 182 SelectRow(View.GetRowHandle(e.ListSourceRowIndex), (bool)e.Value); 183 } 184 } 185 void view_KeyDown(object sender, KeyEventArgs e) { 186 if (View.FocusedColumn != column || e.KeyCode != Keys.Space) return; 187 InvertRowSelection(View.FocusedRowHandle); 188 } 189 void View_Click(object sender, EventArgs e) { 190 GridHitInfo info; 191 Point pt = _view.GridControl.PointToClient(Control.MousePosition); 192 info = _view.CalcHitInfo(pt); 193 if (info.Column == column) { 194 if (info.InColumn) { 195 if (SelectedCount == _view.DataRowCount) 196 ClearSelection(); 197 else 198 SelectAll(); 199 } 200 if (info.InRowCell) { 201 InvertRowSelection(info.RowHandle); 202 } 203 } 204 if (info.InRow && _view.IsGroupRow(info.RowHandle) && info.HitTest != GridHitTest.RowGroupButton) { 205 InvertRowSelection(info.RowHandle); 206 } 207 } 208 void View_CustomDrawColumnHeader(object sender, ColumnHeaderCustomDrawEventArgs e) { 209 if (e.Column == column) { 210 e.Info.InnerElements.Clear(); 211 e.Painter.DrawObject(e.Info); 212 DrawCheckBox(e.Graphics, e.Bounds, SelectedCount == _view.DataRowCount); 213 e.Handled = true; 214 } 215 } 216 void View_CustomDrawGroupRow(object sender, RowObjectCustomDrawEventArgs e) { 217 DevExpress.XtraGrid.Views.Grid.ViewInfo.GridGroupRowInfo info; 218 info = e.Info as DevExpress.XtraGrid.Views.Grid.ViewInfo.GridGroupRowInfo; 219 220 info.GroupText = " " + info.GroupText.TrimStart(); 221 e.Info.Paint.FillRectangle(e.Graphics, e.Appearance.GetBackBrush(e.Cache), e.Bounds); 222 e.Painter.DrawObject(e.Info); 223 224 Rectangle r = info.ButtonBounds; 225 r.Offset(r.Width + CheckboxIndent * 2 - 1, 0); 226 DrawCheckBox(e.Graphics, r, IsGroupRowSelected(e.RowHandle)); 227 e.Handled = true; 228 } 229 void view_RowStyle(object sender, RowStyleEventArgs e) { 230 if (IsRowSelected(e.RowHandle)) { 231 e.Appearance.BackColor = SystemColors.Highlight; 232 e.Appearance.ForeColor = SystemColors.HighlightText; 233 } 234 } 235 }
- 使用方法
1 public Form1() 2 { 3 InitializeComponent(); 4 new GridCheckMarksSelection(gridView1); 5 }