首页 文章

DataGridView ComboBox列将接受任何文本

提问于
浏览
2

我希望 DataGridView 的列使用 ComboBoxStyle.DropDown 样式的ComboBox,用户可以在下拉列表中选择其中一个条目,也可以键入任意文本 .

目前,我正在使用this answer中的代码,我可以自由地键入ComboBox的文本框部分,但是如果我键入的东西不会被提交回数据源并且该字段将恢复为原始选择 . 此外,如果我以编程方式将文本设置为不在下拉列表中的内容,我会收到 DataError 事件"DataGridViewComboBoxCell value is not valid."

我正在使用数据绑定; DataGridView 本身绑定到 BindingList<T> .

this question不同,我不希望将自由文本添加到下拉列表中 .

要清楚,列数据类型是 string ,我不希望它根据ComboBox的下拉列表(或其他任何内容)进行验证 .

(我是否必须按照How to: Host Controls in Windows Forms DataGridView Cells中的描述创建我自己的自定义 DataGridViewColumn 后代?)

2 回答

  • 1

    我找到了一个简单的,如果冗长的答案 . (但我仍然想知道是否有一种方法可以使用标准的 DataGridViewComboBoxColumn 类型 . )

    我按照How to: Host Controls in Windows Forms DataGridView Cells中的方法进行操作 . 我的完整解决方案太长了,无法在此发布,但我可以总结这些更改,使其使用 ComboBox 而不是示例的 DateTimePicker 控件 .

    • 分别重命名三个类 DropDownComboBoxColumnDropDownComboBoxCellDropDownComboBoxEditingControl .

    • string 替换 DateTime 到处 .

    • 将属性 public ComboBoxStyle DropDownStyle { get; set; } 添加到 DropDownComboBoxColumn 以允许调用代码设置下拉样式 .

    • DropDownComboBoxCell 构造函数中删除代码 .

    • DropDownComboBoxEditingControl 构造函数中删除代码 .

    • 使 DropDownComboBoxEditingControl 派生自 ComboBox 而不是 DateTimePicker .

    • OnValueChanged 替换为 OnTextChanged 以说明 ComboBoxDateTimePicker 中的不同命名 .

    • 使 EditingControlFormattedValue 属性获取并设置继承的 Text 属性(而不是 Value ),并且不需要解析 .

    • 使 ApplyCellStyleToEditingControl 设置 ForeColorBackColor 而不是 CalendarForeColorCalendarMonthBackground .

    • 使 EditingControlWantsInputKey 也声明F4,因此它可用于打开和关闭下拉列表 .

    • 将以下代码添加到 PrepareEditingControlForEdit

    DropDownComboBoxColumn col = _dataGridView.Columns[_dataGridView.CurrentCell.ColumnIndex] as DropDownComboBoxColumn;
    if (col == null)
    {
      throw new InvalidCastException("Must be in a DropDownComboBoxColumn");
    }
    DropDownStyle = col.DropDownStyle;
    // (If you don't explicitly set the Text then the current value is
    // always replaced with one from the drop-down list when edit begins.)
    Text = _dataGridView.CurrentCell.Value as string;
    SelectAll();
    

    处理 DataGridViewEditingControlShowing 事件,如OhBeWise's回答相关问题以设置下拉项目,如果需要,还可以自动完成模式:

    private void dataGridView1_EditingControlShowing(object sender, DataGridViewEditingControlShowingEventArgs e)
    {
      ComboBox box = e.Control as ComboBox;
      if (box != null)
      {
        box.AutoCompleteSource = AutoCompleteSource.ListItems;
        box.AutoCompleteMode = AutoCompleteMode.SuggestAppend;
        box.DataSource = _dropDownItems;
      }
    }
    

    如果你想为所有行提供相同的下拉项,那么你总是可以将它作为 DropDownComboBoxColumn 的属性,如 DropDownStyle 并在 PrepareEditingControlForEdit 中设置它以避免必须处理 EditingControlShowing .

  • 0

    为此,您可以通过下面提到的后端代码在数据网格视图中添加列:

    using System.Data.SqlServerCe;
    
    string sqlConnection = "Data Source";
    SqlCeConnection conn = new SqlCeConnection(sqlConnection);
    //Get bind from database.
    string qryGetCategory = "Query to get data for combo box";
    SqlCeCommand cmdCat = new SqlCeCommand(qryGetCategory, conn);
    SqlCeDataAdapter daCat = new SqlCeDataAdapter(qryGetCategory, conn);
    DataTable dtCat = new DataTable();
    daCat.Fill(dtCat);
    
    //Combobox column.
    DataGridViewComboBoxColumn ComboBoxCol = new DataGridViewComboBoxColumn();
    ComboBoxCol.DataSource = dtCat;
    ComboBoxCol.Name = "Column name";
    ComboBoxCol.ValueMember = "Value of member";
    ComboBoxCol.DisplayMember = "Member to be show";
    ComboBoxCol.DropDownStyle = ComboBoxStyle.DropDown;
    datagridview.Columns.Add(ComboBoxCol);
    

    请尝试它可能会解决您的问题 .

相关问题